baldart 3.27.0 → 3.28.0
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/CHANGELOG.md +37 -0
- package/VERSION +1 -1
- package/framework/.claude/agents/codebase-architect.md +11 -0
- package/framework/.claude/hooks/capture-detect.sh +121 -0
- package/framework/.claude/skills/baldart-update/SKILL.md +22 -3
- package/framework/.claude/skills/bug/SKILL.md +12 -0
- package/framework/.claude/skills/prd/SKILL.md +11 -2
- package/framework/.claude/skills/prd/assets/state-template.md +10 -3
- package/framework/.claude/skills/prd/references/discovery-phase.md +180 -11
- package/framework/docs/MCP-INTEGRATION.md +119 -0
- package/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -5,6 +5,43 @@ All notable changes to BALDART will be documented in this file.
|
|
|
5
5
|
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
|
6
6
|
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
|
7
7
|
|
|
8
|
+
## [3.28.0] - 2026-05-28
|
|
9
|
+
|
|
10
|
+
Tre additions indipendenti accumulate nel working tree e pronte per il rilascio: convenzione testuale per le dipendenze MCP, supporto `.zip` per il mockup intake del PRD, e nuovo hook `capture-detect` come parte del proactive mode dello skill `/capture` (registrazione opt-in, non auto-attivata). Tre temi distinti ma raggruppati in un'unica release di accumulo perché tutti additive e zero-schema-change.
|
|
11
|
+
|
|
12
|
+
### Added — Convenzione MCP integration
|
|
13
|
+
|
|
14
|
+
- **[framework/docs/MCP-INTEGRATION.md](framework/docs/MCP-INTEGRATION.md)**: nuovo documento centralizzato. Spiega quando un agent/skill deve appoggiarsi a un MCP server, fornisce un catalogo di MCP raccomandati per i casi d'uso comuni (doc-rag, playwright, firestore/db, LSP, …), e definisce la convenzione testuale "MCP dependencies" per dichiarare le dipendenze nel body dell'agent/skill. Zero nuove chiavi config in `baldart.config.yml` — la convenzione resta testuale finché una skill concreta non dovrà gate-arne il comportamento (regola di schema-change propagation: niente layer drift).
|
|
15
|
+
- **[framework/.claude/agents/codebase-architect.md](framework/.claude/agents/codebase-architect.md)**: aggiunta sezione `## MCP dependencies` con classificazione Required (`doc-rag` come primo step dell'Investigation Protocol) vs Optional (LSP find-references, DB MCP per inspect runtime). Documentato il degrade path quando l'MCP non è disponibile.
|
|
16
|
+
- **[framework/.claude/skills/bug/SKILL.md](framework/.claude/skills/bug/SKILL.md)**: aggiunta sezione `## MCP dependencies` con Required (`playwright` per Phase 1 reproduction di UI/Client bug — senza è impossibile catturare stato deterministico) e Optional (`doc-rag` per known patterns, DB MCP per Data bugs, `codebase-architect` agent).
|
|
17
|
+
|
|
18
|
+
### Added — PRD mockup intake da archivio `.zip`
|
|
19
|
+
|
|
20
|
+
- **[framework/.claude/skills/prd/SKILL.md](framework/.claude/skills/prd/SKILL.md)** Step 1.6: nuovo formato `local-archive` accettato accanto a `chat-images` / `local-paths` / `mixed`. Caso d'uso: export "Download as .zip" da Claude Design (o qualsiasi altro tool che produce bundle di mockup) già scaricato sul disco dell'utente.
|
|
21
|
+
- **[framework/.claude/skills/prd/references/discovery-phase.md](framework/.claude/skills/prd/references/discovery-phase.md)** § Mockup Intake: Step 1.6.4b descrive l'intero flow per `.zip` — `unzip` in scratch dir `mockups/_archive/`, enumerazione candidati visivi, scoring di rilevanza contro lo scope del Kickoff, selezione auto-proposta, STOP per conferma, materializzazione del sottoinsieme confermato in `${paths.prd_dir}/<slug>/mockups/`. Evita di copiare PNG irrilevanti nell'asset directory definitiva.
|
|
22
|
+
- **[framework/.claude/skills/prd/assets/state-template.md](framework/.claude/skills/prd/assets/state-template.md)**: aggiornato `mockups.format` enum per includere `local-archive`.
|
|
23
|
+
|
|
24
|
+
### Added — Hook `capture-detect` (proactive mode, opt-in)
|
|
25
|
+
|
|
26
|
+
- **[framework/.claude/hooks/capture-detect.sh](framework/.claude/hooks/capture-detect.sh)**: nuovo Stop hook che drop una candidate JSON in `.claude/capture-queue/` quando rileva ragionamento cross-document nella sessione appena chiusa. La distillazione vera in synthesis page wiki resta sempre una human-approved manual step via lo skill `/capture`. Failure-isolated (exit 0 sempre, non blocca lo Stop event).
|
|
27
|
+
- **Registrazione opt-in (NOT auto-attivata)**: la entry corrispondente in [src/utils/hooks.js](src/utils/hooks.js) resta commentata (linee 90-97). Lo skill `/capture` funziona già in modalità manual senza il hook; il proactive mode è una feature opzionale. Per attivarlo nel proprio consumer: scommentare la entry e re-installare via `npx baldart update`. Una futura release potrà rendere il proactive il default.
|
|
28
|
+
|
|
29
|
+
### Added — Smoke test del hooks registry
|
|
30
|
+
|
|
31
|
+
- **[scripts/test-hooks.sh](scripts/test-hooks.sh)**: nuovo smoke test per `src/utils/hooks.js` (multi-hook registry introdotto v3.18.0). Verifica register/unregister/isRegistered/merge idempotente con fixture in tmpdir. Dev tooling, non user-visible.
|
|
32
|
+
|
|
33
|
+
## [3.27.1] - 2026-05-28
|
|
34
|
+
|
|
35
|
+
Patch follow-up alla v3.27.0 dopo l'incidente reale in `mayo`: l'utente aveva CLI globale v3.24.0 e ha eseguito `/baldart-update` per aggiornarsi a v3.27.0. La skill ha rilanciato `npx baldart update`, che ha aggiornato il framework payload da v3.24 a v3.27, ma `update.js` in esecuzione era il binario v3.24.0 — quello che precede sia il meccanismo di auto-relaunch (introdotto v3.26.0) sia la logica di symlink-indirection (v3.27.0). Risultato: i 6 agent overlay-merged sono stati rigenerati con la **vecchia logica** (file regolari direttamente in `.claude/agents/`), e quindi il fix v3.27.0 NON si è attivato — `npx baldart doctor` ha riportato "tutto healthy" ma in realtà gli agent erano ancora invisibili a Claude Code (bug #20931). Chicken-and-egg: il CLI vecchio non sa rilanciare il nuovo, il nuovo non è ancora in esecuzione.
|
|
36
|
+
|
|
37
|
+
### Fixed — /baldart-update skill: CLI version drift gate
|
|
38
|
+
|
|
39
|
+
- **[framework/.claude/skills/baldart-update/SKILL.md](framework/.claude/skills/baldart-update/SKILL.md)** Step 0: la skill ora rileva esplicitamente il CLI version drift e HALTA pre-update quando il CLI globale è < v3.26.0 (no auto-relaunch) e il payload sta per attraversare il boundary v3.27.0 (migration breaking). Decision logic articolata: se CLI è già >= v3.26.0 lascia che l'auto-relaunch faccia il suo lavoro; altrimenti istruisce `npm i -g baldart@latest` PRIMA di ri-eseguire la skill. Evita il silent-fail dove il CLI vecchio applica una pseudo-migration con codice obsoleto.
|
|
40
|
+
|
|
41
|
+
### Note al curator
|
|
42
|
+
|
|
43
|
+
Questo è un edge case strutturale che si manifesta SOLO quando un consumer attraversa il boundary v3.26.0 / v3.27.0 partendo da un CLI globale precedente alla v3.26.0. I consumer già su CLI v3.26.0+ hanno l'auto-relaunch (`npx baldart@latest`) e non sono affected. Per i consumer pre-v3.26.0 il fix in skill aiuta solo le sessioni future (skill caricata da framework payload >= v3.27.1); chi aveva già la skill vecchia in sessione al momento dell'incidente — come `mayo` ieri — può solo riparare manualmente: `npm i -g baldart@latest` + restart sessione CC + `/baldart-update`.
|
|
44
|
+
|
|
8
45
|
## [3.27.0] - 2026-05-28
|
|
9
46
|
|
|
10
47
|
Fix critico al meccanismo di overlay-merge degli agent. Sintomo riproducibile osservato in `mayo` durante `/new FEAT-0009 -full` (team mode, claude-opus-4-7): gli agent overlay-merged (`coder`, `ui-expert`, `code-reviewer`, `doc-reviewer`, `qa-sentinel`, `security-reviewer` quando hanno un overlay) **non comparivano nella lista "Available agent types"** del Claude Code session reminder. Sequenza concreta: `codebase-architect` (symlink) parte e completa; i 4 background agent (`coder×2` + `ui-expert×2`) lanciati subito dopo falliscono con `InputValidationError: subagent_type not recognized`; l'orchestratore halta con un AskUserQuestion fuori-protocollo. Repro: `ls -la .claude/agents/` mostra 21 symlink + 6 file regolari (i 6 overlay-merged); CC discoverizza i 21 symlink e omette i 6 file regolari. Confermato su sessioni indipendenti del 2026-05-27 e 2026-05-28 → bug strutturale, non transiente. Workflow `/new` in team mode, `/check`, `/qa`, `/codexreview` e skill `prd` erano **bloccati end-to-end** su qualsiasi consumer con overlay agent.
|
package/VERSION
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
3.
|
|
1
|
+
3.28.0
|
|
@@ -37,6 +37,17 @@ This codebase follows strict protocols defined in AGENTS.md. Key architectural r
|
|
|
37
37
|
- `/docs/references/project-status.md` - Current system state and active work
|
|
38
38
|
- `agents/coding-standards.md` - Terminology and coding conventions
|
|
39
39
|
|
|
40
|
+
## MCP dependencies
|
|
41
|
+
|
|
42
|
+
See [framework/docs/MCP-INTEGRATION.md](../../docs/MCP-INTEGRATION.md) for the BALDART MCP integration contract and the rationale behind this section.
|
|
43
|
+
|
|
44
|
+
**Required** (this agent's primary investigation protocol assumes them; degraded operation only):
|
|
45
|
+
- `mcp__doc-rag__search_docs` — semantic + knowledge-graph search across project docs. This is the **first** call in the Investigation Protocol; without it the agent falls back to broad `rg` sweeps that blow the token budget and miss canonical sources. If the MCP is unavailable the agent must announce the degrade explicitly and switch to targeted `rg` over `docs/`, `backlog/`, and `.claude/agents/` (see § Investigation Protocol step 1).
|
|
46
|
+
|
|
47
|
+
**Optional** (the agent benefits if present, has a documented fallback):
|
|
48
|
+
- LSP find-references / go-to-definition (whichever LSP MCP / plugin is wired by [features.has_lsp_layer](../../templates/baldart.config.template.yml)) — preferred over `rg` for symbol queries (cap: 3 LSP calls per task, then escalate to direct file reads). Fallback: silent degrade to Grep, per [code-search-protocol.md](../../agents/code-search-protocol.md).
|
|
49
|
+
- `mcp__plugin_firebase_firebase__firestore_*` (or equivalent DB MCP) — only when the architectural analysis needs to inspect runtime DB state (rare for an architect agent). Fallback: read schema docs in `${paths.references_dir}` and rely on declared structure.
|
|
50
|
+
|
|
40
51
|
## Linking Protocol Consumption (MUST)
|
|
41
52
|
|
|
42
53
|
You consume Linking Protocol v1 in read-only mode to find the right facts faster before
|
|
@@ -0,0 +1,121 @@
|
|
|
1
|
+
#!/usr/bin/env bash
|
|
2
|
+
#
|
|
3
|
+
# capture-detect.sh — BALDART proactive capture hook (event: Stop)
|
|
4
|
+
#
|
|
5
|
+
# Runs at the end of every Claude Code session. When the just-finished
|
|
6
|
+
# session contains cross-document reasoning (the user has been weaving
|
|
7
|
+
# together facts from multiple docs/references files), this hook drops a
|
|
8
|
+
# *candidate* file into `.claude/capture-queue/` so the next `/capture`
|
|
9
|
+
# invocation can surface it and offer to distill the synthesis into a
|
|
10
|
+
# durable wiki page.
|
|
11
|
+
#
|
|
12
|
+
# This hook NEVER spawns Claude itself — it only writes a small JSON
|
|
13
|
+
# candidate. The actual synthesis is always a human-approved manual step
|
|
14
|
+
# via the `capture` skill.
|
|
15
|
+
#
|
|
16
|
+
# Stdin: Claude Code passes a JSON envelope; we read `transcript_path`,
|
|
17
|
+
# `session_id`, `cwd` (best-effort — falls back if jq is unavailable).
|
|
18
|
+
#
|
|
19
|
+
# Exit: always 0. Failure isolation — a non-zero exit on a Stop hook can
|
|
20
|
+
# be ignored by the runtime, but as a matter of hygiene we never
|
|
21
|
+
# propagate errors out of an instrumentation hook.
|
|
22
|
+
|
|
23
|
+
set -u
|
|
24
|
+
exec 2>/dev/null # silence stderr; we are not user-visible
|
|
25
|
+
|
|
26
|
+
# --- read envelope --------------------------------------------------------
|
|
27
|
+
|
|
28
|
+
INPUT=""
|
|
29
|
+
if [ ! -t 0 ]; then
|
|
30
|
+
INPUT="$(cat)"
|
|
31
|
+
fi
|
|
32
|
+
|
|
33
|
+
# Try jq first, fall back to grep/sed extraction.
|
|
34
|
+
get_field() {
|
|
35
|
+
local field="$1"
|
|
36
|
+
if command -v jq >/dev/null 2>&1; then
|
|
37
|
+
printf '%s' "$INPUT" | jq -r ".$field // empty" 2>/dev/null
|
|
38
|
+
else
|
|
39
|
+
printf '%s' "$INPUT" | sed -n "s/.*\"$field\"[[:space:]]*:[[:space:]]*\"\\([^\"]*\\)\".*/\\1/p" | head -1
|
|
40
|
+
fi
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
TRANSCRIPT_PATH="$(get_field transcript_path)"
|
|
44
|
+
SESSION_ID="$(get_field session_id)"
|
|
45
|
+
CWD_FROM_ENV="$(get_field cwd)"
|
|
46
|
+
CWD="${CWD_FROM_ENV:-$PWD}"
|
|
47
|
+
|
|
48
|
+
[ -n "$TRANSCRIPT_PATH" ] || exit 0
|
|
49
|
+
[ -f "$TRANSCRIPT_PATH" ] || exit 0
|
|
50
|
+
|
|
51
|
+
cd "$CWD" 2>/dev/null || exit 0
|
|
52
|
+
|
|
53
|
+
# --- gate on features.has_wiki_overlay -----------------------------------
|
|
54
|
+
|
|
55
|
+
CONFIG="baldart.config.yml"
|
|
56
|
+
[ -f "$CONFIG" ] || exit 0
|
|
57
|
+
# Coarse check: look for `has_wiki_overlay: true` (whitespace-tolerant).
|
|
58
|
+
if ! grep -E '^\s*has_wiki_overlay\s*:\s*true\b' "$CONFIG" >/dev/null 2>&1; then
|
|
59
|
+
exit 0
|
|
60
|
+
fi
|
|
61
|
+
|
|
62
|
+
# --- gates: kill switch + anti-spam --------------------------------------
|
|
63
|
+
|
|
64
|
+
QUEUE_DIR=".claude/capture-queue"
|
|
65
|
+
mkdir -p "$QUEUE_DIR" || exit 0
|
|
66
|
+
|
|
67
|
+
[ -f "$QUEUE_DIR/.disabled" ] && exit 0
|
|
68
|
+
|
|
69
|
+
# Anti-spam: refuse when ≥10 unprocessed candidates already queued.
|
|
70
|
+
EXISTING="$(find "$QUEUE_DIR" -maxdepth 1 -type f -name '*.json' 2>/dev/null | wc -l | tr -d ' ')"
|
|
71
|
+
[ "${EXISTING:-0}" -ge 10 ] && exit 0
|
|
72
|
+
|
|
73
|
+
# --- heuristic: is this session worth flagging? --------------------------
|
|
74
|
+
#
|
|
75
|
+
# We treat "≥3 distinct docs/references-style paths mentioned across the
|
|
76
|
+
# session" as a weak signal of cross-document reasoning. False positives
|
|
77
|
+
# are acceptable here — the user reviews every candidate in /capture and
|
|
78
|
+
# can reject. False negatives are also fine — the user can always invoke
|
|
79
|
+
# /capture manually.
|
|
80
|
+
|
|
81
|
+
REFS="$(grep -ohE '(\./|/|\b)((docs|wiki|references|backlog|prd)/[A-Za-z0-9._/-]+\.(md|yml|yaml|json))' "$TRANSCRIPT_PATH" 2>/dev/null \
|
|
82
|
+
| sort -u | head -10)"
|
|
83
|
+
|
|
84
|
+
REF_COUNT="$(printf '%s\n' "$REFS" | grep -c . || true)"
|
|
85
|
+
[ "${REF_COUNT:-0}" -lt 3 ] && exit 0
|
|
86
|
+
|
|
87
|
+
# --- write candidate ------------------------------------------------------
|
|
88
|
+
|
|
89
|
+
TS_FILE="$(date -u +%Y%m%dT%H%M%SZ)"
|
|
90
|
+
TS_HUMAN="$(date -u +'%Y-%m-%d %H:%M UTC')"
|
|
91
|
+
OUT="$QUEUE_DIR/${TS_FILE}-${SESSION_ID:-unknown}.json"
|
|
92
|
+
|
|
93
|
+
# JSON-escape with awk (no jq required for emit either).
|
|
94
|
+
escape_json() {
|
|
95
|
+
printf '%s' "$1" | awk 'BEGIN{ORS=""} {gsub(/\\/,"\\\\"); gsub(/"/,"\\\""); gsub(/\r/,""); gsub(/\n/,"\\n"); print}'
|
|
96
|
+
}
|
|
97
|
+
|
|
98
|
+
REFS_JSON="["
|
|
99
|
+
first=1
|
|
100
|
+
while IFS= read -r r; do
|
|
101
|
+
[ -z "$r" ] && continue
|
|
102
|
+
if [ $first -eq 1 ]; then first=0; else REFS_JSON="$REFS_JSON,"; fi
|
|
103
|
+
REFS_JSON="$REFS_JSON\"$(escape_json "$r")\""
|
|
104
|
+
done <<EOF
|
|
105
|
+
$REFS
|
|
106
|
+
EOF
|
|
107
|
+
REFS_JSON="$REFS_JSON]"
|
|
108
|
+
|
|
109
|
+
cat > "$OUT" <<JSON
|
|
110
|
+
{
|
|
111
|
+
"trigger": "cross_doc_refs",
|
|
112
|
+
"detected_at": "$TS_HUMAN",
|
|
113
|
+
"session_id": "$(escape_json "${SESSION_ID:-unknown}")",
|
|
114
|
+
"transcript_path": "$(escape_json "$TRANSCRIPT_PATH")",
|
|
115
|
+
"refs_mentioned": $REFS_JSON,
|
|
116
|
+
"excerpt": "Session referenced ${REF_COUNT} distinct doc paths — possible cross-document synthesis worth capturing.",
|
|
117
|
+
"hint": "Run /capture to review this candidate."
|
|
118
|
+
}
|
|
119
|
+
JSON
|
|
120
|
+
|
|
121
|
+
exit 0
|
|
@@ -178,9 +178,28 @@ Match the `Remote:` line in this order (first match wins):
|
|
|
178
178
|
|
|
179
179
|
Always also capture:
|
|
180
180
|
- `Installed:\s+v(\S+)` → `installedVersion` (saved for post-flight assert).
|
|
181
|
-
- `CLI:\s+v\S
|
|
182
|
-
|
|
183
|
-
|
|
181
|
+
- `CLI:\s+v(\S+?)(?:\s+→\s+v(\S+)\s+available)?` → `cliVersion` (current CLI binary)
|
|
182
|
+
+ optional `cliLatest` (newest npm version).
|
|
183
|
+
|
|
184
|
+
**CLI version drift gate (BLOCKING)** — added in v3.27.1 after a real
|
|
185
|
+
incident in `mayo`: a consumer on CLI v3.24.0 ran update against payload
|
|
186
|
+
v3.27.0 and the v3.27.0 symlink-indirection migration silently did NOT
|
|
187
|
+
trigger (the running `update.js` was the v3.24.0 binary, predating both
|
|
188
|
+
auto-relaunch and the migration logic). The CLI v3.26.0+ self-relaunches
|
|
189
|
+
via `npx baldart@latest`, but pre-v3.26.0 binaries do not — chicken-and-egg.
|
|
190
|
+
|
|
191
|
+
Decision logic (apply after parsing):
|
|
192
|
+
|
|
193
|
+
| If… | Then… |
|
|
194
|
+
|---|---|
|
|
195
|
+
| `cliVersion >= 3.26.0` AND `cliLatest` present | Tell once: "Il CLI globale è v<cliVersion>, ne esiste v<cliLatest>. L'update si autorelancerà via `npx baldart@latest` — niente da fare." Continue. |
|
|
196
|
+
| `cliVersion < 3.26.0` AND `installedVersion >= 3.27.0` (already on the new payload but old binary) | **HALT**. Tell the user: "Il CLI globale (v<cliVersion>) è troppo vecchio per applicare la migration symlink-indirection di v3.27.0 (introdotta v3.26.0+ self-relaunch e v3.27.0 symlink-indirection). Lancia `npm i -g baldart@latest` PRIMA di ri-eseguire /baldart-update, altrimenti `update.js` non vedrà la nuova logica e i 6 agent overlay-merged resteranno file regolari invisibili a Claude Code (bug #20931)." Do not launch `npx baldart update`. |
|
|
197
|
+
| `cliVersion < 3.26.0` AND `installedVersion < 3.27.0` AND update is going to bring the payload to `>= 3.27.0` (parse the remoteVersion from Step 0) | **HALT** with the same message — the payload will cross the v3.27.0 boundary during this update, and the running `update.js` will lack the migration logic. |
|
|
198
|
+
| Otherwise | Continue normally. |
|
|
199
|
+
|
|
200
|
+
Semver compare: split on `.`, compare numerically. Treat any non-numeric
|
|
201
|
+
segment (e.g. `3.27.0-rc1`) as "less than" the same major.minor.patch
|
|
202
|
+
without suffix only when strictly required; if unsure, ASK the user.
|
|
184
203
|
|
|
185
204
|
**Decision after parsing**:
|
|
186
205
|
|
|
@@ -21,6 +21,18 @@ Argument: optional bug description (e.g., `/bug feature X is not saving`).
|
|
|
21
21
|
**Overlay:** loads `.baldart/overlays/bug.md` if present — project-specific debug entry points (e.g. SWR debug switches, env summary helpers, error-code modules). The base skill stays generic; project-specific code paths live in the overlay.
|
|
22
22
|
**On missing/empty keys:** ask the user; do not assume defaults. See `framework/agents/project-context.md` § 3.
|
|
23
23
|
|
|
24
|
+
## MCP dependencies
|
|
25
|
+
|
|
26
|
+
See [framework/docs/MCP-INTEGRATION.md](../../../docs/MCP-INTEGRATION.md) for the BALDART MCP integration contract and the rationale behind this section.
|
|
27
|
+
|
|
28
|
+
**Required** (skill cannot complete its task without these MCPs for the relevant bug class):
|
|
29
|
+
- `mcp__playwright__browser_*` (`browser_navigate`, `browser_take_screenshot`, `browser_console_messages`, `browser_network_requests`, `browser_evaluate`) — Phase 1 reproduction for **UI/Client** bugs. Without it the skill cannot capture deterministic state and Phase 1 degrades to "ask the user to reproduce manually and paste console logs". Phase 2's client-side `window.fetch` interception is impossible without `browser_evaluate`.
|
|
30
|
+
|
|
31
|
+
**Optional** (the skill benefits if present, has a documented fallback):
|
|
32
|
+
- `mcp__doc-rag__search_docs` — Phase 0 lookup for known patterns and error codes. Fallback: targeted `rg` over the project's error-code module (path listed in `.baldart/overlays/bug.md`) and `docs/wiki/`.
|
|
33
|
+
- `mcp__plugin_firebase_firebase__firestore_*` (or the project's DB MCP, when `stack.database.primary` is set) — Phase 1 inspection of runtime data state for **Data** bugs. Fallback: ask the user for a document export, or read the relevant code path and infer.
|
|
34
|
+
- `codebase-architect` agent (always available, listed for completeness) — Phase 0 code-path mapping. Not an MCP per se but is treated as a required dependency by this skill.
|
|
35
|
+
|
|
24
36
|
## ANTI-PATTERNS (NEVER DO)
|
|
25
37
|
|
|
26
38
|
- NEVER change code before reproducing the bug
|
|
@@ -92,8 +92,17 @@ message. You ask questions, wait for answers, and iterate.
|
|
|
92
92
|
structure and `assets/card-template.yml` for child structure.
|
|
93
93
|
16. **Mockup Intake (MANDATORY).** Subito dopo Kickoff (Step 1) e prima di entrare in
|
|
94
94
|
Discovery (Step 2), esegui Step 1.6 — chiedi all'utente se ha mockup a disposizione.
|
|
95
|
-
Se **sì**: chiedi formato (immagini in chat / path locali
|
|
96
|
-
|
|
95
|
+
Se **sì**: chiedi formato (immagini in chat / path locali — singoli file **o
|
|
96
|
+
archivi `.zip`** — / misti), **STOP**, attendi. Sull'arrivo:
|
|
97
|
+
- **chat-images** / file singoli in **local-paths**: copia in `${paths.prd_dir}/<slug>/mockups/`,
|
|
98
|
+
passa subito all'analisi.
|
|
99
|
+
- **`.zip` in local-paths** (es. export "Download as .zip" da Claude Design già
|
|
100
|
+
sul disco): esegui Step 1.6.4b — `unzip` in scratch dir sotto `mockups/_archive/`,
|
|
101
|
+
enumera i candidati visivi, calcola uno score di rilevanza contro lo scope
|
|
102
|
+
del Kickoff, presenta la selezione auto-proposta, **STOP**, attendi conferma,
|
|
103
|
+
poi materializza solo il sottoinsieme confermato in `${paths.prd_dir}/<slug>/mockups/`.
|
|
104
|
+
|
|
105
|
+
Quindi analizza in dettaglio (vedi
|
|
97
106
|
[discovery-phase.md](references/discovery-phase.md) § "Mockup analysis schema"), popola
|
|
98
107
|
`## UI Design` nello state, poi entra in Discovery. Se **no**: marca
|
|
99
108
|
`mockups.status: none` e procedi col flow standard. Il decision tree di Step 3 (UI Design)
|
|
@@ -74,11 +74,18 @@ Scenarios: pending
|
|
|
74
74
|
|
|
75
75
|
## UI Design
|
|
76
76
|
|
|
77
|
-
mockups.status: pending # none | requested | provided | partial
|
|
78
|
-
mockups.format: pending # chat-images | local-paths | mixed
|
|
79
|
-
mockups.original_paths: [] # user-provided paths
|
|
77
|
+
mockups.status: pending # none | requested | provided | partial | pending_external
|
|
78
|
+
mockups.format: pending # chat-images | local-paths | local-archive | mixed
|
|
79
|
+
mockups.original_paths: [] # user-provided paths, chat://image-N, or archive://<rel-path>
|
|
80
80
|
mockups.canonical_paths: [] # mockups/<file> after copy
|
|
81
81
|
|
|
82
|
+
mockups.archive: # populated only when format includes local-archive
|
|
83
|
+
local_zip_path: pending # abs path of the .zip the user gave us
|
|
84
|
+
kind: pending # zip
|
|
85
|
+
extracted_dir: pending # abs path of _archive/extracted/
|
|
86
|
+
truncated: false # true when candidate list capped at 200
|
|
87
|
+
candidates: [] # see discovery-phase.md § 1.6.4b step b-c
|
|
88
|
+
|
|
82
89
|
mockup_analysis.screens: [] # see discovery-phase.md § Mockup analysis schema
|
|
83
90
|
mockup_analysis.user_flow: []
|
|
84
91
|
mockup_analysis.design_system_alignment:
|
|
@@ -172,9 +172,12 @@ Append this follow-up to the SAME message:
|
|
|
172
172
|
Perfetto. In che forma me li passi?
|
|
173
173
|
|
|
174
174
|
- **Immagini in chat** — incollale direttamente nel prossimo messaggio.
|
|
175
|
-
- **Path locali** — incolla i percorsi (assoluti o relativi al repo)
|
|
176
|
-
in `${paths.prd_dir}/<slug>/mockups/`.
|
|
177
|
-
- **
|
|
175
|
+
- **Path locali** — incolla i percorsi (assoluti o relativi al repo). Funzionano:
|
|
176
|
+
- file singoli (PNG, HTML, SVG, …) → li copio in `${paths.prd_dir}/<slug>/mockups/`.
|
|
177
|
+
- **archivi `.zip`** (es. export "Download as .zip" da Claude Design già
|
|
178
|
+
scaricato sul tuo disco) → lo unzippo io, analizzo TUTTI i mockup dentro
|
|
179
|
+
e seleziono automaticamente quelli rilevanti per questa feature.
|
|
180
|
+
- **Misti** — combinazioni delle modalità sopra.
|
|
178
181
|
```
|
|
179
182
|
|
|
180
183
|
- Update state file `## UI Design`: `mockups.status: requested`, `mockups.format: pending`.
|
|
@@ -184,19 +187,170 @@ Perfetto. In che forma me li passi?
|
|
|
184
187
|
|
|
185
188
|
When the user replies with the mockups:
|
|
186
189
|
|
|
187
|
-
1. **Detect format** and update `mockups.format` ∈ {`chat-images`, `local-paths`, `mixed`}.
|
|
190
|
+
1. **Detect format** and update `mockups.format` ∈ {`chat-images`, `local-paths`, `local-archive`, `mixed`}.
|
|
191
|
+
- `local-archive` applies when at least one of the provided local paths is a
|
|
192
|
+
`.zip` (case-insensitive) — also if mixed with other regular files.
|
|
188
193
|
2. **For each local path provided:**
|
|
189
194
|
- Resolve to absolute path. If file does not exist: ask the user to confirm/correct
|
|
190
195
|
(do not silently skip).
|
|
191
|
-
-
|
|
192
|
-
|
|
193
|
-
|
|
196
|
+
- **If the path is a `.zip`** (extension match OR `file <path>` reports a Zip
|
|
197
|
+
archive): route it to Step 1.6.4b and DO NOT copy the zip itself into
|
|
198
|
+
`${paths.prd_dir}/<slug>/mockups/`. Only the user-confirmed subset extracted
|
|
199
|
+
from it ends up there.
|
|
200
|
+
- **Otherwise** (regular mockup file): ensure `${paths.prd_dir}/<slug>/mockups/`
|
|
201
|
+
exists (create if missing), then copy the file into that directory,
|
|
202
|
+
preserving filename. On collision (file with same name already there):
|
|
203
|
+
append numeric suffix (`<name>-2.png`).
|
|
194
204
|
- Record both paths in state: `mockups.original_paths[]` and `mockups.canonical_paths[]`.
|
|
195
205
|
3. **For chat images:** record in state `mockups.original_paths[]` as `chat://image-N`
|
|
196
206
|
(the images remain in the conversation context window).
|
|
197
|
-
4.
|
|
207
|
+
4. **For zip archives:** execute Step 1.6.4b BEFORE marking `status: provided`. The
|
|
208
|
+
archive flow has its own scan + selection + confirmation gate; only the
|
|
209
|
+
user-confirmed subset is copied into `${paths.prd_dir}/<slug>/mockups/`.
|
|
210
|
+
5. Update `mockups.status: provided` (or `partial` only if the user explicitly says
|
|
198
211
|
"ho solo questi 2 ma servono anche altri").
|
|
199
212
|
|
|
213
|
+
### 1.6.4b — Archive ingestion & relevance selection (when `mockups.format` includes `local-archive`)
|
|
214
|
+
|
|
215
|
+
Triggered when the user hands a local `.zip` path (typically a Claude Design
|
|
216
|
+
"Download as .zip" export already on disk). The flow scans every mockup inside,
|
|
217
|
+
scores each against the feature scope from Kickoff, and asks the user to confirm
|
|
218
|
+
the auto-selected subset before analysis.
|
|
219
|
+
|
|
220
|
+
#### Step a — Detect & unpack
|
|
221
|
+
|
|
222
|
+
For each zip path provided:
|
|
223
|
+
|
|
224
|
+
```bash
|
|
225
|
+
file "<user-zip-path>"
|
|
226
|
+
```
|
|
227
|
+
|
|
228
|
+
- If `file` does NOT report a Zip archive, treat the path as a regular file and
|
|
229
|
+
go back to step 1.6.4 point 2's "Otherwise" branch — no special handling.
|
|
230
|
+
- If it IS a zip, record in state:
|
|
231
|
+
- `mockups.archive.local_zip_path: <user-zip-path>` (absolute)
|
|
232
|
+
- `mockups.archive.kind: zip`
|
|
233
|
+
- Unpack into a scratch directory under the PRD's mockup folder:
|
|
234
|
+
|
|
235
|
+
```bash
|
|
236
|
+
mkdir -p "$WORKTREE_PATH/${paths.prd_dir}/<slug>/mockups/_archive"
|
|
237
|
+
unzip -q "<user-zip-path>" \
|
|
238
|
+
-d "$WORKTREE_PATH/${paths.prd_dir}/<slug>/mockups/_archive/extracted"
|
|
239
|
+
```
|
|
240
|
+
|
|
241
|
+
- Record `mockups.archive.extracted_dir`.
|
|
242
|
+
- If `unzip` fails (corrupted/encrypted): STOP, surface the exit code, ask the
|
|
243
|
+
user to verify the zip or provide an alternative.
|
|
244
|
+
|
|
245
|
+
#### Step b — Enumerate candidates
|
|
246
|
+
|
|
247
|
+
Scan the extracted tree for mockup-shaped files. The candidate filter is:
|
|
248
|
+
|
|
249
|
+
- Extensions: `.html`, `.htm`, `.png`, `.jpg`, `.jpeg`, `.svg`, `.webp`, `.gif`, `.pdf`.
|
|
250
|
+
- Exclude: `node_modules/`, `.git/`, anything under a directory named `assets/`
|
|
251
|
+
whose parent is itself excluded, `*.min.*`, `thumbs.db`, `.DS_Store`.
|
|
252
|
+
- Size sanity: skip files > 50 MB (likely video/binary blobs, never a mockup).
|
|
253
|
+
|
|
254
|
+
```bash
|
|
255
|
+
find "$WORKTREE_PATH/${paths.prd_dir}/<slug>/mockups/_archive/extracted" \
|
|
256
|
+
-type f \
|
|
257
|
+
\( -iname '*.html' -o -iname '*.htm' -o -iname '*.png' -o -iname '*.jpg' \
|
|
258
|
+
-o -iname '*.jpeg' -o -iname '*.svg' -o -iname '*.webp' -o -iname '*.gif' \
|
|
259
|
+
-o -iname '*.pdf' \) \
|
|
260
|
+
-size -50M \
|
|
261
|
+
-not -path '*/node_modules/*' -not -path '*/.git/*' \
|
|
262
|
+
-not -name '*.min.*' -not -name 'thumbs.db' -not -name '.DS_Store'
|
|
263
|
+
```
|
|
264
|
+
|
|
265
|
+
For each candidate, build a lightweight index entry:
|
|
266
|
+
- `path` (relative to `extracted/`)
|
|
267
|
+
- `filename`
|
|
268
|
+
- `ext`
|
|
269
|
+
- `size_kb`
|
|
270
|
+
- For HTML: `<title>` content + first `<h1>` (use `grep -oE` or a single Read of
|
|
271
|
+
the first ~200 lines; do NOT load the full file — they can be massive).
|
|
272
|
+
- For images: nothing extra at this stage (filename is the only cheap signal).
|
|
273
|
+
|
|
274
|
+
Cap the indexed list at 200 entries. If the archive contains more, sort by
|
|
275
|
+
`size_kb DESC` (larger files are typically the rendered screens) and keep the
|
|
276
|
+
top 200, recording `mockups.archive.truncated: true`.
|
|
277
|
+
|
|
278
|
+
Record the full index in state under `mockups.archive.candidates[]`.
|
|
279
|
+
|
|
280
|
+
#### Step c — Score against feature scope
|
|
281
|
+
|
|
282
|
+
Build the scope vector from the Kickoff state (Step 1):
|
|
283
|
+
- `feature_title` (from `## Feature Description`).
|
|
284
|
+
- `slug`.
|
|
285
|
+
- ISA touchpoints (if Discovery dimension 9 already ran).
|
|
286
|
+
- Verbatim screen names the user mentioned in the initial description.
|
|
287
|
+
- Keywords from `feature_objective_one_sentence` (strip stopwords).
|
|
288
|
+
|
|
289
|
+
For each candidate, compute a relevance score 0-100:
|
|
290
|
+
- `+40` if any scope keyword appears in the filename (case-insensitive,
|
|
291
|
+
whole-word; for kebab/snake/camelCase, split before matching).
|
|
292
|
+
- `+30` if any scope keyword appears in the HTML `<title>` or `<h1>`.
|
|
293
|
+
- `+15` if the file path contains a directory name matching a scope keyword.
|
|
294
|
+
- `+10` if the filename matches typical screen patterns (`screen`, `page`,
|
|
295
|
+
`view`, `flow`, the user's domain entity names).
|
|
296
|
+
- `-20` if the filename matches typical non-screen patterns (`icon`, `logo`,
|
|
297
|
+
`favicon`, `thumbnail`, `og-image`, `sitemap`, `manifest`).
|
|
298
|
+
|
|
299
|
+
Selection threshold: keep candidates with `score ≥ 30` as the auto-selected set.
|
|
300
|
+
If fewer than 3 candidates clear the threshold, lower to `≥ 20` and surface the
|
|
301
|
+
fact. If zero candidates clear `≥ 20`, surface "selezione non automatizzabile —
|
|
302
|
+
ti chiedo di indicarmi a mano quali sono rilevanti" and present the full
|
|
303
|
+
candidate list.
|
|
304
|
+
|
|
305
|
+
Record per-candidate: `score`, `matched_keywords[]`, `selected: bool`.
|
|
306
|
+
|
|
307
|
+
#### Step d — Confirmation gate (STOP)
|
|
308
|
+
|
|
309
|
+
Present a compact table to the user — selected candidates first, then up to 10
|
|
310
|
+
discarded with the highest scores, then a footer count for "altri N scartati":
|
|
311
|
+
|
|
312
|
+
```
|
|
313
|
+
Bundle scaricato e analizzato: <N> file candidati, <K> selezionati come rilevanti.
|
|
314
|
+
|
|
315
|
+
**Selezionati** (score ≥ 30 vs. feature scope):
|
|
316
|
+
| # | File | Score | Match |
|
|
317
|
+
|---|-------------------------------|-------|------------------------|
|
|
318
|
+
| 1 | screens/lista-fornitori.html | 75 | "fornitori", "lista" |
|
|
319
|
+
| 2 | screens/dettaglio-ordine.html | 55 | "ordine" |
|
|
320
|
+
…
|
|
321
|
+
|
|
322
|
+
**Scartati ad alto score** (per trasparenza):
|
|
323
|
+
| # | File | Score | Motivo |
|
|
324
|
+
|---|-------------------------------|-------|------------------------|
|
|
325
|
+
| 1 | screens/landing-marketing.html| 22 | nessun keyword match |
|
|
326
|
+
…
|
|
327
|
+
|
|
328
|
+
Altri <M> file scartati (score < 20 o pattern non-schermata).
|
|
329
|
+
|
|
330
|
+
Procedo all'analisi visiva dei <K> selezionati? Oppure indicami modifiche
|
|
331
|
+
(es. "aggiungi il #3 degli scartati", "togli il #2 dei selezionati").
|
|
332
|
+
```
|
|
333
|
+
|
|
334
|
+
**STOP.** Wait for explicit confirmation or an adjustment list. On adjustment,
|
|
335
|
+
recompute `mockups.archive.candidates[].selected`, then re-present and STOP again
|
|
336
|
+
until the user confirms.
|
|
337
|
+
|
|
338
|
+
#### Step e — Materialize the confirmed subset
|
|
339
|
+
|
|
340
|
+
Copy ONLY the confirmed selection into `${paths.prd_dir}/<slug>/mockups/`,
|
|
341
|
+
preserving relative directory structure under the extracted root so that
|
|
342
|
+
relative asset references (CSS, images) keep working. On filename collision,
|
|
343
|
+
use the `<name>-2.<ext>` rule from 1.6.4 point 2.
|
|
344
|
+
|
|
345
|
+
Record `mockups.original_paths[]` as `archive://<relative-path-in-zip>` and
|
|
346
|
+
`mockups.canonical_paths[]` as the new path under `mockups/`. The scratch
|
|
347
|
+
`_archive/extracted/` directory is kept for the duration of the PRD session
|
|
348
|
+
(may be needed to resolve `<link>` / `<img src>` references during analysis)
|
|
349
|
+
and cleaned up at Step 7 (Commit & Merge) — add a `.gitignore` entry for
|
|
350
|
+
`mockups/_archive/` if not already present.
|
|
351
|
+
|
|
352
|
+
Then continue to Step 1.6.5 with the selected subset.
|
|
353
|
+
|
|
200
354
|
### 1.6.5 — Mockup analysis (MANDATORY before Discovery)
|
|
201
355
|
|
|
202
356
|
Analyze ALL provided mockups (visual analysis for chat images, Read for copied files
|
|
@@ -561,11 +715,26 @@ structure. Be specific — vague analysis defeats the purpose of skipping Step 3
|
|
|
561
715
|
```yaml
|
|
562
716
|
mockups:
|
|
563
717
|
status: provided | partial | none | requested
|
|
564
|
-
format: chat-images | local-paths | mixed
|
|
718
|
+
format: chat-images | local-paths | local-archive | mixed
|
|
565
719
|
original_paths:
|
|
566
|
-
- <user-provided path
|
|
720
|
+
- <user-provided path, chat://image-N, or archive://<rel-path-in-zip>>
|
|
567
721
|
canonical_paths:
|
|
568
|
-
- mockups/<file>.png # only for local-paths
|
|
722
|
+
- mockups/<file>.png # only for local-paths and local-archive
|
|
723
|
+
archive: # only when format includes local-archive
|
|
724
|
+
local_zip_path: <abs path to the user-provided .zip>
|
|
725
|
+
kind: zip
|
|
726
|
+
extracted_dir: <abs path to _archive/extracted/>
|
|
727
|
+
truncated: false # true when candidate list capped at 200
|
|
728
|
+
candidates: # full enumerated list (post-filter)
|
|
729
|
+
- path: <rel path under extracted/>
|
|
730
|
+
filename: <basename>
|
|
731
|
+
ext: html | png | jpg | svg | …
|
|
732
|
+
size_kb: <int>
|
|
733
|
+
html_title: <optional, HTML only>
|
|
734
|
+
html_h1: <optional, HTML only>
|
|
735
|
+
score: <0-100>
|
|
736
|
+
matched_keywords: [<keyword>, …]
|
|
737
|
+
selected: <bool> # true = part of the confirmed subset
|
|
569
738
|
mockup_analysis:
|
|
570
739
|
screens:
|
|
571
740
|
- name: <inferred name, e.g. "Lista ordini">
|
|
@@ -0,0 +1,119 @@
|
|
|
1
|
+
# MCP Integration — Guida BALDART per i consumer
|
|
2
|
+
|
|
3
|
+
Questo documento spiega **quando** un agent/skill BALDART deve appoggiarsi a un Model Context Protocol (MCP) server, **quali** MCP sono raccomandati per i casi d'uso più comuni, e **come** dichiarare la dipendenza MCP nel body dell'agent in modo che il consumer sappia subito cosa configurare.
|
|
4
|
+
|
|
5
|
+
> **Scope di questa release**: convenzione testuale, **zero nuove chiavi config** in `baldart.config.yml`. Le chiavi `mcp.*` (es. `mcp.required: []` / `mcp.optional: []`) entreranno solo se e quando una skill concreta dovrà gatearne il comportamento, in una release dedicata con propagazione end-to-end completa (regola di [schema-change propagation](../docs/PROJECT-CONFIGURATION.md)).
|
|
6
|
+
|
|
7
|
+
---
|
|
8
|
+
|
|
9
|
+
## 1. Quando usare un MCP
|
|
10
|
+
|
|
11
|
+
Tre opzioni per integrare un sistema esterno in un agent BALDART. Scegli il più semplice che risolve il problema:
|
|
12
|
+
|
|
13
|
+
| Opzione | Quando ha senso | Costi/limiti |
|
|
14
|
+
|---|---|---|
|
|
15
|
+
| **MCP server** | Il sistema è **bidirezionale**, ha molte operazioni discrete (search, get, mutate), serve a **molti agent diversi**, o richiede **stato di sessione** (browser, DB). | Setup nel consumer (configurazione MCP), dipendenza esplicita, esposizione dei dati al modello. |
|
|
16
|
+
| **Script CLI / Bash** | È un'azione **one-shot** o **idempotente** (build, test, git, lint, deploy), output testuale ben definito, niente stato di sessione. | Niente — è la baseline. Preferibile quando funziona. |
|
|
17
|
+
| **API call diretta (fetch/curl)** | Serve **un'unica chiamata** verso un endpoint REST/GraphQL pubblico o autenticato via env var, **non serve a più agent**. | Risposta opaca al framework (non recuperabile per altri agent), parsing manuale, niente cache strutturata. |
|
|
18
|
+
|
|
19
|
+
**Regola pratica**: se la stessa integrazione tornerà utile a **2+ agent o skill**, è un MCP. Se è un'esecuzione una-tantum da una singola skill, è uno script CLI o un fetch.
|
|
20
|
+
|
|
21
|
+
---
|
|
22
|
+
|
|
23
|
+
## 2. Catalogo MCP raccomandati per i casi d'uso comuni
|
|
24
|
+
|
|
25
|
+
Non è un'imposizione: BALDART non installa MCP, non li valida, non li richiede. È una lista curata di MCP che hanno senso nei deployment dove BALDART è già in uso.
|
|
26
|
+
|
|
27
|
+
### Browser automation
|
|
28
|
+
- **Playwright MCP** (`@modelcontextprotocol/server-playwright`) — usato da [bug](../.claude/skills/bug/SKILL.md) e [webapp-testing](../.claude/skills/webapp-testing/SKILL.md) per cattura visiva, network, console.
|
|
29
|
+
|
|
30
|
+
### Documentation retrieval (RAG)
|
|
31
|
+
- **doc-rag MCP** (interno o `@modelcontextprotocol/server-everything-search` come stand-in) — usato da [codebase-architect](../.claude/agents/codebase-architect.md) e [code-search-protocol.md](../agents/code-search-protocol.md) per ricerca semantica nei doc + knowledge graph.
|
|
32
|
+
|
|
33
|
+
### Database
|
|
34
|
+
- **Firebase MCP** (`@modelcontextprotocol/server-firebase` — già integrato come plugin BALDART quando `stack.database.primary` è Firestore) — ispezione documenti, query collection, transazioni.
|
|
35
|
+
- **Postgres MCP** (`@modelcontextprotocol/server-postgres`) — per stack SQL.
|
|
36
|
+
|
|
37
|
+
### Issue tracker / project management
|
|
38
|
+
- **GitHub MCP** (`@modelcontextprotocol/server-github`) o **`gh` CLI** — issue triage, PR review, gist creation. Per BALDART consigliamo `gh` (è una CLI già universale), MCP solo se servono molte mutazioni in pipeline.
|
|
39
|
+
- **Linear MCP**, **Jira MCP** — disponibili nella registry ufficiale Anthropic per chi usa quei ticketing system.
|
|
40
|
+
|
|
41
|
+
### Design tool
|
|
42
|
+
- **Figma MCP** — usato da agent di design / UI per estrarre token, screenshot, asset.
|
|
43
|
+
|
|
44
|
+
### Observability
|
|
45
|
+
- **Sentry MCP** — già disponibile in BALDART come [sentry plugin](../../CLAUDE.md). Per analisi error → root cause.
|
|
46
|
+
|
|
47
|
+
### Communication
|
|
48
|
+
- **Slack MCP**, **Gmail MCP** — disponibili nel marketplace MCP. Usali solo se l'agent deve davvero comunicare verso umani (es. post-mortem auto-pubblicato).
|
|
49
|
+
|
|
50
|
+
**Anti-pattern**: NON installare MCP "perché esistono". Ogni MCP aggiunge tool al system prompt del modello, consuma context, e crea dipendenze infrastrutturali nel consumer. Il pattern BALDART è "tanti agent specializzati, pochi MCP universalmente utili".
|
|
51
|
+
|
|
52
|
+
---
|
|
53
|
+
|
|
54
|
+
## 3. La convenzione `## MCP dependencies` (per author di agent/skill BALDART)
|
|
55
|
+
|
|
56
|
+
Ogni agent o skill BALDART che usa MCP deve dichiararlo esplicitamente nel body, in una sezione dedicata. Questo permette:
|
|
57
|
+
- al **consumer** di sapere cosa configurare (e cosa succede se non lo configura);
|
|
58
|
+
- al `baldart doctor` futuro di leggere queste sezioni e verificare gli MCP `required`;
|
|
59
|
+
- ad altri agent di sapere se invocare questo agent è "free" o richiede setup.
|
|
60
|
+
|
|
61
|
+
### Struttura
|
|
62
|
+
|
|
63
|
+
Subito dopo la sezione `## Project Context` (o, in mancanza, subito dopo il frontmatter e l'intro):
|
|
64
|
+
|
|
65
|
+
```markdown
|
|
66
|
+
## MCP dependencies
|
|
67
|
+
|
|
68
|
+
**Required** (skill/agent rifiuta o degrada visibilmente senza questi MCP):
|
|
69
|
+
- `mcp__<server>__<tool>` — cosa serve, perché.
|
|
70
|
+
|
|
71
|
+
**Optional** (l'agent ne approfitta se disponibile, ma ha un fallback):
|
|
72
|
+
- `mcp__<server>__<tool>` — cosa offre in più, qual è il fallback.
|
|
73
|
+
|
|
74
|
+
**None** (per skill senza MCP — utile dichiararlo esplicitamente):
|
|
75
|
+
- This skill uses no MCP servers. <breve nota se rilevante>
|
|
76
|
+
```
|
|
77
|
+
|
|
78
|
+
### Regole
|
|
79
|
+
|
|
80
|
+
1. **Sii specifico**: cita il prefisso del tool (`mcp__playwright__browser_navigate`), non il "concetto" (`Playwright MCP`). Aiuta il consumer a fare grep.
|
|
81
|
+
2. **Required vs Optional**: required = la skill non può completare il proprio task senza il MCP (o degrada gravemente). Optional = la skill ha un fallback funzionante.
|
|
82
|
+
3. **Fallback espliciti**: per ogni `Optional`, descrivi il fallback in una frase ("se MCP unavailable, usa `rg` su `docs/` per trovare pattern noti").
|
|
83
|
+
4. **Niente nuovo schema in `baldart.config.yml`**: non aggiungere `mcp.required` o `mcp.optional` nel config — è solo convenzione testuale finché non c'è una skill che ha bisogno di gatearne il comportamento a runtime.
|
|
84
|
+
5. **Aggiorna la dichiarazione quando la dipendenza cambia**: se rimuovi un MCP dall'agent, rimuovi la riga; se aggiungi un fallback Grep e l'MCP diventa optional, sposta la riga.
|
|
85
|
+
|
|
86
|
+
### Esempi nel framework corrente
|
|
87
|
+
|
|
88
|
+
Vedi le seguenti dichiarazioni per pattern di riferimento:
|
|
89
|
+
- [framework/.claude/agents/codebase-architect.md](../.claude/agents/codebase-architect.md) — `## MCP dependencies` con doc-rag required + LSP-related optional.
|
|
90
|
+
- [framework/.claude/skills/bug/SKILL.md](../.claude/skills/bug/SKILL.md) — Playwright required per UI bug, doc-rag + Firestore optional.
|
|
91
|
+
- [framework/.claude/skills/playwright-skill/SKILL.md](../.claude/skills/playwright-skill/SKILL.md) — esempio di sezione "None" (la skill usa Playwright Test CLI, non MCP).
|
|
92
|
+
|
|
93
|
+
---
|
|
94
|
+
|
|
95
|
+
## 4. FAQ per il consumer
|
|
96
|
+
|
|
97
|
+
**D: BALDART installa gli MCP per me?**
|
|
98
|
+
R: No. BALDART distribuisce agent e skill che eventualmente li **usano**. L'installazione e configurazione MCP è responsabilità del consumer (di solito via `.mcp.json` o `.claude/settings.json`). Vedi la [documentazione Claude Code](https://docs.claude.com) per il setup MCP.
|
|
99
|
+
|
|
100
|
+
**D: Cosa succede se invoco un agent che richiede un MCP non configurato?**
|
|
101
|
+
R: Dipende da come l'agent è stato scritto. Gli agent BALDART che seguono il pattern raccomandato fanno **graceful degrade** (riportano il missing MCP e provano un fallback documentato). Quelli che dichiarano un MCP come **Required** dovrebbero rifiutare visibilmente di proseguire — ma oggi BALDART non enforza questa policy in modo automatico. Il `baldart doctor` futuro potrà controllarla.
|
|
102
|
+
|
|
103
|
+
**D: Posso aggiungere un MCP custom non nella lista del § 2?**
|
|
104
|
+
R: Sì, e se diventa utile a più agent valuta una PR upstream a BALDART per aggiungerlo al catalogo. Vedi [MAINTAINING.md](../../MAINTAINING.md) per il workflow di contribuzione.
|
|
105
|
+
|
|
106
|
+
**D: La mia organizzazione ha un sistema interno (ticketing, docs, monitoring) — devo per forza esporlo via MCP?**
|
|
107
|
+
R: Non per forza. Se l'integrazione serve a **uno** script una tantum, una semplice fetch è meglio. Se serve a 2+ agent BALDART o se vuoi che gli agent possano "scoprire" dati senza che tu glieli passi manualmente, allora vale la pena un MCP custom.
|
|
108
|
+
|
|
109
|
+
---
|
|
110
|
+
|
|
111
|
+
## 5. Cosa cambia per BALDART nelle prossime release
|
|
112
|
+
|
|
113
|
+
Roadmap (vedi piano [gap-analysis vs. large codebases](../../.claude/plans/voglio-che-studi-questo-fluttering-nova.md)):
|
|
114
|
+
|
|
115
|
+
- **Adesso** (questa release): convenzione testuale `## MCP dependencies`, doc + 3 agent/skill aggiornati come reference.
|
|
116
|
+
- **Prossima release MINOR** (se serve): introduzione di una skill che richiede gating runtime su MCP → in quella release sarà propagata la chiave `mcp.required/optional` end-to-end (template + configure + doctor + CHANGELOG), seguendo la regola di schema-change propagation.
|
|
117
|
+
- **Routine `mcp-check`** (opzionale, T-level): controllo settimanale che ogni MCP `Required` dichiarato nel framework abbia un endpoint sano nel consumer.
|
|
118
|
+
|
|
119
|
+
Finché la chiave config non esiste, la convenzione testuale **è** il contratto.
|