// services/quote-writer.service.ts
import { Injectable, Logger } from '@nestjs/common';
import { ConfigService } from '@nestjs/config';
import { AIProviderFactory } from '../providers/ai-provider.factory';
import { ProviderRouterService } from './provider-router.service';
import { LengthStrategyService } from './length-strategy.service';
import { ReviewerService } from './reviewer.service';
import { GenerateQuoteDto } from '../dto/generate-quote.dto';
import { buildQuotePrompt, suggestQuoteType } from '../prompts/quote.templates';
import { AccountTier } from '../enum/account-tier.enum';
import { Platform } from '../enum/platform.enum';
import { ContentStyle } from '../enum/style.enum';
import { ContentTone } from '../enum/tone.enum';
import {calculateTokenBudget} from "../../../common/utils/token-calculator";
import {QuoteType} from "../enum/quote-type.enum";

@Injectable()
export class QuoteWriterService {
    private readonly logger = new Logger(QuoteWriterService.name);

    constructor(
        private factory: AIProviderFactory,
        private router: ProviderRouterService,
        private lengthStrategy: LengthStrategyService,
        private reviewer: ReviewerService,
        private config: ConfigService,
    ) {}

    async generateQuote(dto: GenerateQuoteDto) {
        this.logger.debug(`==> QuoteWriterService_generateQuote`);
        // 1. Auto-detect quote type nếu không có
        const quoteType = dto.quoteType ?? suggestQuoteType(dto.originalPost, dto.yourAngle);
        this.logger.log(`Quote type: ${quoteType}`);

        // 2. Tier & length
        const tier = dto.accountTier ?? this.config.get<AccountTier>('X_ACCOUNT_TIER', AccountTier.PREMIUM);

        const lengthDecision = this.lengthStrategy.decide({
            platform: Platform.X,
            tier,
            style: ContentStyle.GENERAL, // quote không map style thông thường
            tone: dto.tone ?? ContentTone.CASUAL,
            requestedLength: dto.postLength,
        });

        const budget = calculateTokenBudget(lengthDecision.range, dto.language);

        // 3. Router — quote EN ưu tiên Grok (X-native voice), non-EN -> GPT
        const providerDecision = this.router.route({
            language: dto.language,
            contentType: 'comment', // quote giống comment hơn post về routing
            tone: dto.tone,
        });
        console.log({lengthDecision,tier, budget,providerDecision});
        // 4. Build prompt
        const { system, user } = buildQuotePrompt({
            originalPost: dto.originalPost,
            originalAuthor: dto.originalAuthor,
            quoteType,
            language: dto.language,
            tone: dto.tone,
            persona: dto.persona,
            yourAngle: dto.yourAngle,
            lengthRange: lengthDecision.range,
        });

        console.log({providerDecision, system, user})

        // 5. Generate
        const provider = this.factory.get(providerDecision.writer);
        const res = await provider.complete(
            [
                { role: 'system', content: system },
                { role: 'user', content: user },
            ],
            {
                temperature: 0.85, // cao để quote có personality
                maxTokens: budget.maxTokens,
            },
        );

        let quote = this.cleanOutput(res.content);
        let reviewNotes: string | undefined;
        let totalTokens = res.tokensUsed;
        let modelUsed = res.model;

        // 6. Optional review
        if (dto.enableReview) {
            const ctx = {
                topic: dto.originalPost,
                platform: Platform.X,
                style: ContentStyle.GENERAL,
                tone: dto.tone ?? ContentTone.CASUAL,
                language: dto.language,
            } as any;

            try {
                const reviewed = await this.reviewer.review(
                    quote,
                    ctx,
                    providerDecision.reviewer,
                    dto.originalPost,
                    Math.ceil(budget.maxTokens * 1.3),
                );
                if (reviewed.languageValid) {
                    quote = this.cleanOutput(reviewed.improved);
                    reviewNotes = reviewed.notes;
                }
                totalTokens += reviewed.tokensUsed;
                modelUsed = `${res.model} + ${reviewed.model}`;
            } catch (err) {
                this.logger.warn('Quote review failed, using draft', err);
            }
        }

        // // 7. Hard cap
        // if (quote.length > lengthDecision.hardLimit) {
        //     quote = quote.substring(0, lengthDecision.hardLimit);
        // }

        return {
            quote,
            quoteType,
            charCount: quote.length,
            language: dto.language,
            reviewNotes,
            tokensUsed: totalTokens,
            model: modelUsed,
        };
    }

    /**
     * Generate nhiều variants để bạn chọn bài hay nhất.
     */
    async generateVariants(dto: GenerateQuoteDto, count = 3) {
        const tasks = Array.from({ length: count }, () => this.generateQuote(dto));
        return Promise.all(tasks);
    }

    /**
     * Generate 1 quote cho MỖI quote type — để bạn thấy tất cả góc nhìn.
     */
    async generateAllAngles(dto: GenerateQuoteDto) {
        const types = Object.values(QuoteType) as QuoteType[];
        const tasks = types.map((t) =>
            this.generateQuote({ ...dto, quoteType: t }).catch((e) => ({
                quoteType: t,
                error: e.message,
            })),
        );
        return Promise.all(tasks);
    }

    private cleanOutput(text: string): string {
        return text
            .trim()
            .replace(/^["""'「『]+|["""'」』]+$/g, '') // bỏ quote wrapping
            .replace(/^(Here is|Here's|Quote:|以下|다음은)[^\n]*\n+/i, '') // bỏ AI preamble
            .trim();
    }
}
