pi-ui-extend 1.0.39 → 1.0.40

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -140,7 +140,7 @@ Optional:
140
140
  - an audio recorder for dictation: SoX (`rec`/`sox`), `ffmpeg`, or `arecord` on Linux
141
141
  - `tmux` and `rsvg-convert` only if you want to regenerate README screenshots
142
142
  - Ollama with web search enabled for the bundled `web_search` and `web_fetch` tools
143
- - language servers for the LSP module
143
+ - language servers for the LSP module (see [LSP setup](external/pi-tools-suite/README.md#lsp-setup) for install commands and ready-to-paste configs for popular servers, including Svelte, Vue, Go, clangd, Lua, and bash)
144
144
 
145
145
  ### One-shot use
146
146
 
@@ -188,9 +188,28 @@ Install the language servers used by the bundled example config. The commands be
188
188
  # TypeScript / JavaScript
189
189
  npm install -g typescript typescript-language-server
190
190
 
191
+ # Svelte
192
+ npm install -g svelte-language-server
193
+
194
+ # Vue
195
+ npm install -g @vue/language-server
196
+
191
197
  # Python
192
198
  python3 -m pip install --user python-lsp-server
193
199
 
200
+ # Go
201
+ go install golang.org/x/tools/gopls@latest
202
+
203
+ # C / C++ (clangd)
204
+ brew install llvm
205
+ # or use your distro's clangd package: apt install clangd, dnf install clang-tools-extra, ...
206
+
207
+ # Lua
208
+ brew install lua-language-server
209
+
210
+ # Bash
211
+ npm install -g bash-language-server
212
+
194
213
  # C# / Unity
195
214
  dotnet tool install -g Microsoft.CodeAnalysis.LanguageServer
196
215
 
@@ -252,6 +271,160 @@ Minimal shared config shape:
252
271
 
253
272
  Project-local overrides can be added in `.pi/pi-tools-suite.jsonc`; pi-tools-suite asks for trust before using project-local LSP binaries.
254
273
 
274
+ ### Popular language-server examples
275
+
276
+ Copy the entries you need into `lsp.servers` of the shared config. Values mirror the commented templates shipped in the generated config file; where they disagree, the generated file is authoritative. Both diagnostics modes are on by default: servers that support pull diagnostics (`textDocument/diagnostic`) are queried directly, and push diagnostics (`publishDiagnostics`) are awaited for every server — `pullDiagnostics: false` / `waitForPublishDiagnostics: false` disable either side explicitly. Servers start lazily: one spawns only after a mutating tool (Edit/Write/ast-grep/apply_patch) touches a file matching `include`, and diagnostics land in that tool's result.
277
+
278
+ ```jsonc
279
+ {
280
+ "lsp": {
281
+ "servers": [
282
+ // Svelte (verified with svelte-language-server): compiler + embedded TS/JS diagnostics
283
+ {
284
+ "id": "svelte",
285
+ "include": ["**/*.svelte"],
286
+ "exclude": ["**/node_modules/**"],
287
+ "rootMarkers": ["svelte.config.js", "package.json"],
288
+ "bin": "svelteserver",
289
+ "args": ["--stdio"],
290
+ "startupTimeoutMs": 30000,
291
+ "diagnosticsWaitMs": 8000,
292
+ "languageIdByExtension": { ".svelte": "svelte" }
293
+ },
294
+ // Vue (Volar)
295
+ {
296
+ "id": "vue",
297
+ "include": ["**/*.vue"],
298
+ "exclude": ["**/node_modules/**"],
299
+ "rootMarkers": ["package.json"],
300
+ "bin": "vue-language-server",
301
+ "args": ["--stdio"],
302
+ "startupTimeoutMs": 30000,
303
+ "diagnosticsWaitMs": 8000,
304
+ "languageIdByExtension": { ".vue": "vue" }
305
+ },
306
+ // Python (python-lsp-server)
307
+ {
308
+ "id": "python",
309
+ "include": ["**/*.py", "**/*.pyi"],
310
+ "exclude": ["**/.git/**", "**/node_modules/**", "**/__pycache__/**", "**/.venv/**", "**/venv/**", "**/.tox/**", "**/.mypy_cache/**", "**/.ruff_cache/**"],
311
+ "rootMarkers": ["pyproject.toml", "setup.py", "setup.cfg", "requirements.txt", "Pipfile", "poetry.lock", ".git"],
312
+ "bin": "pylsp",
313
+ "args": [],
314
+ "languageIdByExtension": { ".py": "python", ".pyi": "python" }
315
+ },
316
+ // Go (gopls, push diagnostics)
317
+ {
318
+ "id": "go",
319
+ "include": ["**/*.go"],
320
+ "exclude": ["**/.git/**", "**/vendor/**"],
321
+ "rootMarkers": ["go.mod", ".git"],
322
+ "bin": "gopls",
323
+ "args": [],
324
+ "startupTimeoutMs": 20000,
325
+ "diagnosticsWaitMs": 8000,
326
+ "languageIdByExtension": { ".go": "go" }
327
+ },
328
+ // Rust (rust-analyzer, push diagnostics)
329
+ {
330
+ "id": "rust",
331
+ "include": ["**/*.rs"],
332
+ "exclude": ["**/.git/**", "**/node_modules/**", "**/target/**"],
333
+ "rootMarkers": ["Cargo.toml", "rust-project.json", ".git"],
334
+ "bin": "rust-analyzer",
335
+ "args": [],
336
+ "startupTimeoutMs": 20000,
337
+ "diagnosticsWaitMs": 20000,
338
+ "pullDiagnostics": false,
339
+ "waitForPublishDiagnostics": true,
340
+ "languageIdByExtension": { ".rs": "rust" }
341
+ },
342
+ // C / C++ (clangd, push diagnostics)
343
+ {
344
+ "id": "clangd",
345
+ "include": ["**/*.c", "**/*.cc", "**/*.cpp", "**/*.cxx", "**/*.h", "**/*.hh", "**/*.hpp"],
346
+ "exclude": ["**/.git/**", "**/node_modules/**"],
347
+ "rootMarkers": ["compile_commands.json", "CMakeLists.txt", "Makefile", ".clang-format", ".git"],
348
+ "bin": "clangd",
349
+ "args": [],
350
+ "startupTimeoutMs": 20000,
351
+ "diagnosticsWaitMs": 8000,
352
+ "languageIdByExtension": {
353
+ ".c": "c", ".cc": "cpp", ".cpp": "cpp", ".cxx": "cpp",
354
+ ".h": "c", ".hh": "cpp", ".hpp": "cpp"
355
+ }
356
+ },
357
+ // C# / Unity (Roslyn)
358
+ {
359
+ "id": "csharp",
360
+ "include": ["**/*.cs", "**/*.csx"],
361
+ "exclude": ["**/.git/**", "**/node_modules/**", "**/bin/**", "**/obj/**", "**/.vs/**", "**/Library/**", "**/Temp/**", "**/Logs/**"],
362
+ "rootMarkers": ["*.sln", "*.csproj", "global.json", "Directory.Build.props", "Directory.Packages.props", "Packages/manifest.json", "ProjectSettings/ProjectVersion.txt", ".git"],
363
+ "bin": "~/.dotnet/tools/roslyn-language-server",
364
+ "args": ["--stdio", "--autoLoadProjects", "--logLevel", "Error"],
365
+ "startupTimeoutMs": 30000,
366
+ "diagnosticsWaitMs": 15000,
367
+ "languageIdByExtension": { ".cs": "csharp", ".csx": "csharp" }
368
+ },
369
+ // Ruby
370
+ {
371
+ "id": "ruby",
372
+ "include": ["**/*.rb", "**/*.rake", "**/Gemfile", "**/Rakefile", "**/*.gemspec"],
373
+ "exclude": ["**/.git/**", "**/node_modules/**", "**/vendor/bundle/**", "**/.bundle/**", "**/tmp/**", "**/log/**"],
374
+ "rootMarkers": ["Gemfile.lock", "*.gemspec", "Rakefile", ".ruby-version", ".git"],
375
+ "bin": "ruby-lsp",
376
+ "args": [],
377
+ "startupTimeoutMs": 60000,
378
+ "diagnosticsWaitMs": 10000,
379
+ "languageIdByExtension": { ".rb": "ruby", ".rake": "ruby", ".gemspec": "ruby" }
380
+ },
381
+ // Lua (lua-language-server)
382
+ {
383
+ "id": "lua",
384
+ "include": ["**/*.lua"],
385
+ "exclude": ["**/.git/**", "**/node_modules/**"],
386
+ "rootMarkers": [".luarc.json", ".git"],
387
+ "bin": "lua-language-server",
388
+ "args": [],
389
+ "startupTimeoutMs": 30000,
390
+ "diagnosticsWaitMs": 6000,
391
+ "languageIdByExtension": { ".lua": "lua" }
392
+ },
393
+ // Bash
394
+ {
395
+ "id": "bash",
396
+ "include": ["**/*.sh", "**/*.bash"],
397
+ "exclude": ["**/.git/**", "**/node_modules/**"],
398
+ "rootMarkers": [".git"],
399
+ "bin": "bash-language-server",
400
+ "args": ["start"],
401
+ "startupTimeoutMs": 15000,
402
+ "diagnosticsWaitMs": 5000,
403
+ "languageIdByExtension": { ".sh": "shellscript", ".bash": "shellscript" }
404
+ },
405
+ // Markdown (link validation settings ship in the generated config template)
406
+ {
407
+ "id": "markdown",
408
+ "include": ["**/*.md", "**/*.markdown", "**/*.mdown", "**/*.mkd", "**/*.mmd"],
409
+ "exclude": ["**/.git/**", "**/node_modules/**"],
410
+ "rootMarkers": [".git", "package.json", "README.md"],
411
+ "bin": "vscode-markdown-language-server",
412
+ "args": ["--stdio"],
413
+ "startupTimeoutMs": 15000,
414
+ "diagnosticsWaitMs": 5000,
415
+ "languageIdByExtension": { ".md": "markdown", ".markdown": "markdown", ".mdown": "markdown", ".mkd": "markdown", ".mmd": "markdown" }
416
+ }
417
+ ]
418
+ }
419
+ }
420
+ ```
421
+
422
+ Notes:
423
+
424
+ - Svelte resolves `svelte` and `typescript` from the workspace `node_modules`, so project-local versions win; `.svelte.js`/`.svelte.ts` runes modules are not covered because their extensions collide with the TypeScript server.
425
+ - Vue requires `@vue/language-server` v2+ (the `vue-language-server` binary) plus the workspace's `vue` package for template type-checking.
426
+ - The full commented templates (including GDScript via a headless Godot wrapper and the complete Markdown link-validation `settings`) are written to the shared config file on first run.
427
+
255
428
  ## Async sub-agents
256
429
 
257
430
  Sub-agent model routing normally follows task overrides, subagent type config, then `ASYNC_SUBAGENTS_MODEL` / `PI_SUBAGENTS_MODEL` fallbacks. Set `ASYNC_SUBAGENTS_FORCE_CURRENT_MODEL=1` (or `PI_SUBAGENTS_FORCE_CURRENT_MODEL=1`) to ignore task/config/env model choices and launch every sub-agent with the current parent session model. When this flag is enabled, any `--model` entries in sub-agent extra args are stripped so they cannot override the current model.
@@ -520,6 +693,40 @@ npm run test:prompt-evals:dcp
520
693
 
521
694
  The default live model is `zai/glm-5-turbo`. Override it for the whole suite with `PI_TOOLS_SUITE_E2E_MODEL=provider/model`, or use the existing component variables such as `TOOL_SELECTION_E2E_MODEL`, `ASYNC_SUBAGENTS_MODEL`, `ASYNC_SUBAGENTS_ROUTING_E2E_MODEL`, and `DCP_SUMMARY_E2E_MODEL`. The normal deterministic coverage remains `npm test`; run prompt evals after changing tool descriptions, routing/classifier prompts, DCP summary prompts, or the default evaluation model.
522
695
 
696
+ ### Unified eval harness
697
+
698
+ `test/evals/` adds a shared deterministic + live-model eval layer. The coverage
699
+ gate requires every registered extension and model-facing tool to have a
700
+ deterministic contract. The initial live corpus contains 20 cases across tool
701
+ selection, coding quality, orchestration/escalation, and negative overuse
702
+ controls. Coding-quality fixtures use executable behavioral checks rather than
703
+ an LLM judge, while reports compare parent/worker tokens, provider-reported cost,
704
+ tool calls, changed files, and elapsed time.
705
+
706
+ ```bash
707
+ # Deterministic coverage/contract gate only
708
+ npm run test:evals:contracts
709
+
710
+ # Live matrix as Bun tests. Models are comma/semicolon separated.
711
+ PI_TOOLS_SUITE_EVAL_MODELS='zai/glm-5.3,openai-codex/gpt-5.6-luna,openai-codex/gpt-5.6-terra,openai-codex/gpt-5.6-sol' \
712
+ npm run test:evals:live
713
+
714
+ # Produce JSON + Markdown comparison artifacts.
715
+ PI_TOOLS_SUITE_EVAL_MODELS='zai/glm-5.3,openai-codex/gpt-5.6-terra,openai-codex/gpt-5.6-sol' \
716
+ npm run evals:report
717
+
718
+ # Focus the report runner when iterating
719
+ PI_TOOLS_SUITE_EVAL_MODELS='zai/glm-5.3' \
720
+ PI_TOOLS_SUITE_EVAL_CATEGORIES='coding-quality,negative' \
721
+ npm run evals:report
722
+ ```
723
+
724
+ Live evals are opt-in. The deterministic coverage registry is part of normal
725
+ tests, so adding an extension or tool without eval coverage fails the gate. See
726
+ [`docs/evals.md`](docs/evals.md) for the architecture, complete 20-case catalog,
727
+ fixtures, assertions, metrics, model matrix, report format, environment
728
+ variables, CI recommendations, and the procedure for adding new evals.
729
+
523
730
  Supporting docs and historical standalone README content are kept in `docs/`; third-party license texts are kept in `licenses/`.
524
731
 
525
732
  ## SDK pin