Files
html/api/ambre-early-doc-gen.php
2026-04-22 17:05:02 +02:00

223 lines
12 KiB
PHP

<?php
// V179 wevia-brand · user-visible strings use WEVIA Vision only
/**
* ambre-early-doc-gen.php · v4 · 5 capabilities réelles
* 1. File gen pdf/docx/pptx via pandoc
* 2. xlsx via PhpSpreadsheet (si dispo, sinon fallback docx)
* 3. Mermaid validated
* 4. Image SVG via LLM structured prompt
* 5. Code with file URL (py/js/html/php depending on topic)
*/
static $__ad_already = false;
if ($__ad_already) return;
$__ad_already = true;
$__ad_raw = @file_get_contents("php://input");
if (!$__ad_raw) return;
$__ad_body = @json_decode($__ad_raw, true);
$__ad_msg = trim($__ad_body["message"] ?? "");
if (!$__ad_msg) return;
// ========== HANDLER 1: xlsx réel via PhpSpreadsheet ==========
if (preg_match("/g[eéèê]n[eéèê]re?\s+(?:un|une)?\s*(?:tableau\s+)?excel|xlsx/iu", $__ad_msg) &&
preg_match("/(?::|pour|sur)\s*(.+)$/iu", $__ad_msg, $__xm)) {
$__xlsx_topic = trim($__xm[1]);
// try PhpSpreadsheet
$__xl_url = "http://127.0.0.1/api/ambre-xlsx-gen.php?topic=" . urlencode($__xlsx_topic);
$__xl_out = @file_get_contents($__xl_url, false, stream_context_create(["http"=>["timeout"=>60,"header"=>"Host: weval-consulting.com\r\n"]]));
$__xl_d = @json_decode($__xl_out, true);
if ($__xl_d && !empty($__xl_d["ok"]) && !empty($__xl_d["url"])) {
header("Content-Type: application/json; charset=utf-8");
echo json_encode([
"response"=>"📊 **" . $__xlsx_topic . "** (Excel)\n\n🔗 Télécharger: " . $__xl_d["full_url"] . "\n📦 Taille: " . $__xl_d["size_human"] . " · ⚙️ " . $__xl_d["elapsed_ms"] . "ms · engine: PhpSpreadsheet\n\n" . ($__xl_d["preview"] ?? ""),
"executed"=>true,"provider"=>"ambre-doc-gen-v5","intent"=>"xlsx_real","topic"=>$__xlsx_topic,
], JSON_UNESCAPED_UNICODE|JSON_UNESCAPED_SLASHES);
exit;
}
// fallback to docx handler below
}
// ========== HANDLER 2: File generation PDF/DOCX/PPTX ==========
if (preg_match("/g[eéèê]n[eéèê]re?\s+(?:un|une|des|le|la)?\s*(pdf|pptx?|powerpoint|docx?|word|excel|xlsx?|pr[eéèê]sentation|presentation|document|tableau)[^:]*(?::|sur|pour)\s*(.+)$/iu", $__ad_msg, $__ad_m)) {
$__raw_type = mb_strtolower($__ad_m[1]);
$__topic = trim($__ad_m[2]);
$__type_map = [
"pdf"=>"pdf","pptx"=>"pptx","ppt"=>"pptx","powerpoint"=>"pptx",
"presentation"=>"pptx","présentation"=>"pptx",
"docx"=>"docx","doc"=>"docx","word"=>"docx","document"=>"docx",
"xlsx"=>"xlsx","excel"=>"xlsx","tableau"=>"xlsx",
];
$__type = $__type_map[$__raw_type] ?? "pdf";
$__pandoc_type = ($__type === "xlsx") ? "docx" : $__type;
$__url = "http://127.0.0.1/api/ambre-gen-pipeline.php?type=" . urlencode($__pandoc_type) . "&topic=" . urlencode($__topic);
$__out = @file_get_contents($__url, false, stream_context_create(["http"=>["timeout"=>75,"method"=>"GET","header"=>"Host: weval-consulting.com\r\n"]]));
if ($__out && strlen($__out) > 50) {
header("Content-Type: application/json; charset=utf-8");
echo json_encode([
"response"=>$__out,"executed"=>true,"provider"=>"ambre-doc-gen-v5",
"intent"=>"file_generation_real","type"=>$__type,"topic"=>$__topic,
], JSON_UNESCAPED_UNICODE|JSON_UNESCAPED_SLASHES);
exit;
}
}
// ========== HANDLER 3: Mermaid validated ==========
if (preg_match("/g[eéèê]n[eéèê]re?.*(sch[eéèê]ma|mermaid|diagramme|flowchart).*(?::|pour|sur)\s*(.+)$/iu", $__ad_msg, $__mm)) {
$__topic = trim($__mm[2]);
$__sys = "Tu es generateur de diagrammes Mermaid. Reponds UNIQUEMENT avec code mermaid valide, pas de markdown, pas de backticks. Commence par \"flowchart TD\" ou \"graph TD\". Syntaxe: A[Label] --> B[Label]. MAX 12 nodes.";
$__user = "Genere un flowchart mermaid VALIDE pour: $__topic";
$__llm = @file_get_contents("http://127.0.0.1:4000/v1/chat/completions", false, stream_context_create([
"http"=>["method"=>"POST","header"=>"Content-Type: application/json\r\n",
"content"=>json_encode(["model"=>"fast","messages"=>[
["role"=>"system","content"=>$__sys],["role"=>"user","content"=>$__user]
],"max_tokens"=>400,"temperature"=>0.1]),"timeout"=>20]
]));
$__mmd = @json_decode($__llm,true)["choices"][0]["message"]["content"] ?? "";
$__mmd = trim(preg_replace("/```(?:mermaid)?\n?|```/","",$__mmd));
if (!preg_match("/^(flowchart|graph|sequenceDiagram|classDiagram)/i", $__mmd)) $__mmd = "flowchart TD\n$__mmd";
header("Content-Type: application/json; charset=utf-8");
echo json_encode([
"response"=>"🧩 Schema Mermaid: $__topic\n\n".chr(96).chr(96).chr(96)."mermaid\n$__mmd\n".chr(96).chr(96).chr(96),
"executed"=>true,"provider"=>"ambre-doc-gen-v5","intent"=>"mermaid_valid","topic"=>$__topic,
], JSON_UNESCAPED_UNICODE);
exit;
}
// ========== HANDLER 4: Image via ambre-tool-image.php CASCADE (V177 image-gemini-cascade) ==========
// V177: Replace LLM SVG by real image cascade (Gemini 3 Pro Image Preview primary, Qwen fallback, Pollinations last resort)
if (preg_match("/g[e\xc3\xa9\xc3\xa8\xc3\xaa]n[e\xc3\xa9\xc3\xa8\xc3\xaa]re?\s+(?:une|un)?\s*image\s*(?:\b(?:decrivant|repr[e\xc3\xa9\xc3\xa8\xc3\xaa]sentant|pour|sur|de)\b\s*)?:?\s*(.+)$/iu", $__ad_msg, $__im)) {
$__topic = trim($__im[1]);
$__t0 = microtime(true);
// Call ambre-tool-image.php directly (internal, loopback)
$__img_ctx = stream_context_create([
"http" => [
"method" => "POST",
"header" => "Content-Type: application/json\r\nHost: weval-consulting.com\r\n",
"content" => json_encode(["prompt" => $__topic]),
"timeout" => 75,
"ignore_errors" => true,
],
]);
$__img_resp = @file_get_contents("http://127.0.0.1/api/ambre-tool-image.php", false, $__img_ctx);
$__img_d = @json_decode($__img_resp, true);
if ($__img_d && !empty($__img_d["success"]) && !empty($__img_d["url"])) {
$__url = $__img_d["url"];
$__provider = $__img_d["provider"] ?? "WEVIA Image Engine";
$__quality = $__img_d["quality"] ?? "standard";
$__size_kb = $__img_d["size_kb"] ?? 0;
$__elapsed = round((microtime(true) - $__t0) * 1000);
header("Content-Type: application/json; charset=utf-8");
echo json_encode([
"response" => "\xf0\x9f\x8e\xa8 **$__topic**\n\n\xf0\x9f\x94\x97 T\xc3\xa9l\xc3\xa9charger: $__url\n\xf0\x9f\x93\xa6 Taille: {$__size_kb}KB \xc2\xb7 \xe2\x9a\x99\xef\xb8\x8f {$__elapsed}ms \xc2\xb7 engine: $__provider",
"executed" => true,
"provider" => "ambre-doc-gen-v5",
"intent" => "image_real_cascade",
"topic" => $__topic,
"url" => $__url,
"quality" => $__quality,
"image_provider" => $__provider,
], JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES);
exit;
}
// If cascade failed, fall through (old LLM SVG code removed to force real images)
// Return an informative error to widget rather than fake SVG
header("Content-Type: application/json; charset=utf-8");
echo json_encode([
"response" => "\xe2\x9a\xa0\xef\xb8\x8f G\xc3\xa9n\xc3\xa9ration d\"image temporairement indisponible pour: $__topic. WEVIA Vision temporairement indisponible. Les providers internes ont \xc3\xa9chou\xc3\xa9. R\xc3\xa9essayez dans quelques instants.",
"executed" => true,
"provider" => "ambre-doc-gen-v5",
"intent" => "image_cascade_failed",
"topic" => $__topic,
], JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES);
exit;
}
// ========== HANDLER 5: Code generation with file ==========
if (preg_match("/(?:ecris?|[eéèê]cri(?:re)?|g[eéèê]n[eéèê]re?)\s+(?:le|du|un)?\s*code(?:\s+(?:pour|en|python|javascript|php|html|js|ts|react|jsx))?\s*(?::|pour)?\s*(.+)$/iu", $__ad_msg, $__cm)) {
$__topic = trim($__cm[1]);
// Detect language from topic
$__lang = "python"; $__ext = "py";
$__lc = mb_strtolower($__topic);
if (preg_match("/\b(react|jsx|tsx|nextjs|next\.js)\b/i", $__lc)) { $__lang="jsx"; $__ext="jsx"; }
elseif (preg_match("/\b(javascript|js|node|vanilla)\b/i", $__lc)) { $__lang="javascript"; $__ext="js"; }
elseif (preg_match("/\b(typescript|ts)\b/i", $__lc)) { $__lang="typescript"; $__ext="ts"; }
elseif (preg_match("/\b(php)\b/i", $__lc)) { $__lang="php"; $__ext="php"; }
elseif (preg_match("/\b(html|page web|site web)\b/i", $__lc)) { $__lang="html"; $__ext="html"; }
elseif (preg_match("/\b(bash|shell|sh)\b/i", $__lc)) { $__lang="bash"; $__ext="sh"; }
elseif (preg_match("/\b(sql|postgres|mysql)\b/i", $__lc)) { $__lang="sql"; $__ext="sql"; }
$__sys = "Tu es un generateur de code $__lang. Reponds UNIQUEMENT avec du code $__lang complet et fonctionnel. Pas de preambule, pas de markdown, pas de backticks, pas de commentaire meta. Juste le code pret a executer.";
$__user = "Ecris le code $__lang pour: $__topic";
$__llm = @file_get_contents("http://127.0.0.1:4000/v1/chat/completions", false, stream_context_create([
"http"=>["method"=>"POST","header"=>"Content-Type: application/json\r\n",
"content"=>json_encode(["model"=>"fast","messages"=>[
["role"=>"system","content"=>$__sys],["role"=>"user","content"=>$__user]
],"max_tokens"=>2000,"temperature"=>0.3]),"timeout"=>45]
]));
$__code = @json_decode($__llm,true)["choices"][0]["message"]["content"] ?? "";
$__code = trim(preg_replace("/```(?:" . $__lang . "|python|javascript|jsx|ts|php|html|bash|sql)?\n?|```/","", $__code));
if ($__code && strlen($__code) > 20) {
$__ts = date("Ymd-His");
$__rand = substr(md5(random_bytes(4)),0,6);
$__safe = preg_replace("/[^a-zA-Z0-9\-_]/","-",substr($__topic,0,40));
$__fname = "wevia-code-$__safe-$__ts-$__rand.$__ext";
@file_put_contents("/var/www/html/generated/$__fname", $__code);
header("Content-Type: application/json; charset=utf-8");
$__tb = chr(96).chr(96).chr(96);
echo json_encode([
"response"=>"💻 **$__topic** (code $__lang)\n\n🔗 Telecharger: https://weval-consulting.com/generated/$__fname\n📦 " . strlen($__code) . " chars · " . count(explode("\n",$__code)) . " lignes · lang: $__lang\n\n{$__tb}$__lang\n$__code\n{$__tb}",
"executed"=>true,"provider"=>"ambre-doc-gen-v5","intent"=>"code_real",
"topic"=>$__topic,"lang"=>$__lang,"url"=>"https://weval-consulting.com/generated/$__fname",
], JSON_UNESCAPED_UNICODE|JSON_UNESCAPED_SLASHES);
exit;
}
}
// ========== HANDLER 6: Translation via LLM direct ==========
if (preg_match("/(?:traduis?|traduire?|translate)\\s+(?:ce\\s+texte|le\\s+texte)?\\s*(?:en)?\\s*:?\\s*(anglais|francais|espagnol|allemand|italien|portugais|arabe|chinois|japonais|english|spanish|french|german|italian|portuguese|arabic|chinese|japanese)\\s*:?\\s*(.+)$/iu", $__ad_msg, $__tr)) {
$__tgt = mb_strtolower($__tr[1]);
$__txt = trim($__tr[2]);
$__lang_map = [
"anglais"=>"English","english"=>"English",
"francais"=>"French","french"=>"French",
"espagnol"=>"Spanish","spanish"=>"Spanish",
"allemand"=>"German","german"=>"German",
"italien"=>"Italian","italian"=>"Italian",
"portugais"=>"Portuguese","portuguese"=>"Portuguese",
"arabe"=>"Arabic","arabic"=>"Arabic",
"chinois"=>"Chinese","chinese"=>"Chinese",
"japonais"=>"Japanese","japanese"=>"Japanese",
];
$__target = $__lang_map[$__tgt] ?? "English";
$__sys = "You are a professional translator. Translate the text to $__target. Output ONLY the translation, no preamble, no explanation.";
$__llm = @file_get_contents("http://127.0.0.1:4000/v1/chat/completions", false, stream_context_create([
"http"=>["method"=>"POST","header"=>"Content-Type: application/json\r\n",
"content"=>json_encode(["model"=>"fast","messages"=>[
["role"=>"system","content"=>$__sys],["role"=>"user","content"=>$__txt]
],"max_tokens"=>1500,"temperature"=>0.2]),"timeout"=>20]
]));
$__trans = @json_decode($__llm,true)["choices"][0]["message"]["content"] ?? "";
if ($__trans) {
header("Content-Type: application/json; charset=utf-8");
echo json_encode([
"response"=>"🌐 Traduction vers $__target\n\n**Original:**\n$__txt\n\n**$__target:**\n" . trim($__trans),
"executed"=>true,"provider"=>"ambre-doc-gen-v5","intent"=>"translate_real",
"target"=>$__target,
], JSON_UNESCAPED_UNICODE);
exit;
}
}
// fall through to main flow