diff --git a/MyIA.AI.Notebooks/GenAI/Texte/19_OWUI_Orchestration.ipynb b/MyIA.AI.Notebooks/GenAI/Texte/19_OWUI_Orchestration.ipynb index 4623d0c0e2..bab1673828 100644 --- a/MyIA.AI.Notebooks/GenAI/Texte/19_OWUI_Orchestration.ipynb +++ b/MyIA.AI.Notebooks/GenAI/Texte/19_OWUI_Orchestration.ipynb @@ -780,26 +780,32 @@ "tags": [] }, "source": [ - "## 6. OWUI API - `SOTA-OK` (key provisionnee)\n", + "## 6. OWUI API — SOTA-OK ou RECOVERABLE-USER-HAND selon provisionnement\n", "\n", "Cette section instancie un **client OpenAI-compatible pointe vers l'instance OWUI** de\n", - "cours (`OWUI_URL`) authentifie par `OWUI_API_KEY`. OWUI expose en effet une API compatible\n", - "OpenAI (`/api/chat/completions`), ce qui permet de reutiliser le client `openai` standard.\n", - "\n", - "> **Statut SOTA - Prong A.** `OWUI_API_KEY` est **provisionnée** pour cette instance de\n", - "> cours (cf. cell[2] : `OWUI_API_KEY = configure (masquee)`, `OWUI_READY = True`). Les\n", - "> cells 17/18 s'exécutent **réellement** et les sorties committées (`Ping OWUI : 'OK'`,\n", - "> réponse chat authentifiée) sont les **vraies sorties OWUI** → verdict **SOTA-OK**. Le\n", - "> code conserve une branche **graceful skip** défensive (`os.getenv(\"OWUI_API_KEY\")`\n", - "> **sans** valeur par défaut) au cas où la clé serait absente sur une autre machine : si\n", - "> la clé est absente, on affiche un message `RECOVERABLE-USER-HAND` explicite et on\n", - "> poursuit (règle C.1, pas d'erreur volontaire).\n", - "\n", - "La clé est donc **déjà provisionnée** dans le `.env` de la série `GenAI/Texte` (cf. cell[2]),\n", - "et les sorties committées ci-dessous sont **réelles**. C'est le verdict `SOTA-OK` au sens de\n", - "la règle SOTA du repo : l'outil est proprement invoqué, la sortie committée est sa vraie\n", - "sortie. Le `graceful skip` reste en place comme filet de sécurité sur une machine non\n", - "configurée." + "cours (`OWUI_URL`) authentifié par `OWUI_API_KEY`. OWUI expose en effet une API compatible\n", + "OpenAI (`/api/chat/completions`), ce qui permet de réutiliser le client `openai` standard.\n", + "\n", + "> **Statut SOTA — verdict conditionnel.** Le verdict dépend de l'état de `OWUI_API_KEY`\n", + "> mesuré en cell[2] :\n", + ">\n", + "> - **`OWUI_READY = True`** (clé provisionnée dans le `.env` de la série `GenAI/Texte`)\n", + "> → les cells 17/18 s'exécutent **réellement** et les sorties committées\n", + "> (`Ping OWUI : 'OK'`, réponse chat authentifiée) sont les **vraies sorties OWUI**\n", + "> → verdict **SOTA-OK** (Prong A).\n", + "> - **`OWUI_READY = False`** (clé absente du `.env`) → les cells 17/18 affichent un\n", + "> message `RECOVERABLE-USER-HAND` explicite ; le carnet reste invocable et le\n", + "> squelette est complet → verdict **RECOVERABLE-USER-HAND** (action user one-time :\n", + "> provisionner `OWUI_API_KEY` puis re-exécuter le carnet).\n", + ">\n", + "> Le code évite délibérément toute erreur volontaire (règle C.1) : pas de `raise`, pas de\n", + "> `assert False` ; à la place, un message clair et un skip gracieux\n", + "> (`os.getenv(\"OWUI_API_KEY\")` **sans** valeur par défaut). C'est ce filet qui maintient\n", + "> le carnet exécutable end-to-end même quand la clé n'est pas (ou plus) provisionnée.\n", + "\n", + "Le `graceful skip` est volontairement **défensif** : sur la machine de cours la clé est\n", + "provisionnée, mais le carnet reste lisible et exécutable sur toute machine sans `OWUI_API_KEY`,\n", + "sans crasher ni afficher de fausses sorties OWUI.\n" ] }, { @@ -1217,38 +1223,38 @@ "source": [ "## 8. Conclusion et suite\n", "\n", - "On a pose les **trois niveaux d'abstraction** pour orchestrer des LLM : le **produit** OWUI\n", + "On a pose les **trois niveaux d abstraction** pour orchestrer des LLM : le **produit** OWUI\n", "v0.9.0 (Automations / Task Management / Calendar, **sans code**), la **librairie** de\n", - "graphes d'états (LangChain / LangGraph), et le **framework multi-agents** par rôles\n", + "graphes d etats (LangChain / LangGraph), et le **framework multi-agents** par roles\n", "(CrewAI). Le concept-phare : OWUI atteint sans code ce que les frameworks atteignent avec du\n", - "code - avec un trade-off **facilité vs contrôle fin**.\n", + "code - avec un trade-off **facilite vs controle fin**.\n", "\n", - "**Points à retenir :**\n", + "**Points a retenir :**\n", "1. **Axe temporel** (Automations, RRULE iCalendar, pas de cron) **!= axe structurel**\n", - " (Task Management, liste de tâches vivante) **!= axe calendrier** (événements persistés).\n", - "2. L'overlay **« Scheduled Tasks calendar »** est une **projection runtime non persistée** -\n", - " a ne pas confondre avec un événement calendrier réel.\n", + " (Task Management, liste de taches vivante) **!= axe calendrier** (evenements persistes).\n", + "2. L overlay **« Scheduled Tasks calendar »** est une **projection runtime non persistee** -\n", + " a ne pas confondre avec un evenement calendrier reel.\n", "3. Sous le capot : un worker `scheduler_worker_loop`, une mock `Request` ASGI, et la table\n", - " `automation_run` qui rend chaque exécution **observable**.\n", + " `automation_run` qui rend chaque execution **observable**.\n", "4. La migration 0.8 -> 0.9 est un **breaking change async** (`async def`, `AsyncSession`,\n", " `aiosqlite`).\n", "\n", "**Limites honnetes (G.2 + SOTA Prong A).**\n", - "- Les concepts (RRULE, async, comparatif, architecture) sont **verifies par exécution\n", + "- Les concepts (RRULE, async, comparatif, architecture) sont **verifies par execution\n", " reelle** dans ce notebook (sections 2.1 et 5).\n", - "- Les **appels API OWUI réels** sont **exécutés** dans ce notebook (sections 6-7) :\n", - " `OWUI_API_KEY` est provisionnée (cf. cell[2], `OWUI_READY = True`), et les sorties\n", - " committées (`Ping OWUI : 'OK'`, réponse chat) sont les vraies sorties OWUI → statut\n", - " **`SOTA-OK`**. Le squelette reste complet et le `graceful skip` défensif est conservé.\n", - "- La ligne comparative *« CrewAI : pas de scheduler cron natif »* est marquee **à vérifier**\n", - " dans la source - à confirmer avant tout choix d'architecture définitif s'appuyant dessus.\n", - "\n", - "**Suite naturelle :**\n", - "- **Phase 2** - exécuter les exercices 1 et 2 sur l'instance OWUI de cours (la clé est\n", - " provisionnée) et explorer les comparaisons (chat_id retrouve, comparaison naïf vs\n", - " Task Management).\n", - "- **Phase 3** - croiser avec la serie `GenAI/Playwright-OWUI` qui couvre OWUI sous l'angle\n", - " **tests E2E** (Playwright) : un même use-case teste E2E vient valider l'automation.\n" + "- Les **appels API OWUI reels** sont executes dans ce notebook (sections 6-7) si et\n", + " seulement si la cle est provisionnee : `OWUI_READY` est evalue en cell[2]\n", + " (`OWUI_API_KEY = os.getenv(\"OWUI_API_KEY\")` sans default ; `OWUI_READY = key is not None`).\n", + " - Si `OWUI_READY = True` → les sorties committées (`Ping OWUI : 'OK'`, reponse chat) sont\n", + " les vraies sorties OWUI → statut **`SOTA-OK`**.\n", + " - Si `OWUI_READY = False` → la cle n est pas provisionnee, les appels API sont **defensifs**\n", + " (skip silencieux, message d information), et le notebook n a pas pu verifier les appels\n", + " reels → statut **`RECOVERABLE-USER-HAND`** (verdict signale en vscode au user pour\n", + " approvisionner `OWUI_API_KEY` dans `.secrets/master.env`).\n", + "- **Pas de redaction manuelle d une sortie de cellule** (regle 6 secrets-hygiene) : le carnet\n", + " est execute en Papermill, et les sorties refletees sont les vraies sorties. Si l etat\n", + " reel diverge, c est la **cause** qu on corrige, pas la sortie (cf. c.1432 et #18124).\n", + "" ] }, { @@ -1333,4 +1339,4 @@ }, "nbformat": 4, "nbformat_minor": 5 -} \ No newline at end of file +}