#!/usr/bin/env python3
"""exp14 — рендер промптов армов (ЗАМОРОЖЕНЫ; sha256 в §2 дока).

- baseline editor = backend/prompts/editor.md (v2-bilingual-reflow), brief-filled.
- discourse editor = baseline + дискурс-reflow ядро (§1.2: 5 техник Ван Цуй + Розенталь) + few-shot.
- translator (для re-draft глав/нарезки) = backend/prompts/translator.md (v1-reflow).
Few-shot — минимальные ортогональные (narrative N:1, dialogue 1:N, focal-shift). НЕ ручной CoT.
"""
from __future__ import annotations
import hashlib
from pathlib import Path

PROMPTS = Path("/home/ubuntu/projects/textmachine/backend/prompts")
BRIEF = dict(source_lang="zh", target_lang="ru", genre="вебновелла",
             audience="взрослые читатели вебновелл", title="蛊真人",
             honorifics="keep", transcription="palladius", venuti="0.6", footnotes="minimal")


def _fill(t: str) -> str:
    for k, v in BRIEF.items():
        t = t.replace("{{" + k + "}}", v)
    return t


def _split(md_text: str) -> tuple[str, str]:
    sysmd, usermd = md_text.split("---USER---", 1)
    return _fill(sysmd).strip(), _fill(usermd).strip()


# ── Дискурс-reflow ядро (§1.2; арм для ЗАМЕРА, не «оптимальный промпт») ──────────────
DISCOURSE_CORE = """
ДИСКУРС-ПЕРЕВЁРСТКА (обязательная операция передачи китайского паратаксиса в русскую гипотактическую прозу — это КОНВЕНЦИЯ русского языка, а не вольность):
1. Молча определи смысловые ходы фрагмента: единый фокал/наблюдатель; действие и его непосредственная реакция; одна тема рассуждения; границы — смена говорящего, времени, места или фокала.
2. Один повествовательный ход оформляй ОДНИМ русским абзацем, ДАЖЕ если китайский исходник разбит на однофразовые строки. Инструмент слияния — причастные и деепричастные обороты, подчинительные союзы и связки (построй иерархию, сегментируй по смыслу, промаркируй вид/время предикатов, варьируй лексику, добавляй связки). Не сливай ТОЛЬКО ради длины и не теряй смысловые атомы.
3. Каждую новую реплику начинай с нового абзаца через тире «—»; слова автора при той же реплике оставляй в её абзаце.
4. Разрешено объединять и делить русские предложения; число предложений и абзацев совпадать с исходником НЕ обязано. Запрещено терять смысловые атомы (участников, действия, числа, полярность, заголовки).
"""

FEWSHOT = """
Примеры требуемой ПЕРЕВЁРСТКИ (показана структура вывода, не стиль):

[narrative N:1] Исходник построчно — «Он вышел за дверь.» / «Небо было серым.» / «Он вздохнул.» / «Дорога уходила вдаль.» — становится ОДНИМ абзацем:
Он вышел за дверь. Небо было серым; вздохнув, он смотрел, как дорога уходит вдаль.

[dialogue 1:N] Исходник — «Дядя нахмурился и сказал: „Время летит. Садись.“ Племянник ответил: „Спасибо.“» — становится:
Дядя нахмурился.
— Время летит. Садись, — сказал он.
— Спасибо, — ответил племянник.

[focal-shift] При смене наблюдателя/места/времени — новый абзац, даже если в исходнике это продолжение той же строки.
"""

REFERENCE_NOTE = ("\n\nСПРАВОЧНЫЙ КОНТЕКСТ (соседние фрагменты — ТОЛЬКО для разрешения связей, "
                  "местоимений и опущенных подлежащих; НЕ переводи и НЕ пересказывай его в выходе):")


def editor_system(variant: str, few_shot: bool = True) -> str:
    sysmd, _ = _split((PROMPTS / "editor.md").read_text(encoding="utf-8"))
    if variant == "baseline":
        return sysmd
    if variant == "discourse":
        out = sysmd + "\n" + DISCOURSE_CORE
        if few_shot:
            out += FEWSHOT
        return out
    raise ValueError(variant)


def editor_user(source: str, draft: str, reference: str = "") -> str:
    _, usermd = _split((PROMPTS / "editor.md").read_text(encoding="utf-8"))
    u = usermd.replace("{{text}}", source).replace("{{draft}}", draft)
    if reference.strip():
        u += REFERENCE_NOTE + "\n" + reference.strip()
    return u


def translator_system() -> str:
    sysmd, _ = _split((PROMPTS / "translator.md").read_text(encoding="utf-8"))
    return sysmd

def translator_user(source: str) -> str:
    _, usermd = _split((PROMPTS / "translator.md").read_text(encoding="utf-8"))
    return usermd.replace("{{text}}", source)


def sha_frozen() -> dict:
    return {
        "editor_baseline_sys": hashlib.sha256(editor_system("baseline").encode()).hexdigest()[:16],
        "editor_discourse_sys": hashlib.sha256(editor_system("discourse").encode()).hexdigest()[:16],
        "discourse_core": hashlib.sha256(DISCOURSE_CORE.encode()).hexdigest()[:16],
        "fewshot": hashlib.sha256(FEWSHOT.encode()).hexdigest()[:16],
        "translator_sys": hashlib.sha256(translator_system().encode()).hexdigest()[:16],
    }


if __name__ == "__main__":
    import json
    print("=== frozen prompt sha256[:16] ===")
    print(json.dumps(sha_frozen(), indent=1, ensure_ascii=False))
    print("\n=== editor discourse system (first 600) ===")
    print(editor_system("discourse")[:600])
