bots-garden/mini-mepublic Fork
⑂ v1.0.4
Commits
⬇ Clone ▾
git clone https://git.rickub.com/bots-garden/mini-me.git
git clone ssh://git@rickub.com/bots-garden/mini-me.git

Host key fingerprint (ed25519): SHA256:iycHnxEyq0Q7uyVpB7JlznP0G7JrTPXLYRcAU5CSLhc — verify it before your first connect.

Download ZIP
🛟 Updated. 8734926Unverified · on v1.0.4 · k33g · Oct 6, 2026
navigate-code-with-lsp.md · 110 lines · 8.0 KBmarkdown
Blame HistoryOpen raw

Naviguer et refactorer le code avec un serveur de langage (lsp)

Ce guide montre comment donner un serveur de langage à mm, pour que le modèle demande au compilateur où un symbole est défini, qui l'utilise, quel est son type, ce qui ne va pas dans un fichier, et le renomme partout — plutôt que de grepper et de deviner. Il suppose que mm tourne avec un fichier de configuration modifiable, et qu'au moins un serveur de langage est installé.

Étapes

  1. Installez le serveur de votre langage et vérifiez qu'il est sur le PATH :

    Langage Serveur Installation command / args
    Go gopls go install golang.org/x/tools/gopls@latest gopls
    TypeScript, JavaScript typescript-language-server npm i -g typescript typescript-language-server typescript-language-server, ["--stdio"]
    Python pyright pip install pyright ou npm i -g pyright pyright-langserver, ["--stdio"]
    Rust rust-analyzer rustup component add rust-analyzer rust-analyzer
    C, C++ clangd apt install clangd, brew install llvm clangd
    Java Eclipse JDT LS votre gestionnaire de paquets, ou la release jdtls jdtls
    Zig zls release de la chaîne zig, ou brew install zls zls

    which gopls (ou le nom du serveur) doit répondre. Un serveur configuré mais introuvable est ignoré avec un avertissement au démarrage.

  2. Déclarez les serveurs dans le fichier YAML. L'extension du fichier choisit le serveur :

    lsp:
      servers:
        - name: gopls
          command: gopls
          extensions: [".go"]
        - name: typescript
          command: typescript-language-server
          args: ["--stdio"]
          extensions: [".ts", ".tsx", ".js", ".jsx"]
        - name: python
          command: pyright-langserver
          args: ["--stdio"]
          extensions: [".py"]
        - name: rust
          command: rust-analyzer
          extensions: [".rs"]
    

    Le fichier livré agent.lsp.yaml est agent.dmr.yaml avec ce bloc (gopls actif, les autres prêts à décommenter) et un prompt système écrit pour l'outil — partez de lui.

  3. Dites au modèle quand utiliser l'outil. Un petit modèle ne va pas chercher un nouvel outil de lui-même ; le prompt système doit le dire. Le bloc ci-dessous est celui d'agent.lsp.yaml ; collez-le dans votre system: (il est en anglais, la langue dans laquelle le modèle lit le mieux ses consignes) :

    CODE NAVIGATION (lsp)
    You have an `lsp` tool: it asks the project's language server what the
    compiler knows. Its description says which file extensions it covers.
    Use it INSTEAD of grep or reading whole files for anything about a symbol:
    - "where is X defined / declared"        → action definition, symbol X
    - "who calls / uses X", "find usages"     → action references, symbol X
    - "what is the type / signature of X"    → action hover, symbol X
    - "what does this file contain"          → action symbols, path only
    - "are there errors", after every edit    → action diagnostics, path only
    - "rename X to Y everywhere"             → action rename, symbol X, new_name Y
      (rename NEEDS new_name — the new identifier; never rename with edit_file:
       {"action": "rename", "path": "main.go", "symbol": "Greet", "new_name": "Hello"})
    Point at a symbol with its NAME (the `symbol` field), exactly as written in
    the code; add `line` only to pick one occurrence among several. Do not
    guess columns. Answers are "path:line:column  <source line>": quote them,
    they are the evidence.
    Before changing a symbol used in several files, call references and say how
    many places are affected. After editing, call diagnostics on each edited
    file and fix what it reports before running tests.
    

    Le skill lsp-navigation livré dans skills/ dit la même chose plus longuement ; avec skillsDir pointant dessus, le modèle peut le charger avec read_skill quand la tâche le demande.

  4. Lancez mm depuis le répertoire du projet (les serveurs le reçoivent comme racine de travail) et lisez la bannière :

    [warning: lsp server ghost (no-such-lsp-server) not found on the PATH — skipped]
    mm v0.1.7 | config: agent.lsp.yaml | provider: dmr | model: … | ctx: unknown | tools: bash, read_skill, read_file, write_file, edit_file, lsp | skills: 4
    

    lsp dans la colonne tools: signifie qu'au moins un serveur a été trouvé. Les serveurs démarrent à leur premier usage, pas ici.

  5. Posez des questions. Quelques prompts pour tester les six actions, sur n'importe quel projet couvert par le serveur :

    Prompt Ce que vous devez voir
    Where is the function greet defined in main.go? Use lsp. 🔎 lsp: definition main.go greet puis une ligne main.go:6:6 func greet(…), citée dans la réponse.
    Who uses greet? List every call site. 🔎 lsp: references main.go greet, N reference(s): avec une ligne par site.
    What is the signature of greet? 🔎 lsp: hover main.go greet, la signature et le commentaire de doc du serveur.
    What does main.go contain? Give me its outline. 🔎 lsp: symbols main.go, une ligne par fonction, type, variable.
    Are there compile errors in main.go? 🔎 lsp: diagnostics main.go, no diagnostics: main.go is clean ou une ligne par erreur.
    Rename greet to hello everywhere, then check main.go for errors. 🔎 lsp: rename main.go greet → hello, renamed to hello: N edit(s) in M file(s), puis un appel diagnostics.
    Add a parameter to greet. Before you edit, tell me how many places call it. references d'abord, puis edit_file, puis diagnostics — la procédure que le skill enseigne.

    Les prompts en français marchent aussi (« Où est définie la fonction greet ? ») : c'est le prompt système qui décide de l'outil, pas la langue de la question. La ligne de récapitulatif après la réponse compte les appels : ⚙ 0 command(s) · 🔎 2 lsp call(s).

