// utils/token-calculator.ts

import {Platform} from "../../modules/content-writer/enum/platform.enum";
import {Language} from "../interfaces/language.prompt.interface";
import {LengthRange} from "../../modules/content-writer/config/platform-limits";

/**
 * Tokens trung bình per character theo ngôn ngữ.
 * Dựa trên tokenizer GPT/Claude thực tế.
 */
const TOKENS_PER_CHAR: Record<Language, number> = {
    en: 0.25,  // 1 token ≈ 4 chars
    vi: 0.5,   // 1 token ≈ 2 chars (dấu tiếng Việt tốn token)
    ja: 1.0,   // 1 token ≈ 1 char (hiragana/kanji)
    ko: 1.0,   // 1 token ≈ 1 char (hangul)
    cn: 1.0,   // 1 token ≈ 1 char (chinese)
};

/**
 * Target character length theo platform + buffer để AI có không gian "thở".
 */
const PLATFORM_TARGET_CHARS: Record<Platform, { min: number; max: number; buffer: number }> = {
    [Platform.X]:        { min: 180, max: 280,  buffer: 1.3 },
    [Platform.FACEBOOK]: { min: 400, max: 1200, buffer: 1.5 },
};

export interface LengthBudget {
    minChars: number;
    maxChars: number;
    maxTokens: number;
}
export interface TokenBudget {
    minChars: number;
    maxChars: number;
    sweetChars: number;
    maxTokens: number;
}

export function calculateLengthBudget(
    platform: Platform,
    language: Language,
): LengthBudget {
    const target = PLATFORM_TARGET_CHARS[platform];
    const tokensPerChar = TOKENS_PER_CHAR[language];

    const raw = Math.ceil(target.max * tokensPerChar * target.buffer);

    // Safe minimums để đảm bảo không bị cắt
    const SAFE_MIN: Record<Platform, number> = {
        [Platform.X]: 300,        // X post không bao giờ < 300 tokens
        [Platform.FACEBOOK]: 800, // FB không bao giờ < 800 tokens
    };
    return {
        minChars: target.min,
        maxChars: target.max,
        maxTokens: Math.max(raw, SAFE_MIN[platform]),
    };
}


export function calculateTokenBudget(
    range: LengthRange,
    language: Language,
): TokenBudget {
    const tokensPerChar = TOKENS_PER_CHAR[language];

    // Buffer 1.4x cho emoji, punctuation, line breaks
    const maxTokens = Math.ceil(range.max * tokensPerChar * 1.4);

    // Safe minimum theo range
    const SAFE_MIN = Math.ceil(range.min * tokensPerChar * 1.5);

    return {
        minChars: range.min,
        maxChars: range.max,
        sweetChars: range.sweet,
        maxTokens: Math.max(maxTokens, SAFE_MIN, 200), // floor 200 tokens
    };
}
