Leçon 1 : la carte
Sections
Réglages de lecture
Aucune voix pour cette langue dans ce navigateur.
Plus de voix
Code et termes techniques en anglais
Désactivé : la voix de la page lit tout, sans pause entre deux voix.
Aucune voix pour cette langue dans ce navigateur.
Plus de voix
D’autres voix : Microsoft Edge propose des voix naturelles en ligne, et Windows (Paramètres › Heure et langue › Voix), macOS et Android en installent d’autres.
« L’IA de GA » n’est pas un composant unique. C’est un pipeline qui calcule un vecteur pour chaque forme d’accord jouable à la guitare et les range dans un fichier, et un hôte web qui répond aux messages de chat, tantôt avec ce fichier, tantôt avec du simple code C#, tantôt avec un modèle de langage. Cette leçon dessine les deux, puis ouvre l’hôte du chatbot et liste ce qu’il enregistre réellement, pour que les trois leçons suivantes zooment chacune sur une case de la carte.
Tous les liens vers GA pointent sur le commit a826864.
Exécuter le code
Section intitulée « Exécuter le code »Le programme du cours se trouve dans code/ga-ai. La première exécution clone dans code/ga-ai/.ga les parties de GA dont il a besoin, compile le tout et compare chaque leçon avec sa sortie attendue :
bash code/ga-ai/check.shSous Windows, lance-le depuis Git Bash ; les commandes sont les mêmes sur les trois systèmes. Le clone est sans blobs et clairsemé : fetch-ga.sh extrait 17 dossiers de projets, environ 11 Mo de sources, et ne touche jamais à un clone de GA que tu aurais déjà. Sur les runners de CI, une exécution complète, clone et compilation compris, prend une minute et demie sous Linux et trois sous Windows. Ensuite, chaque leçon s’exécute seule :
dotnet run --project code/ga-ai/GaAi -c Release -- l1Cinq couches
Section intitulée « Cinq couches »Le CLAUDE.md de GA décrit un modèle strict de cinq couches, de bas en haut, et une règle : le code d’IA va dans la couche 4, l’orchestration dans la couche 5, jamais plus bas.
| Couche | Projets | Ce que le côté IA en utilise |
|---|---|---|
| 1. Core | GA.Core, GA.Domain.Core |
notes, classes de hauteurs, manche, classes d’ensembles : le cours de théorie musicale les lit |
| 2. Domain | GA.Business.Core, GA.Business.Config |
les records que remplit l’analyse d’un voicing |
| 3. Analysis | génération et analyse des voicings (dans GA.Domain.Services à ce commit) |
VoicingGenerator, VoicingAnalyzer |
| 4. AI/ML | GA.Business.ML |
le schéma OPTIC-K, le générateur d’embeddings, la lecture et la recherche dans l’index, les agents et les intentions |
| 5. Orchestration | GA.Business.Core.Orchestration |
ProductionOrchestrator, le plugin des skills, les services de préchauffage |
Les projets de couche 3 que nomme CLAUDE.md, GA.Business.Core.Harmony et GA.Business.Core.Fretboard, ne sont pas ceux qui contiennent le code des voicings à ce commit : VoicingGenerator et VoicingAnalyzer sont dans Common/GA.Domain.Services. Les applications sont au-dessus des cinq couches : l’hôte du chatbot est Apps/GaChatbot.Api, et l’outil qui écrit l’index est un projet de démonstration, Demos/Music Theory/FretboardVoicingsCLI.
Deux pipelines
Section intitulée « Deux pipelines »Le diagramme montre les deux moitiés. Le premier groupe est le travail fait une fois, hors ligne : chaque forme d’accord jouable devient un vecteur, et les vecteurs vont dans un seul fichier. Le second groupe est le travail fait pour chaque message de chat.
flowchart TB subgraph Offline["Hors ligne : construire l'index"] Gen["VoicingGenerator<br/>chaque forme jouable"] --> Ana["VoicingAnalyzer<br/>nom d'accord, notes, caractéristiques"] Ana --> Doc["VoicingDocumentFactory<br/>un document par forme"] Doc --> Emb["MusicalEmbeddingGenerator<br/>240 nombres : OPTIC-K"] Emb --> Wri["OptickIndexWriter<br/>garde 124 nombres"] Wri --> File[("optick.index")] end subgraph Online["En ligne : répondre à un message"] User(["POST /api/chatbot/chat"]) --> App["OrchestratedChatApplicationService"] App --> Orch["ProductionOrchestrator"] Orch --> Hooks["hooks"] Hooks --> Guards["gardes déterministes<br/>voicing, algèbre"] Guards --> Intents["SemanticIntentRouter<br/>36 intentions"] Intents --> Agents["SemanticRouter<br/>6 agents"] Guards -. "agent voicing" .-> Search["OptickSearchStrategy"] Search --> File Intents -. "embeddings" .-> Ollama[["Ollama"]] Agents -. "embeddings, texte" .-> Ollama endLa leçon 2 ouvre la case de l’embedding, la leçon 3 l’index et sa recherche, la leçon 4 l’orchestrateur. Deux remarques dès maintenant :
- Le même schéma sert des deux côtés. Une requête de recherche est transformée en vecteur avec les mêmes partitions et les mêmes poids que les formes stockées, pour qu’un produit scalaire entre eux ait un sens. Si les deux divergent, l’en-tête du fichier d’index porte une empreinte de la disposition, et le lecteur refuse un fichier écrit avec une autre (leçon 3).
- Le serveur de modèles est facultatif pour certains chemins et indispensable pour d’autres. GA parle à Ollama, un serveur local de modèles à poids ouverts, via Microsoft.Extensions.AI :
IEmbeddingGeneratorpour les embeddings,IChatClientpour le texte. La leçon 4 montre quelles questions survivent sans lui.
Les dépôts voisins
Section intitulée « Les dépôts voisins »Le CLAUDE.md de GA nomme trois dépôts qui échangent des fichiers avec lui :
- ix, des algorithmes d’apprentissage automatique en Rust, « produit
state/voicings/optick.indexconsommé par la couche RAG de GA », et entraîne dessus des autoencodeurs parcimonieux. Dans le code de GA, pourtant, le fichier est écrit par leOptickIndexWriteren C# deFretboardVoicingsCLI: le skilloptic-k-rebuildde GA lui-même construit l’index avec cette CLI, puis lance dessus les diagnostics d’ix. Qu’ix puisse aussi écrire le fichier est à vérifier. Le cours sur IX lit le code d’ix à un autre commit. - Demerzel, la gouvernance : ses pipelines exécutent les revues que décrivent les contrats de GA, et il génère les modules Streeling de ce site.
- TARS, en F#, est décrit comme un « validateur de théorie inter-modèles ». Rien dans ce cours ne l’appelle.
Ce qu’enregistre l’hôte du chatbot
Section intitulée « Ce qu’enregistre l’hôte du chatbot »L’hôte canonique du chatbot est GaChatbot.Api : le document sur les surfaces de chat de GA le dit depuis le 2026-05-13, et dit qu’il sert la démo publique sur demos.guitaralchemist.com/chatbot/. L’hôte a trois modes. AddMinimalChatbotApi lit Chatbot:Mode, direct par défaut : direct envoie chaque message au modèle, routed utilise un routeur léger, et full (ou orchestrated) enregistre toute la pile d’orchestration. Le cours utilise full.
Plutôt que de lire les enregistrements, le programme démarre l’hôte et interroge son conteneur. WebApplicationFactory<TEntryPoint> est la classe qu’utilisent les tests d’intégration d’ASP.NET Core : elle exécute le Program d’une application dans le processus de test, avec un serveur en mémoire, et permet à l’appelant de remplacer paramètres et services. Le ChatHost.cs du cours en est la version pour un programme console :
builder.UseSetting("Chatbot:Mode", "full");builder.UseSetting("Chatbot:PathBase", "");builder.UseSetting("Ollama:BaseUrl", DeadOllama);builder.UseSetting("Ollama:Endpoint", DeadOllama);builder.UseSetting("VoicingSearch:OpticIndexPath", Lesson3.IndexPath);builder.UseSetting("IX:External:Enabled", "false");DeadOllama vaut http://127.0.0.1:9, un port sur lequel rien n’écoute, si bien que chaque appel au modèle échoue aussitôt, comme sur un runner de CI. L’index est un petit index que construit la leçon 3. La mémoire du chat, que GA range par défaut dans ~/.ga, est redirigée vers des fichiers à côté du programme, pour qu’une exécution ne lise ni ne modifie jamais celle de l’auteur. Puis Lesson1.cs résout quelques services :
== Orchestrator and application serviceIHarmonicChatOrchestrator ProductionOrchestratorIChatApplicationService (host) OrchestratedChatApplicationService36 intentions
Section intitulée « 36 intentions »Une intention (intent), ici, est un objet C# capable de répondre à un type de question, avec une liste de prompts d’exemple. Le routeur sémantique d’intentions compare un message à ces exemples (leçon 4). L’hôte en enregistre 36 :
== Intents the semantic router chooses from (36)id examples first exampleskill.chordinfo 32 What is a C major chord?skill.scaleinfo 24 What notes are in C major?skill.modes 37 What are the modes of the major scaleskill.interval 13 What is the interval between C and G?skill.fretspan 0 (none)skill.chordsubstitution 12 Tritone substitution for G7skill.beginnerchords 7 Show me some easy beginner chordsskill.progressionmood 15 How do I make this progression sound darker?skill.circleoffifths 10 Explain the circle of fifthsskill.practiceroutine 9 give me a 20 minute practice routineskill.genreessentials 8 essential chords for blues guitarskill.whatcanyoudo 14 what can you doskill.transpose 13 transpose this progression down a half stepskill.commontones 9 What notes do Cmaj7 and Am7 share?skill.diatonicchords 20 Give me the diatonic chords in C majorskill.relativekey 12 What is the relative minor of G majorskill.theorycomparison 7 What is the difference between major and minorskill.settheoryequivalence 5 Are pitch classes 0,1,4 and 0,1,6 equivalent under inversionskill.capo 10 What shape do I play in E with capo 4skill.voiceleading 10 voice leading from C to Fskill.alternatetunings 12 what is DADGAD tuningskill.intervalclassvector 10 what is the interval-class vector of Cmaj7skill.grothendieckdelta 10 how harmonically far is Am from D7skill.icvneighbors 10 which chords are most similar to Dm7skill.icvshortestpath 10 shortest harmonic path from Cmaj7 to G7skill.grothendieckparse 10 parse C ⊗ Gskill.chordvoicings 12 voicings for Cmaj7skill.improvisation 17 what scale can I use to solo over Cmaj7?skill.outsidenotes 10 why does F sound outside over Cmaj7skill.keyidentification 7 What key is C Am F G in?skill.progressioncompletion 5 What chord comes next after C G Am?skill.rememberthis 7 remember that I prefer drop-2 voicings for jazz compingalgebra 13 Are 0146 and 0137 z-related?tab.optimize 5 Make this progression smoother to playtab.analyze 4 Analyse this tabvoicing 11 Show me Drop 2 voicings of Cmaj732 d’entre elles enveloppent un skill, une classe qui implémente IOrchestratorSkill et que GaPlugin enregistre trois fois : comme elle-même, comme IOrchestratorSkill, et enveloppée dans un OrchestratorSkillIntent. L’une d’elles, skill.fretspan, n’a aucun exemple, et le routeur ignore les intentions sans exemples : elle ne peut jamais être choisie par similarité.
6 agents et 4 hooks
Section intitulée « 6 agents et 4 hooks »Un agent, dans le code de GA, est une classe qui répond avec un modèle de langage, en appelant éventuellement des outils. Les messages qu’aucune intention ne réclame vont à l’un des six :
== Agents behind the LLM path (6)tab TabAgenttheory TheoryAgenttechnique TechniqueAgentcomposer ComposerAgentcritic CriticAgentvoicing VoicingAgent
== Hooks, in the order they run (4)PromptSanitizationHookMemoryHookMemoryWriteHookObservabilityHookUn hook s’exécute à des points fixes de chaque requête : quand elle arrive, avant et après un skill, quand la réponse part. C’est la même idée que les hooks du cours de programmation agentique, vue de l’autre côté : là-bas, du code autour d’un agent que tu utilises ; ici, du code autour des agents que GA exécute.
La dernière ligne de la leçon relie les deux pipelines :
== The embedding every voicing getsOPTIC-K-v1.8, 240 dims in 11 partitions, 124 of them searchedCe que le chatbot doit devenir
Section intitulée « Ce que le chatbot doit devenir »La feuille de route du chatbot de GA énonce son étoile polaire en une phrase : le chatbot est « the conversational front end to the Guitar Alchemist domain », la façade conversationnelle du domaine de Guitar Alchemist, où « each user query is routed by intent, answered by the domain, formatted by the skill, and shaped by the LLM only at the prose layer » : chaque question est routée par intention, répondue par le domaine, mise en forme par le skill, et façonnée par le modèle seulement au niveau de la prose. Le modèle écrit les phrases ; les faits viennent de la théorie musicale typée de GA.
Le ticket #623, ouvert le 2026-08-01 et marqué P0, en fait un objectif visible par l’utilisateur : un guitariste donne une progression d’accords et un accordage, et obtient la tonalité et les fonctions des accords, des choix de gammes et d’arpèges, des voicings jouables avec peu de déplacement de la main entre eux, et une explication des compromis. Le ticket #589 nomme le risque auquel il répond : « free-form LLM text asserting music-theory claims nothing validates », du texte libre de modèle qui affirme des faits de théorie musicale que rien ne valide, et propose que le modèle se contente de remplir une structure JSON que le moteur de théorie vérifie.
Où en sont les choses, pour autant que ce cours puisse le dire le 2026-09-14 :
| État | Quoi | Preuve |
|---|---|---|
| Fonctionne, vérifié ici | vecteurs OPTIC-K, écriture et lecture de l’index, recherche par chiffrage d’accord, chemins algèbre et voicing du chatbot, skills appelés directement | leçons 2 à 4, exécutées en CI sans modèle |
| Fonctionne avec un modèle, non vérifié ici | routage par embeddings, les six agents, réponses en prose | nécessite Ollama ; non exécuté par ce cours (à vérifier) |
| Problèmes connus, ouverts | la partition CONTEXT ne porte rien (#616) ; mauvais conseils sur les accords d’emprunt (#567) ; « E-flat major » lu comme E majeur (#554) ; tonalités des cadences (#614) | tickets de GA, ouverts le 2026-09-14 |
| Prévu | le coach de la progression aux voicings (#623) ; sortie structurée validée (#589) | proposés, ouverts |
| Recherche | modèles du monde latents et planification sur OPTIC-K (#605, #610, #611, #606, #607) | explorations, ouvertes |
Les leçons complètent la ligne des problèmes connus : le cours a trouvé plus d’une douzaine de différences entre le code de GA et ses documents, listées dans le journal.
Exercices
Section intitulée « Exercices »- Sans rien exécuter, quel chemin répond à « Are 0146 and 0137 z-related? » : une intention, un agent, ou quelque chose avant les deux ? Regarde la liste des intentions ci-dessus et le diagramme.
- L’hôte est démarré avec
Chatbot:Modelaissé à sa valeur par défaut. QuelIChatApplicationServicerésout-il, et qu’arrive-t-il à chaque message ? - Pourquoi le programme du cours redirige-t-il
MemoryStoreetChatTranscriptStoreau lieu de laisser GA utiliser ses valeurs par défaut ?
Solutions
- Quelque chose avant les deux :
ProductionOrchestratorexécute un test d’algèbre déterministe avant tout routage par intention (lignes 359-373). Le prompt contient « z-related », l’un des mots-clés du classifieur. L’intentionalgebraexiste aussi, avec ce prompt même comme premier exemple, mais le chemin rapide répond avant que le routeur soit consulté. La leçon 4 montre la réponse :routingMethod ix-algebra. DirectChatApplicationService: le mode par défaut estdirect(ligne 22), et dans ce mode chaque message part directement au modèle de chat avec un prompt système. Si le modèle est injoignable, chaque message échoue.- Parce que les valeurs par défaut sont des fichiers dans le répertoire personnel de l’utilisateur,
~/.ga: un test qui écrit un tour de chat modifierait la vraie mémoire de l’auteur, et un test qui la lit en dépendrait. Faire pointer les deux stockages vers un dossier neuf rend l’exécution reproductible et inoffensive.ConfigureTestServicesenregistre les remplacements après les enregistrements de l’application elle-même, donc ce sont eux qui l’emportent.
À retenir
Section intitulée « À retenir »- L’IA de GA, ce sont deux pipelines qui partagent un schéma : hors ligne, les formes d’accords deviennent des vecteurs OPTIC-K de 240 nombres rangés dans un index ; en ligne, un message de chat passe par des hooks, des gardes déterministes, 36 intentions et 6 agents.
- Le code d’IA vit dans
GA.Business.ML(couche 4), l’orchestration dansGA.Business.Core.Orchestration(couche 5) ; l’hôte du chatbot estGaChatbot.Api, et l’écrivain de l’index est une CLI deDemos. WebApplicationFactorypermet à un simple programme console de démarrer un vrai hôte ASP.NET Core, de remplacer ses paramètres et services, et de lire son conteneur : la carte la plus fiable de ce qui est enregistré.- L’étoile polaire est un chatbot où le domaine répond et le modèle ne fait que formuler ; le coach prévu et la sortie structurée sont des pas dans cette direction, et plusieurs problèmes connus barrent la route.
- GuitarAlchemist/ga au commit
a826864:CLAUDE.md,docs/architecture/chat-surfaces.md,docs/plans/2026-05-07-chatbot-roadmap.md,Apps/GaChatbot.Api/Extensions/ServiceCollectionExtensions.cs,Common/GA.Business.Core.Orchestration/Plugins/GaPlugin.cs,Common/GA.Business.Core.Orchestration/Services/ProductionOrchestrator.cs. - Tickets de GA #554, #567, #589, #605, #606, #607, #610, #611, #614, #616, #623, lus le 2026-09-14.
- Microsoft Learn : Tests d’intégration dans ASP.NET Core, Bibliothèques Microsoft.Extensions.AI.
- Ollama.