Le point de départ
Quand on utilise ChatGPT ou Claude pour coder, on pose une question générale et on reçoit une réponse générale. Le modèle ne connaît pas votre projet, vos conventions, vos patterns internes, vos dépendances spécifiques. Chaque conversation recommence à zéro.
Les grands LLMs en cloud ont un avantage évident : ils savent tout sur tout. Mais sur votre code interne, sur vos APIs privées, sur vos choix d'architecture — ils ne savent rien. Et ils ne pourront jamais le savoir sans que vous le leur expliquiez à chaque fois.
Un LLM local change la donne. Non pas parce qu'il est plus intelligent — il ne l'est probablement pas — mais parce qu'on peut lui donner exactement le contexte dont il a besoin, de manière persistante, structurée, et sous notre contrôle complet.
L'approche habituelle vs l'approche RAG locale
Ce qu'on a construit : PyContextBuilder
PyContextBuilder est un outil standalone PySide6 qui analyse statiquement un projet Python (et ses fichiers front-end associés), extrait les symboles pertinents, et les injecte dans une instance LLMInternal locale.
L'idée centrale : au lieu de coller du code dans un chat, on préindexe toute la structure du projet. Le LLM peut alors récupérer précisément le bon contexte au moment de chaque question.
Ces chiffres viennent d'une analyse réelle de LLMInternal lui-même — 49 fichiers Python + 57 fichiers statiques (JS, HTML, CSS, YAML). Le système analyse et s'auto-indexe.
Le pipeline d'analyse : du code aux vecteurs
@router.post("/upload")) et les appels fetch JS (authFetch('/api/documents/upload')). 216 liens cross-langage détectés sur LLMInternal.embed_text optimisé : signature complète + docstring (≤500c) + début du corps (budget restant jusqu'à 1400c max). Tronquage propre à la ligne avec marqueur.artifacts.parquet (merge incrémental par symbol_id), embeddings_queue.jsonl (embeddable=True uniquement), manifest.json (stats + graphe d'imports).Ce qui est injecté — le graphe des artefacts
Sur une analyse de PyContextBuilder lui-même (27 fichiers Python + 1 YAML de config) :
La sélection embeddable=True est critique : on n'injecte que ce qui a une valeur sémantique réelle — fonctions et classes publiques avec docstring ou corps suffisant. Le reste (getters d'une ligne, méthodes privées) polluerait l'index et dégraderait la précision des réponses.
La structure d'un artefact
# Exemple réel extrait de LLMInternal
{
"symbol_id": "226e617b-498b-54bd-94c3-...",
"qualified_name": "src.rag.rag_engine.RAGEngine.chat_agent",
"symbol_type": "method",
"file_path": "/opt/llminternal/src/rag/rag_engine.py",
"start_line": 142,
"end_line": 264,
"priority": 6, // public method, non-test
"embeddable": true,
"confidence": "certain",
"embed_text": "async def chat_agent(self, query, ctx):\n \"\"\"Runs the agent pipeline...\"\"\"\n intent = await self._intent_analyzer...",
"used_by": ["static.js.chat.sendMessage"] // cross-ref JS→Python
}
Le graphe d'imports — la topologie du projet
Ce graphe n'est pas juste décoratif : il guide la priorité d'injection. Les modules centraux (rag_engine, agent_pipeline) qui sont importés par beaucoup d'autres reçoivent une priorité d'indexation plus haute. Le LLM trouvera d'abord le contexte le plus structurant.
Ce que ça change concrètement
Une fois LLMInternal indexé avec le contexte complet de votre projet, les questions deviennent beaucoup plus précises :
# Question classique (LLM cloud)
"Comment implémenter un système de RAG en Python ?"
→ Réponse générique, LangChain, ChromaDB, patterns publics
# Question avec contexte injecté (LLM local + LLMInternal)
"Dans notre RAGEngine, comment fonctionne le mode agent ?"
→ Réponse ancrée dans chat_agent(), agent_pipeline.py,
les vrais agents (intent_analyzer, reranker, retriever)
et les appels fetch() depuis chat.js qui le déclenchent
La différence n'est pas dans la capacité du modèle. Elle est dans la précision du contexte fourni. Un Qwen3-32B local avec le bon contexte surpasse souvent un GPT-4 qui travaille dans le vide.
Stack technique
Tout est open-source et auto-hébergeable :
Le hardware : un serveur AMD avec GPU ROCm (GFX1151) héberge les modèles.