Depuis un éditeur (ACP) et dans le mode fenêtre

Rien à configurer : le même YAML s'applique. Les appels de navigation apparaissent comme des appels d'outil de sorte read, sans boîte de permission ; rename est de sorte edit et demande la permission comme edit_file (quand yolo: false). Les serveurs démarrent dans le répertoire où mm a été lancé — pour un éditeur, le projet qu'il a ouvert.

Variantes

  • Un projet en plusieurs langages. Listez un serveur par famille d'extensions ; chacun ne démarre que quand on l'interroge sur un fichier de sa sorte.
  • Un serveur avec des réglages. Passez-les en args (beaucoup de serveurs lisent un drapeau ou un fichier de configuration à la racine du projet) ; mm répond « pas de réglages » à un serveur qui demande sa configuration, qui tourne alors avec ses valeurs par défaut.
  • Positions exactes. Quand le modèle a une position exacte — via read_file avec numbered=true — il peut envoyer line et column (base 1, dans l'identifiant) au lieu de symbol. symbol est la voie fiable : les petits modèles comptent rarement les colonnes juste.
  • Aucun serveur sur cette machine. L'outil n'est pas déclaré et la bannière dit lsp: none of the configured servers is on the PATH — the lsp tool is not declared. La configuration peut rester ; l'agent fonctionne sans.
  • Première réponse lente. Le premier appel pour un langage démarre le serveur et le laisse indexer le projet ; diagnostics peut dire as last published ou no diagnostics received … within 3s — redemandez une fois.

Voir aussi

  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
# Naviguer et refactorer le code avec un serveur de langage (`lsp`)

Ce guide montre comment donner un serveur de langage à `mm`, pour que le modèle demande au compilateur où un symbole est défini, qui l'utilise, quel est son type, ce qui ne va pas dans un fichier, et le renomme partout — plutôt que de grepper et de deviner. Il suppose que `mm` tourne avec un fichier de configuration modifiable, et qu'au moins un serveur de langage est installé.

## Étapes

1. Installez le serveur de votre langage et vérifiez qu'il est sur le `PATH` :

   | Langage | Serveur | Installation | `command` / `args` |
   |---------|---------|--------------|--------------------|
   | Go | gopls | `go install golang.org/x/tools/gopls@latest` | `gopls` |
   | TypeScript, JavaScript | typescript-language-server | `npm i -g typescript typescript-language-server` | `typescript-language-server`, `["--stdio"]` |
   | Python | pyright | `pip install pyright` ou `npm i -g pyright` | `pyright-langserver`, `["--stdio"]` |
   | Rust | rust-analyzer | `rustup component add rust-analyzer` | `rust-analyzer` |
   | C, C++ | clangd | `apt install clangd`, `brew install llvm` | `clangd` |
   | Java | Eclipse JDT LS | votre gestionnaire de paquets, ou la release jdtls | `jdtls` |
   | Zig | zls | release de la chaîne `zig`, ou `brew install zls` | `zls` |

   `which gopls` (ou le nom du serveur) doit répondre. Un serveur configuré mais introuvable est ignoré avec un avertissement au démarrage.

2. Déclarez les serveurs dans le fichier YAML. L'extension du fichier choisit le serveur :

   ```yaml
   lsp:
     servers:
       - name: gopls
         command: gopls
         extensions: [".go"]
       - name: typescript
         command: typescript-language-server
         args: ["--stdio"]
         extensions: [".ts", ".tsx", ".js", ".jsx"]
       - name: python
         command: pyright-langserver
         args: ["--stdio"]
         extensions: [".py"]
       - name: rust
         command: rust-analyzer
         extensions: [".rs"]
   ```

   Le fichier livré `agent.lsp.yaml` est `agent.dmr.yaml` avec ce bloc (gopls actif, les autres prêts à décommenter) et un prompt système écrit pour l'outil — partez de lui.

3. Dites au modèle quand utiliser l'outil. Un petit modèle ne va pas chercher un nouvel outil de lui-même ; le prompt système doit le dire. Le bloc ci-dessous est celui d'`agent.lsp.yaml` ; collez-le dans votre `system:` (il est en anglais, la langue dans laquelle le modèle lit le mieux ses consignes) :

   ```text
   CODE NAVIGATION (lsp)
   You have an `lsp` tool: it asks the project's language server what the
   compiler knows. Its description says which file extensions it covers.
   Use it INSTEAD of grep or reading whole files for anything about a symbol:
   - "where is X defined / declared"        → action definition, symbol X
   - "who calls / uses X", "find usages"     → action references, symbol X
   - "what is the type / signature of X"    → action hover, symbol X
   - "what does this file contain"          → action symbols, path only
   - "are there errors", after every edit    → action diagnostics, path only
   - "rename X to Y everywhere"             → action rename, symbol X, new_name Y
     (rename NEEDS new_name — the new identifier; never rename with edit_file:
      {"action": "rename", "path": "main.go", "symbol": "Greet", "new_name": "Hello"})
   Point at a symbol with its NAME (the `symbol` field), exactly as written in
   the code; add `line` only to pick one occurrence among several. Do not
   guess columns. Answers are "path:line:column  <source line>": quote them,
   they are the evidence.
   Before changing a symbol used in several files, call references and say how
   many places are affected. After editing, call diagnostics on each edited
   file and fix what it reports before running tests.
   ```

   Le skill `lsp-navigation` livré dans `skills/` dit la même chose plus longuement ; avec `skillsDir` pointant dessus, le modèle peut le charger avec `read_skill` quand la tâche le demande.

4. Lancez `mm` depuis le répertoire du projet (les serveurs le reçoivent comme racine de travail) et lisez la bannière :

   ```text
   [warning: lsp server ghost (no-such-lsp-server) not found on the PATH — skipped]
   mm v0.1.7 | config: agent.lsp.yaml | provider: dmr | model: … | ctx: unknown | tools: bash, read_skill, read_file, write_file, edit_file, lsp | skills: 4
   ```

   `lsp` dans la colonne `tools:` signifie qu'au moins un serveur a été trouvé. Les serveurs démarrent à leur premier usage, pas ici.

5. Posez des questions. Quelques prompts pour tester les six actions, sur n'importe quel projet couvert par le serveur :

   | Prompt | Ce que vous devez voir |
   |--------|------------------------|
   | `Where is the function greet defined in main.go? Use lsp.` | `🔎 lsp: definition main.go greet` puis une ligne `main.go:6:6  func greet(…)`, citée dans la réponse. |
   | `Who uses greet? List every call site.` | `🔎 lsp: references main.go greet`, `N reference(s):` avec une ligne par site. |
   | `What is the signature of greet?` | `🔎 lsp: hover main.go greet`, la signature et le commentaire de doc du serveur. |
   | `What does main.go contain? Give me its outline.` | `🔎 lsp: symbols main.go`, une ligne par fonction, type, variable. |
   | `Are there compile errors in main.go?` | `🔎 lsp: diagnostics main.go`, `no diagnostics: main.go is clean` ou une ligne par erreur. |
   | `Rename greet to hello everywhere, then check main.go for errors.` | `🔎 lsp: rename main.go greet → hello`, `renamed to hello: N edit(s) in M file(s)`, puis un appel `diagnostics`. |
   | `Add a parameter to greet. Before you edit, tell me how many places call it.` | `references` d'abord, puis `edit_file`, puis `diagnostics` — la procédure que le skill enseigne. |

   Les prompts en français marchent aussi (« Où est définie la fonction greet ? ») : c'est le prompt système qui décide de l'outil, pas la langue de la question. La ligne de récapitulatif après la réponse compte les appels : `⚙ 0 command(s) · 🔎 2 lsp call(s)`.

## Depuis un éditeur (ACP) et dans le mode fenêtre

Rien à configurer : le même YAML s'applique. Les appels de navigation apparaissent comme des appels d'outil de sorte `read`, sans boîte de permission ; `rename` est de sorte `edit` et demande la permission comme `edit_file` (quand `yolo: false`). Les serveurs démarrent dans le répertoire où `mm` a été lancé — pour un éditeur, le projet qu'il a ouvert.

## Variantes

- **Un projet en plusieurs langages.** Listez un serveur par famille d'extensions ; chacun ne démarre que quand on l'interroge sur un fichier de sa sorte.
- **Un serveur avec des réglages.** Passez-les en `args` (beaucoup de serveurs lisent un drapeau ou un fichier de configuration à la racine du projet) ; `mm` répond « pas de réglages » à un serveur qui demande sa configuration, qui tourne alors avec ses valeurs par défaut.
- **Positions exactes.** Quand le modèle a une position exacte — via `read_file` avec `numbered=true` — il peut envoyer `line` et `column` (base 1, dans l'identifiant) au lieu de `symbol`. `symbol` est la voie fiable : les petits modèles comptent rarement les colonnes juste.
- **Aucun serveur sur cette machine.** L'outil n'est pas déclaré et la bannière dit `lsp: none of the configured servers is on the PATH — the lsp tool is not declared`. La configuration peut rester ; l'agent fonctionne sans.
- **Première réponse lente.** Le premier appel pour un langage démarre le serveur et le laisse indexer le projet ; `diagnostics` peut dire `as last published` ou `no diagnostics received … within 3s` — redemandez une fois.

## Voir aussi

- [Référence des outils intégrés](../reference/tools.md) — les champs, sorties et échecs de `lsp`
- [Référence de la configuration](../reference/configuration.md) — les clés `lsp.servers` et les erreurs de validation
- [Pourquoi un seul outil `lsp`, et pourquoi un champ `symbol`](../explanation/lsp-tool.md)
- [Ajouter un skill](add-a-skill.md) — le format du skill `lsp-navigation`