import { Injectable, Logger } from "@nestjs/common";
import { ConfigService } from "@nestjs/config";
import { GeminiService } from "../gemini/gemini.service";
import { PredictionCardDto } from "./dto/prediction-card.dto";
import axios from "axios";

const SYSTEM_PROMPT = `Sen profesyonel bir spor analisti ve sosyal medya içerik üreticisisin.
Verilen maç tahmin verisini kullanarak kısa, etkili ve ilgi çekici sosyal medya postları yazıyorsun.

KURALLAR:
- Türkçe yaz
- Maximum 250 karakter (X/Twitter uyumlu)
- Emoji kullan ama abartma (2-4 emoji yeterli)
- Skor tahminini vurgula
- Güven yüzdesini belirt
- Lig, ülke, takım adları ve ana tahminleri SEO için doğal şekilde geçir
- İlgili hashtag'leri ekle (#PremierLeague, #SüperLig vb.)
- KESİNLİKLE "kesin kazanır", "garanti" gibi ifadeler KULLANMA
- "Tahminimiz", "Beklentimiz", "Analizimiz" gibi ifadeler kullan
- Farklı maçlar için farklı tarzda yaz, tekdüze olma
- Son satıra her zaman hashtag'leri koy`;

@Injectable()
export class CaptionGeneratorService {
  private readonly logger = new Logger(CaptionGeneratorService.name);
  private readonly ollamaBaseUrl: string;
  private readonly ollamaModel: string;

  constructor(
    private readonly geminiService: GeminiService,
    private readonly configService: ConfigService,
  ) {
    this.ollamaBaseUrl =
      this.configService.get<string>("OLLAMA_BASE_URL") ||
      "http://localhost:11434";
    this.ollamaModel =
      this.configService.get<string>("OLLAMA_MODEL") ||
      this.configService.get<string>("SOCIAL_POSTER_OLLAMA_MODEL") ||
      "";
  }

  /**
   * Generate a social media caption for a match prediction using Gemini AI.
   */
  async generateCaption(card: PredictionCardDto): Promise<string> {
    if (this.ollamaModel) {
      const caption = await this.generateWithOllama(card);
      if (caption) return caption;
    }

    if (!this.geminiService.isAvailable()) {
      this.logger.warn("Gemini not available, using template caption");
      return this.generateFallbackCaption(card);
    }

    const prompt = this.buildPrompt(card);

    try {
      const { text } = await this.geminiService.generateText(prompt, {
        systemPrompt: SYSTEM_PROMPT,
        temperature: 0.8,
        maxTokens: 300,
      });

      // Ensure hashtags are present
      const caption = this.ensureHashtags(text, card);
      this.logger.log(
        `Caption generated for ${card.homeTeam} vs ${card.awayTeam}`,
      );
      return caption;
    } catch (error) {
      this.logger.error("Gemini caption generation failed", error);
      return this.generateFallbackCaption(card);
    }
  }

  private async generateWithOllama(card: PredictionCardDto): Promise<string> {
    const prompt = `${SYSTEM_PROMPT}

${this.buildPrompt(card)}`;

    try {
      const response = await axios.post(
        `${this.ollamaBaseUrl.replace(/\/$/, "")}/api/generate`,
        {
          model: this.ollamaModel,
          prompt,
          stream: false,
          options: {
            temperature: 0.7,
            num_predict: 260,
          },
        },
        { timeout: 20000 },
      );

      const text = String(response.data?.response || "").trim();
      if (!text) return "";

      this.logger.log(
        `Ollama caption generated for ${card.homeTeam} vs ${card.awayTeam}`,
      );
      return this.ensureHashtags(text, card);
    } catch (error) {
      this.logger.warn(`Ollama caption generation failed: ${error.message}`);
      return "";
    }
  }

  private buildPrompt(card: PredictionCardDto): string {
    const topPicksText = card.topPicks
      .map(
        (p, i) =>
          `${i + 1}. ${p.market} (${p.marketEn}) — ${p.pick} — Güven: %${p.confidence} — Oran: ${p.odds}`,
      )
      .join("\n");

    return `Aşağıdaki maç tahmin verisini kullanarak bir sosyal medya postu oluştur:

MAÇ: ${card.homeTeam} vs ${card.awayTeam}
SPOR: ${card.sport === "basketball" ? "Basketbol" : "Futbol"}
LİG: ${card.leagueName}
ÜLKE/BÖLGE: ${card.countryName || "-"}
TARİH: ${card.matchDate}
${card.sport === "basketball" ? "İLK DEVRE" : "İLK YARI"} SKOR TAHMİNİ: ${card.htScore}
MAÇ SONU SKOR TAHMİNİ: ${card.ftScore}
SKOR GÜVEN: %${card.scoreConfidence}
RİSK SEVİYESİ: ${card.riskLevel}

EN İYİ TAHMİNLER:
${topPicksText}

Sadece post metnini yaz, başka hiçbir şey ekleme.`;
  }

  private ensureHashtags(text: string, card: PredictionCardDto): string {
    // If no hashtags in text, add them
    if (!text.includes("#")) {
      const leagueTag = card.leagueName
        .replace(/\s+/g, "")
        .replace(/[^a-zA-Z0-9üöçşğıİÜÖÇŞĞ]/g, "");
      const homeTag = card.homeTeam.replace(/\s+/g, "");
      const awayTag = card.awayTeam.replace(/\s+/g, "");
      const sportTag = card.sport === "basketball" ? "Basketbol" : "Futbol";
      text += `\n\n#${leagueTag} #${homeTag} #${awayTag} #${sportTag}`;
    }
    return text.trim();
  }

  /**
   * Fallback caption when Gemini is not available.
   */
  private generateFallbackCaption(card: PredictionCardDto): string {
    const topPick = card.topPicks[0];
    const leagueTag = card.leagueName
      .replace(/\s+/g, "")
      .replace(/[^a-zA-Z0-9üöçşğıİÜÖÇŞĞ]/g, "");

    const sportLabel = card.sport === "basketball" ? "Basketbol" : "Futbol";
    const halfLabel = card.sport === "basketball" ? "İD" : "İY";

    return `⚡ ${card.leagueName}${card.countryName ? ` (${card.countryName})` : ""}: ${card.homeTeam} vs ${card.awayTeam}
🎯 ${sportLabel} tahminimiz: ${card.ftScore} (${halfLabel}: ${card.htScore})
📊 Güven: %${card.scoreConfidence}
${topPick ? `🔥 ${topPick.market}: ${topPick.pick} (%${topPick.confidence})` : ""}

#${leagueTag} #${sportLabel} #MaçTahmini #iddaai`.trim();
  }
}
