Files
siop2/apps/ai
pr-daaif 28eecc1fb9 feat(r5.3): écrans IA — assistant web, corpus administrable, suggestions OT/mobile
- Contrat (76 opérations) : Document expose inCorpus/indexedAt/chunkCount,
  PATCH /documents/{id}/corpus (ASSETS.edit), POST /assistant/reindex
  (bilan chiffré) ; ci-contract vérifie désormais aussi le client mobile.
- Web : page /assistant (chat sourcé — extraits exacts cités, Ouvrir vers
  PDF authentifié ou fiche OT, avertissement permanent ; refus honnête
  chiffré avec action utile) ; Bibliothèque = corpus (bandeau 09-08,
  statut d'indexation par document, interrupteur d'exclusion PDF,
  Réindexer tout) ; fiche OT : « Décrire pour suggérer » (Appliquer =
  geste humain, liseré « suggéré » retiré au choix manuel).
- Mobile : chips de suggestion dans la clôture (un appui = un champ
  pré-rempli, « réseau requis » hors-ligne — la file R4 n'en dépend pas).
- apps/ai : seuils AI_SEUIL_* configurables par env (CI + calibrage).
- CI e2e : service siop2-ai (embeddeur déterministe, seuils calibrés sur
  mesures : match 0,66 vs bruit 0,11) + parcours R5 Playwright (PDF généré
  xref valide → réindexation → réponse sourcée → refus → suggestion).
- Vérifié : 16/16 Playwright, 78 tests API, 23 pytest, 17 jest-expo ;
  chaîne réelle au vrai modèle ONNX (web 7/7, mobile Expo web 6/6).

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-17 17:26:22 +01:00
..

@siop/ai — service IA (R5)

FastAPI + uv (ADR-001), jamais exposé : seule l'API NestJS le contacte avec X-Service-Token (ADR-004 §4). Maquettes et décisions D1-D5 validées le 17/07/2026.

Lancer (dev)

cd apps/ai
uv sync --extra embeddings      # le vrai modèle ONNX (CPU, ~120 Mo au premier run)
uv run uvicorn siop_ai.app:app --port 8000
# CI / tests : uv sync && uv run pytest  (embeddeur déterministe, aucun téléchargement)

Variables (défauts dev dans config.py, gabarit dans .env.example) : DATABASE_URL, MINIO_*, AI_SERVICE_TOKEN, AI_EMBEDDINGS=locale|deterministe, et la génération opt-in (ADR-004 §3) : AI_GENERATION=off|api, AI_API_KEY (exigée en mode api — le boot refuse sinon, jamais loguée ni exposée), AI_MODEL (défaut claude-opus-4-8). Mode api : uv sync --extra generation (SDK officiel anthropic) ; tout échec du LLM retombe sur le mode extractif.

Ce que porte R5.1 (socle)

  • Ingestion anonymisée (D4) : PDF de la bibliothèque (MinIO) page par page + bilans codés clôturés → anonymisation (e-mails, téléphones, noms connus de la base) → découpage → embeddings locaux → RagChunk (pgvector, schéma Prisma).
  • Recherche sémantique /internal/search : extraits sourcés (document + page ou bilan daté) avec score — la brique de « sourcé ou silencieux » (D2).
  • /internal/reindex idempotent ; l'exclusion de corpus (Document.inCorpus, D3) s'applique à l'ingestion ET à la lecture.

La suite : R5.2 assistant (mode extractif puis génération opt-in) + suggestion de bilan ; R5.3 écrans ; durcissement : Dockerfile + compose Dokploy (siop2-ai).