spec-first-copilot 0.6.0-beta.2 → 0.6.0-beta.4

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "spec-first-copilot",
3
- "version": "0.6.0-beta.2",
3
+ "version": "0.6.0-beta.4",
4
4
  "description": "Spec-first workflow kit for GitHub Copilot — AI-driven development with specs, not guesswork",
5
5
  "bin": {
6
6
  "spec-first-copilot": "bin/cli.js"
@@ -8,6 +8,54 @@
8
8
 
9
9
  ---
10
10
 
11
+ ## 0.6.0-beta.4 (2026-04-13)
12
+
13
+ ### UX: `/sf-mcp confluence` self-contained pra usuário leigo
14
+
15
+ Perguntas do skill agora mostram EXATAMENTE onde achar cada informação inline,
16
+ sem depender de consulta externa ao SETUP.md:
17
+
18
+ - **URL do Confluence**: "abra no browser, copie URL base com /wiki"
19
+ - **API Token**: 4 sub-passos numerados (URL Atlassian, Create button, nome, copiar antes que suma)
20
+ - **Space Key**: mostra URL pattern `/wiki/spaces/XXX/` com seta + exemplos ("ST", "DEV", "PROJ")
21
+ - **Root Page ID**: 2 opções (A: Page ID com URL pattern `/pages/NNNN/`, B: título exato com aviso de match)
22
+
23
+ Qualquer modelo / usuário leigo consegue responder sem ficar travado.
24
+
25
+ ---
26
+
27
+ ## 0.6.0-beta.3 (2026-04-13)
28
+
29
+ ### Fix: `/sf-mcp confluence` idempotente com `root_page_id` como âncora
30
+
31
+ Antes a skill era linear e podia pular a coleta do Page ID raiz do projeto depois de
32
+ um restart (caso user tivesse que reiniciar o Claude após criar `.mcp.json`), resultando
33
+ em `sfw.config.yml` sem `project.root_page_id` — framework ficava sem âncora.
34
+
35
+ Novo fluxo:
36
+ 1. Detecta estado de `sfw.config.yml` (tem root_page_id?) + `.mcp.json` (tem credenciais?)
37
+ 2. Se AMBOS existem → testa conexão e reconfirma Input/Output
38
+ 3. Se algo falta → pede só o que falta (idempotente)
39
+ 4. `root_page_id` validado contra `get_page(id)` antes de mapear árvore
40
+ 5. Handler explícito pra 401 (credencial expirou) e 404 (root inválido)
41
+
42
+ ### Fix: Auto-publish imperativo em `/sf-extract`, `/sf-design`, `/sf-plan`
43
+
44
+ Antes a instrução era "Se `sfw.config.yml` com output.targets[] ativo: Executar /sf-publish" —
45
+ ambígua, agent podia interpretar como opcional e pular.
46
+
47
+ Agora:
48
+ - Instrução imperativa: "Se `sfw.config.yml` existe → Chamar `/sf-publish`. Execute."
49
+ - Cada skill adiciona **seção "Saída obrigatória"** reportando status do publish
50
+ (CREATED/UPDATED/SKIPPED/CONFLICT/ERROR) ou "SKIPPED (no sfw.config.yml)"
51
+ - User vê explicitamente o que aconteceu no Confluence
52
+
53
+ ### Fix: `publishes: [PRD, PRD, SDD, Progresso]` → `[PRD, SDD, Progresso]`
54
+
55
+ Resquício do rename `TRD → PRD` na seção de template do `/sf-mcp confluence`. Agora gera yaml correto.
56
+
57
+ ---
58
+
11
59
  ## 0.6.0-beta.2 (2026-04-12)
12
60
 
13
61
  ### Fix: CLI `init` output
@@ -31,7 +31,7 @@ Note: **não validar** presença de `docs/` — ausência é válida (first_run)
31
31
  - `docs/` se existir (feature mode: usa como baseline pra §Sistema; não preenche subseções que não mudam)
32
32
  - `workspace/Output/$ARGUMENTS/sf-discovery.md` se existir
33
33
  - `.github/rules.md`
34
- - Template `.github/templates/feature/sdd.template.md`
34
+ - Template `.github/templates/sf-feature/sdd.template.md`
35
35
 
36
36
  ### 2. Checkpoint de aprovação
37
37
 
@@ -66,7 +66,7 @@ SDD §Área-X: popular apenas áreas tocadas (GATE=SIM); resto marca N/A.
66
66
 
67
67
  ### 5. Gerar SDD
68
68
 
69
- Usar template `.github/templates/feature/sdd.template.md`:
69
+ Usar template `.github/templates/sf-feature/sdd.template.md`:
70
70
 
71
71
  **Meta**: preencher `first_run`, `PRD empty`, `áreas tocadas`.
72
72
 
@@ -120,7 +120,7 @@ Cada serviço = 1 repo. Repos serão criados/clonados pelo `/sf-dev` (INFRA-001)
120
120
  - Organização/usuário do GitHub (ex: `empresa`)
121
121
  - Nome base do projeto (ex: `meu-projeto`)
122
122
  - Se algum repo já existe (pra clonar em vez de criar)
123
- 3. Gerar `projetos.yaml` na raiz usando template `.github/templates/feature/projetos.template.yaml`
123
+ 3. Gerar `projetos.yaml` na raiz usando template `.github/templates/sf-feature/projetos.template.yaml`
124
124
  4. Mapear áreas de task para repos:
125
125
  - BACK → api (ou worker, se separado)
126
126
  - DB → api (se usa migrations) ou repo próprio
@@ -157,14 +157,41 @@ ultima_skill: "/sf-design"
157
157
  atualizado_em: "{{ISO_DATETIME}}"
158
158
  ```
159
159
 
160
- ### 10. Publicar SDD no backend
160
+ ### 10. Publicar SDD no backend (OBRIGATÓRIO quando config existe)
161
161
 
162
- Se `sfw.config.yml` com `output.targets[]` ativo:
163
- - Executar `/sf-publish $ARGUMENTS SDD`
164
- - `/sf-publish` respeita `mode` (auto/manual/off) de cada target
165
- - Se não existe `sfw.config.yml` → pular silenciosamente
162
+ **Este passo NÃO é opcional**. Tomar decisão baseada em arquivo:
166
163
 
167
- Ver `.github/skills/sf-publish/SKILL.md`.
164
+ | Detecção | Ação |
165
+ |----------|------|
166
+ | `sfw.config.yml` NÃO existe | Pular silenciosamente. Registrar no output: "publish: skipped (no sfw.config.yml)" |
167
+ | `sfw.config.yml` existe | **Chamar `/sf-publish $ARGUMENTS SDD`** — sem condicional. Execute. |
168
+
169
+ `/sf-publish` respeita `mode` de cada target. Ver `.github/skills/sf-publish/SKILL.md`.
170
+
171
+ ### 11. Saída obrigatória
172
+
173
+ Antes de terminar, a skill DEVE reportar:
174
+
175
+ ```
176
+ /sf-design $ARGUMENTS — completo (first_run={true|false})
177
+
178
+ Artefatos locais:
179
+ - workspace/Output/$ARGUMENTS/sdd.md
180
+ - specs/$ARGUMENTS/{brief,contracts,scenarios}.md
181
+ {se first_run: + docs/*.md (5 arquivos) + projetos.yaml}
182
+
183
+ Áreas tocadas: [{lista do Meta do SDD}]
184
+
185
+ Publish:
186
+ - {target-name}: {CREATED|UPDATED|SKIPPED|CONFLICT|ERROR} — ver .ai/sf-publish-log.md
187
+ OU
188
+ - SKIPPED (no sfw.config.yml)
189
+
190
+ Próximo passo:
191
+ /sf-plan $ARGUMENTS ← gerar tasks por área
192
+ ```
193
+
194
+ Se `/sf-publish` retornou ERROR, a skill NÃO falha — artefato local está salvo.
168
195
 
169
196
  ## Notas
170
197
 
@@ -27,9 +27,9 @@ Skill atômica de extração. Lê insumos brutos de `workspace/Input/$ARGUMENTS/
27
27
  - `discovery.md` (se existir) → análise profunda prévia dos insumos
28
28
  - **`docs/` se existir** — usar como baseline pra responder checklist sem perguntar ao user
29
29
  - Templates:
30
- - `.github/templates/feature/PRD.template.md` (destino principal)
31
- - `.github/templates/feature/sf-extract-log.template.md` (append-only)
32
- - `.github/templates/feature/backlog-extraido.template.md` (condicional, ver passo 6)
30
+ - `.github/templates/sf-feature/PRD.template.md` (destino principal)
31
+ - `.github/templates/sf-feature/sf-extract-log.template.md` (append-only)
32
+ - `.github/templates/sf-feature/backlog-extraido.template.md` (condicional, ver passo 6)
33
33
 
34
34
  > Se `discovery.md` existir: usar mapa do sistema e perguntas respondidas como contexto
35
35
  > enriquecido. Resultado: menos ambiguidades, melhor estruturação.
@@ -110,7 +110,7 @@ Temas não cobertos nem por insumos nem por `docs/` viram ambiguidades:
110
110
 
111
111
  ### 5. Gerar PRD.md
112
112
 
113
- Usar template `.github/templates/feature/PRD.template.md`:
113
+ Usar template `.github/templates/sf-feature/PRD.template.md`:
114
114
 
115
115
  - Meta: preencher `empty` com resultado do 4.1
116
116
  - Se `empty: true`: só preencher Meta + adicionar nota rodapé "scope puro-técnico"
@@ -124,7 +124,7 @@ Gerar `backlog_extraido.md` **APENAS** se:
124
124
  - `first_run = true` (detectado do `.context.md`) E
125
125
  - Insumos mencionam features/funcionalidades que extrapolam o escopo atual
126
126
 
127
- Usar template `.github/templates/feature/backlog-extraido.template.md`:
127
+ Usar template `.github/templates/sf-feature/backlog-extraido.template.md`:
128
128
  - Funcionalidades fora-de-escopo organizadas em roadmap faseado
129
129
  - Cada item sugere `/sf-start <nome>` futuro
130
130
  - Máximo 4-5 fases, priorizando cadastros/fundação na fase 1
@@ -163,16 +163,42 @@ ultima_skill: "/sf-extract"
163
163
  atualizado_em: "{{ISO_DATETIME}}"
164
164
  ```
165
165
 
166
- ### 9. Publicar no backend
166
+ ### 9. Publicar PRD no backend (OBRIGATÓRIO quando config existe)
167
167
 
168
- Se `sfw.config.yml` com `output.targets[]` ativo:
169
- - Executar `/sf-publish $ARGUMENTS PRD`
170
- - `/sf-publish` respeita `mode` (auto/manual/off) de cada target
171
- - Se `empty: true`: publicar mesmo assim — Meta + rodapé já informam o estado ao humano
172
- - Se não existe `sfw.config.yml` pular silenciosamente (projeto 100% local)
168
+ **Este passo NÃO é opcional**. Tomar decisão baseada em arquivo, não em intenção:
169
+
170
+ | Detecção | Ação |
171
+ |----------|------|
172
+ | `sfw.config.yml` NÃO existe | Pular silenciosamente (projeto 100% local). Registrar no output da skill: "publish: skipped (no sfw.config.yml)" |
173
+ | `sfw.config.yml` existe | **Chamar `/sf-publish $ARGUMENTS PRD`** — sem "se", sem "talvez". Execute. |
174
+
175
+ `/sf-publish` internamente respeita `mode` de cada target (`auto`/`manual`/`off`) e lida com `empty: true` (publica com nota).
173
176
 
174
177
  Ver `.github/skills/sf-publish/SKILL.md`.
175
178
 
179
+ ### 10. Saída obrigatória
180
+
181
+ Antes de terminar, a skill DEVE reportar:
182
+
183
+ ```
184
+ /sf-extract $ARGUMENTS — completo
185
+
186
+ Artefatos locais:
187
+ - workspace/Output/$ARGUMENTS/PRD.md (empty: {true|false})
188
+ - workspace/Output/$ARGUMENTS/.extract-log.md
189
+ - workspace/Output/$ARGUMENTS/backlog_extraido.md (se aplicável)
190
+
191
+ Publish:
192
+ - {target-name}: {CREATED|UPDATED|SKIPPED|CONFLICT|ERROR} — ver .ai/sf-publish-log.md
193
+ OU
194
+ - SKIPPED (no sfw.config.yml) — projeto 100% local
195
+
196
+ Próximo passo:
197
+ /sf-design $ARGUMENTS ← após revisar PRD e responder ambiguidades §14
198
+ ```
199
+
200
+ Se `/sf-publish` retornou ERROR, a skill NÃO falha — apenas reporta no output pro user decidir. Artefato local está salvo.
201
+
176
202
  ## Re-extração
177
203
 
178
204
  - Merge ADITIVO com PRD existente (nunca remove info de inalterados)
@@ -1,6 +1,6 @@
1
1
  # /sf-mcp <provider>
2
2
 
3
- Setup interativo de backend externo. Pergunta os dados necessários, descobre a estrutura do projeto e cria todos os arquivos de configuração.
3
+ Setup interativo de backend externo. Idempotente pode rodar múltiplas vezes, pergunta o que falta.
4
4
 
5
5
  ## Providers disponíveis
6
6
 
@@ -11,57 +11,96 @@ Setup interativo de backend externo. Pergunta os dados necessários, descobre a
11
11
  ## Uso
12
12
 
13
13
  ```
14
- /sf-mcp confluence
15
- /sf-mcp confluence test ← só testa conexão
14
+ /sf-mcp confluence ← setup ou reconfiguração (idempotente)
15
+ /sf-mcp confluence test ← só testa conexão
16
16
  ```
17
17
 
18
18
  ---
19
19
 
20
20
  ## Provider: Confluence
21
21
 
22
- ### Passo 1 — Verificar pré-requisitos
22
+ ### Passo 1 — Detectar estado atual
23
+
24
+ Ler os 2 arquivos âncora:
25
+
26
+ | Arquivo | O que extrair | Se ausente |
27
+ |---------|---------------|------------|
28
+ | `sfw.config.yml` | `project.root_page_id`, `project.name`, credenciais do space (`space_key`) | marcar como "falta config" |
29
+ | `.mcp.json` | entry `mcpServers.atlassian` com `CONFLUENCE_URL`, `CONFLUENCE_USERNAME`, `CONFLUENCE_API_TOKEN` | marcar como "falta credenciais" |
30
+
31
+ Calcular `state`:
32
+ - **COMPLETO** — `sfw.config.yml` tem `root_page_id` E `.mcp.json` tem credenciais → ir pro Passo 2
33
+ - **INCOMPLETO** — algo falta → ir pro Passo 3
34
+
35
+ ### Passo 2 — Estado COMPLETO: validar conexão
36
+
37
+ Testar:
38
+ ```
39
+ mcp__atlassian__confluence_get_page(page_id={root_page_id})
40
+ ```
41
+
42
+ | Resultado | Ação |
43
+ |-----------|------|
44
+ | 200 OK | → Passo 4 (remapear árvore, reconfirmar Input/Output) |
45
+ | 401 Unauthorized | Credencial expirou. Perguntar novo token, atualizar `.mcp.json`, avisar pra reiniciar Claude Code, PARAR |
46
+ | 404 Not Found | `root_page_id` inválido. Perguntar novo ID, atualizar `sfw.config.yml`, retry teste |
47
+ | MCP não responde | `.mcp.json` foi atualizado mas Claude não recarregou. Avisar pra reiniciar Claude Code, PARAR |
48
+ | Network error | Mostrar erro, instruir troubleshooting (`.github/adapters/SETUP.md`) |
49
+
50
+ ### Passo 3 — Estado INCOMPLETO: coletar o que falta
51
+
52
+ #### 3.1 Verificar `uvx`
23
53
 
24
- Verificar se `uvx` está instalado:
25
54
  ```bash
26
55
  uvx --version
27
56
  ```
28
57
 
29
- Se NÃO está instalado:
58
+ Se não instalado:
30
59
  ```
31
60
  uvx não encontrado. Instale com:
32
61
  pip install uv
33
62
 
34
63
  Depois rode /sf-mcp confluence novamente.
35
64
  ```
36
- **Parar aqui** se uvx não estiver disponível.
37
-
38
- ### Passo 2 — Coletar credenciais
65
+ **PARAR**.
39
66
 
40
- Perguntar uma por uma:
67
+ #### 3.2 Se FALTA credenciais (`.mcp.json` ausente ou incompleto)
41
68
 
69
+ Perguntar uma por uma. Pra cada item, mostrar ao user exatamente ONDE achar:
42
70
  ```
43
- Configurando Confluence para o SFW.
71
+ Configurando acesso ao Confluence.
44
72
 
45
- 1. URL do Confluence (ex: https://sua-empresa.atlassian.net/wiki):
73
+ 1. URL do Confluence
74
+ Abra o Confluence no browser. A URL base é algo como:
75
+ https://sua-empresa.atlassian.net/wiki
76
+ Cole essa URL (com /wiki no final):
46
77
  >
47
78
 
48
- 2. Email da conta Atlassian (ex: dev@empresa.com):
79
+ 2. Email da conta Atlassian
80
+ É o email que você usa pra logar no Atlassian (não é o token).
49
81
  >
50
82
 
51
- 3. API Token (gere em https://id.atlassian.com/manage-profile/security/api-tokens):
83
+ 3. API Token
84
+ Token é diferente de senha. Gere um novo:
85
+ a) Abra https://id.atlassian.com/manage-profile/security/api-tokens
86
+ b) Clique "Create API token"
87
+ c) Dê um nome (ex: "sfw-mcp")
88
+ d) Copie o token que aparece — ele só aparece UMA VEZ
89
+ Cole aqui:
52
90
  >
53
91
 
54
- 4. Space Key (as letras na URL: /wiki/spaces/XX/...):
92
+ 4. Space Key
93
+ É o código CURTO do seu espaço Confluence (geralmente 2-4 letras maiúsculas).
94
+ Abra qualquer page do seu espaço. Na URL, você verá:
95
+ https://...atlassian.net/wiki/spaces/XXX/pages/...
96
+ ^^^
97
+ esse é o Space Key
98
+ Exemplos comuns: "ST", "DEV", "PROJ", "ENG"
99
+ Qual é o seu?:
55
100
  >
56
101
  ```
57
102
 
58
- ### Passo 3 — Criar `.mcp.json`
59
-
60
- Verificar se `.mcp.json` já existe:
61
- - Se existe e já tem entrada `atlassian` → perguntar se quer atualizar
62
- - Se existe sem `atlassian` → adicionar entrada
63
- - Se não existe → criar
64
-
103
+ Criar/atualizar `.mcp.json`:
65
104
  ```json
66
105
  {
67
106
  "mcpServers": {
@@ -78,95 +117,115 @@ Verificar se `.mcp.json` já existe:
78
117
  }
79
118
  ```
80
119
 
81
- **IMPORTANTE**: Credenciais hardcoded — `${VAR}` NÃO funciona no Claude Code.
82
-
83
- ### Passo 4 — Testar conexão e descobrir projeto
120
+ **IMPORTANTE**: credenciais hardcoded — `${VAR}` NÃO funciona no Claude Code.
84
121
 
85
- Testar chamando:
122
+ Se `.mcp.json` acabou de ser criado/atualizado:
86
123
  ```
87
- mcp__atlassian__confluence_search(query="space.key={space_key}", limit=5)
124
+ .mcp.json pronto. Preciso que você reinicie o Claude Code para o MCP carregar.
125
+
126
+ 1. Feche o Claude Code
127
+ 2. Abra novamente na mesma pasta
128
+ 3. Rode /sf-mcp confluence — vou continuar de onde paramos (credenciais já salvas,
129
+ só vou pedir o que ainda falta)
88
130
  ```
89
- ou
131
+ **PARAR**.
132
+
133
+ #### 3.3 Se FALTA root_page_id (credenciais OK mas config sem root)
134
+
135
+ Testar conexão básica primeiro:
90
136
  ```
91
- mcp__atlassian__confluence_get_page_children(page_id=<root do space>)
137
+ mcp__atlassian__confluence_search(query="space.key={space_key}", limit=1)
92
138
  ```
93
139
 
94
- **Se MCP não disponível** (primeira vez `.mcp.json` acabou de ser criado):
95
- ```
96
- .mcp.json criado. O Claude Code precisa ser reiniciado para carregar o MCP.
140
+ Se falha Passo 2 error table (401/MCP não responde/etc).
141
+ Se OK:
97
142
 
98
- 1. Reinicie o Claude Code (feche e abra)
99
- 2. Rode /sf-mcp confluence novamente — vou continuar de onde paramos
100
143
  ```
101
- **Parar aqui.**
144
+ Conexão OK.
102
145
 
103
- **Se MCP funcionar** pedir o projeto:
146
+ Qual é a page RAIZ do seu projeto no Confluence?
147
+ (A page-mãe que contém TUDO do projeto — geralmente tem Input e Output como filhas.)
104
148
 
105
- ```
106
- Conexão OK!
149
+ Duas formas de informar:
107
150
 
108
- 5. Qual é a page raiz do seu projeto no Confluence?
109
- Cole o Page ID (número na URL) ou o título exato:
110
- >
151
+ A) Page ID (recomendado mais confiável):
152
+ Abra a page raiz no Confluence. A URL mostra:
153
+ https://...atlassian.net/wiki/spaces/ST/pages/65708/Nome-da-Page
154
+ ^^^^^
155
+ esse número é o Page ID
156
+ Cole só o número (ex: 65708).
157
+
158
+ B) Título exato:
159
+ O título que aparece no topo da page. Tem que bater EXATAMENTE
160
+ (incluindo acentos e maiúsculas/minúsculas).
161
+
162
+ Page ID ou título:
163
+ >
111
164
  ```
112
165
 
113
- ### Passo 5 — Mapear a árvore do projeto
166
+ Validar:
167
+ ```
168
+ mcp__atlassian__confluence_get_page(page_id={resposta})
169
+ ```
170
+ - Se 404 e user colou título → usar `confluence_search` pra achar
171
+ - Se 404 e user colou ID → pedir de novo
172
+ - Se OK → seguir
114
173
 
115
- Após receber o Page ID ou título da raiz:
174
+ ### Passo 4 Mapear árvore do projeto
116
175
 
117
- 1. Chamar `mcp__atlassian__confluence_get_page` pra confirmar que existe
118
- 2. Chamar `mcp__atlassian__confluence_get_page_children` na raiz
119
- 3. Chamar recursivamente nos filhos pra mapear a árvore completa
176
+ Chamar recursivamente:
177
+ ```
178
+ mcp__atlassian__confluence_get_page_children(page_id={root_page_id})
179
+ → pra cada filho, chamar get_page_children até bater em folha
180
+ ```
120
181
 
121
182
  Mostrar ao usuário:
122
-
123
183
  ```
124
- Projeto: "Barbearia Digital" (page_id: 65708)
184
+ Projeto: "Barbearia Digital" (root_page_id: 65708)
125
185
 
126
186
  Estrutura encontrada:
127
- ├── Requisitos (page_id: 360668)
128
- │ ├── App mobile (page_id: 294950)
129
- │ └── Painel admin (page_id: 131084)
130
- ├── Documentação técnica (page_id: 294931)
131
- ├── Referências (page_id: 557057)
132
- └── Decisões (page_id: 425998)
187
+ ├── Requisitos (360668)
188
+ │ ├── App mobile (294950)
189
+ │ └── Painel admin (131084)
190
+ ├── Documentação técnica (294931)
191
+ ├── Referências (557057)
192
+ └── Decisões (425998)
133
193
  ```
134
194
 
135
- ### Passo 6 — Identificar Input e Output
195
+ ### Passo 5 — Identificar Input e Output
136
196
 
137
- Perguntar ao usuário:
197
+ **Se existe config com Input/Output**: mostrar o que está salvo + opção de mudar:
198
+ ```
199
+ Config atual:
200
+ Input: Requisitos (360668)
201
+ Output: Documentação técnica (294931)
138
202
 
203
+ Manter? (s/n)
139
204
  ```
140
- Preciso saber qual pasta contém os INSUMOS (Input) e onde devo PUBLICAR os artefatos (Output).
141
205
 
142
- Qual dessas é o Input (onde estão os insumos do PM/PO)?
206
+ Se `s` pular pro Passo 7.
207
+ Se `n` → continuar perguntando (como se fosse setup novo).
208
+
209
+ **Se é setup novo**:
210
+ ```
211
+ Qual dessas pages contém os INSUMOS (Input, onde PM/PO publica)?
143
212
  1. Requisitos (360668)
144
213
  2. Documentação técnica (294931)
145
214
  3. Referências (557057)
146
215
  4. Decisões (425998)
147
- 5. Criar nova page "Input"
216
+ 5. Criar nova page "Input" (filha da raiz)
148
217
  >
149
218
  ```
150
219
 
151
- Após o user escolher Input:
220
+ Após escolher Input, perguntar Output com as pages restantes + opção "Criar nova page 'Output'".
152
221
 
153
- ```
154
- Qual dessas é o Output (onde publico PRD, SDD, Progresso)?
155
- 1. Documentação técnica (294931)
156
- 2. Referências (557057)
157
- 3. Decisões (425998)
158
- 4. Criar nova page "Output"
159
- >
160
- ```
161
-
162
- **Se o user escolher "Criar nova"** → usar `mcp__atlassian__confluence_create_page` como filha da raiz.
163
-
164
- ### Passo 7 — Sugerir mapeamento de páginas úteis (opcional)
222
+ Se escolher "Criar nova" → `mcp__atlassian__confluence_create_page` como filha da raiz.
165
223
 
166
- Se a árvore tem outras pages relevantes, sugerir:
224
+ ### Passo 6 Sugerir context_pages (opcional)
167
225
 
226
+ Pages da árvore que não viraram Input nem Output:
168
227
  ```
169
- Encontrei outras páginas que podem ser úteis durante o desenvolvimento:
228
+ Encontrei outras pages que podem ser úteis durante o desenvolvimento:
170
229
 
171
230
  - "Referências" (557057) → posso consultar durante /sf-extract e /sf-design
172
231
  - "Decisões" (425998) → posso consultar para ADRs no /sf-design
@@ -174,9 +233,11 @@ Encontrei outras páginas que podem ser úteis durante o desenvolvimento:
174
233
  Quer que eu mapeie essas páginas como contexto adicional? (s/n)
175
234
  ```
176
235
 
177
- Se sim, registrar no `sfw.config.yml` como `context_pages`.
236
+ Se sim, incluir em `context_pages[]` no `sfw.config.yml`.
178
237
 
179
- ### Passo 8Criar `sfw.config.yml`
238
+ ### Passo 7Escrever `sfw.config.yml`
239
+
240
+ Preservar seções existentes (naming, etc) se já havia arquivo. Atualizar/criar:
180
241
 
181
242
  ```yaml
182
243
  project:
@@ -191,12 +252,12 @@ input:
191
252
  adapter: confluence
192
253
  config:
193
254
  space_key: "{space_key}"
194
- parent_page_id: "{page_id escolhido como Input}"
255
+ parent_page_id: "{page_id do Input}"
195
256
  recursive: true
196
257
  include_attachments: true
197
258
  cache:
198
259
  local_dir: "workspace/Input/"
199
- log: ".ai/load-log.md"
260
+ log: ".ai/sf-load-log.md"
200
261
  incremental: true
201
262
 
202
263
  output:
@@ -205,44 +266,41 @@ output:
205
266
  adapter: confluence
206
267
  config:
207
268
  space_key: "{space_key}"
208
- parent_page_id: "{page_id escolhido como Output}"
209
- publishes: [PRD, PRD, SDD, Progresso]
269
+ parent_page_id: "{page_id do Output}"
270
+ publishes: [PRD, SDD, Progresso]
210
271
  mode: auto
211
272
  conflict_detection: version
212
273
  approval_mechanism: label
213
274
  approval_label: "sfw-approved"
214
275
 
215
- # Pages de contexto adicional (consultadas pelo /sf-extract e /sf-design)
276
+ # Descomente se tiver selecionado context_pages no Passo 6
216
277
  # context_pages:
217
278
  # - id: "557057"
218
279
  # title: "Referências"
219
280
  # use_in: [extract, design]
220
- # - id: "425998"
221
- # title: "Decisões"
222
- # use_in: [design]
223
281
  ```
224
282
 
225
- ### Passo 9 — Ajustar `.gitignore`
283
+ ### Passo 8 — Ajustar `.gitignore`
226
284
 
227
- Adicionar se não existem:
228
- - `.mcp.json`
229
- - Bloco workspace ignored:
230
- ```
231
- # SFW: workspace ignored (external backend detected)
232
- workspace/Output/**
233
- !workspace/Output/.gitkeep
234
- ```
285
+ Adicionar se não existe:
286
+ ```
287
+ .mcp.json
235
288
 
236
- ### Passo 10 Resumir
289
+ # SFW: workspace ignored (external backend detected)
290
+ workspace/Output/**
291
+ !workspace/Output/.gitkeep
292
+ ```
293
+
294
+ ### Passo 9 — Resumir
237
295
 
238
296
  ```
239
297
  Confluence configurado!
240
298
 
241
- Projeto: {nome} ({page_id raiz})
299
+ Projeto: {nome} ({root_page_id})
242
300
  Input: {título Input} ({page_id})
243
301
  Output: {título Output} ({page_id})
244
302
 
245
- Arquivos criados/atualizados:
303
+ Arquivos:
246
304
  .mcp.json ← credenciais (gitignored)
247
305
  sfw.config.yml ← configuração do projeto
248
306
  .gitignore ← atualizado
@@ -251,42 +309,50 @@ O projeto tem {N} scopes no Input:
251
309
  - {lista dos filhos do Input}
252
310
 
253
311
  Próximo passo:
254
- /sf-start <nome-do-scope> ← bootstrap técnico
255
- /sf-feature <nome-do-scope> ← nova feature
312
+ /sf-start <nome-do-scope>
256
313
  ```
257
314
 
258
315
  ---
259
316
 
260
317
  ## Subcomando: `/sf-mcp confluence test`
261
318
 
262
- Apenas testa a conexão sem criar/modificar arquivos:
263
-
264
- 1. Verificar que `.mcp.json` existe
265
- 2. Verificar que `sfw.config.yml` existe e tem `adapter: confluence`
266
- 3. Chamar `mcp__atlassian__confluence_get_page_children(page_id={input.parent_page_id})`
267
- 4. Se OK"Conexão OK! {N} scopes encontrados em Input: {lista}"
268
- 5. Se falha → orientar troubleshooting (ver `.github/adapters/SETUP.md`)
319
+ Apenas testa sem modificar arquivos:
320
+
321
+ 1. Verificar que `sfw.config.yml` existe com `project.root_page_id` e `input.config.parent_page_id`
322
+ 2. Verificar que `.mcp.json` existe com credenciais
323
+ 3. Testar `confluence_get_page(root_page_id)` → root acessível?
324
+ 4. Testar `confluence_get_page_children(input.config.parent_page_id)`listar scopes
325
+ 5. Reportar:
326
+ ```
327
+ Conexão OK!
328
+ Root: "{nome}" ({root_page_id})
329
+ Input: {N} scopes encontrados
330
+ Output: {M} artefatos publicados anteriormente
331
+ ```
332
+ 6. Se falha: mostrar qual check falhou + link pro troubleshooting
269
333
 
270
334
  ---
271
335
 
272
336
  ## Notas
273
337
 
338
+ - **`/sf-mcp confluence` é idempotente** — pode rodar N vezes. Só pergunta o que falta baseado em `sfw.config.yml` + `.mcp.json`
339
+ - **`root_page_id` é âncora** — sem ele o framework não sabe os limites do projeto no space
274
340
  - `.mcp.json` é SEMPRE gitignored — contém credenciais
275
341
  - `sfw.config.yml` é commitável — zero segredos
276
- - Após criar `.mcp.json`, Claude Code PRECISA ser reiniciado
342
+ - Após criar/atualizar `.mcp.json`, Claude Code PRECISA ser reiniciado
277
343
  - O framework conhece o projeto INTEIRO (raiz + toda a árvore), não só Input/Output
278
- - `context_pages` permite que /sf-extract e /sf-design consultem páginas extras como referência
279
- - Token Atlassian pode expirar — se der 401, gerar novo e atualizar `.mcp.json`
344
+ - Token Atlassian pode expirar se der 401, skill pede novo e atualiza `.mcp.json`
280
345
 
281
346
  ## Erros
282
347
 
283
348
  | Erro | Ação |
284
349
  |------|------|
285
350
  | uvx não instalado | Parar, instruir instalação |
286
- | MCP não disponível | Pedir reinício do Claude Code |
287
- | Page raiz não encontrada | Pedir ID/título correto |
288
- | Sem permissão de escrita | Informar, pedir ao admin |
289
- | Space key errado | Listar spaces disponíveis se possível |
351
+ | MCP não responde após `.mcp.json` novo | Pedir reinício, retomar depois |
352
+ | `root_page_id` 404 | Pedir ID/título correto, validar |
353
+ | Token expirado (401) | Pedir novo token, atualizar .mcp.json, pedir reinício |
354
+ | Sem permissão de escrita no space | Informar, pedir ao admin |
355
+ | Space key inválido | Listar spaces disponíveis se possível |
290
356
 
291
357
  ## Referências
292
358
 
@@ -20,8 +20,8 @@ Metódico e exaustivo. Cada task auto-contida. Prioriza ordem correta.
20
20
  ### 1. Ler contexto
21
21
  - `workspace/Output/{nome}/sdd.md` completo (fonte humana)
22
22
  - `specs/{nome}/contracts.md` e `scenarios.md` (projeções já geradas pelo /sf-design)
23
- - `projetos.yaml` + `docs/` (architecture, domain, conventions) + `.claude/rules.md`
24
- - Template `.claude/templates/specs/tasks.template.md`
23
+ - `projetos.yaml` + `docs/` (architecture, domain, conventions) + `.github/rules.md`
24
+ - Template `.github/templates/specs/tasks.template.md`
25
25
 
26
26
  ### 2. Identificar fases de entrega
27
27
  Ler PRD §11 (Fases de Entrega) — cada fase vira um agrupamento de tasks:
@@ -88,15 +88,39 @@ status: "plan_done"
88
88
  ultima_skill: "/sf-plan"
89
89
  ```
90
90
 
91
- ### 7. Publicar Progresso no(s) backend(s)
91
+ ### 7. Publicar Progresso no backend (OBRIGATÓRIO quando config existe)
92
92
 
93
- Se existe `sfw.config.yml` com `output.targets[]` ativo:
94
- - Executar `/sf-publish $ARGUMENTS Progresso`
95
- - O `/sf-publish` respeita o `mode` (auto/manual/off) de cada target
96
- - Se não existe `sfw.config.yml` → pular silenciosamente
97
- - **Nota**: `tasks.md`, `specs/`, `docs/`, `projetos.yaml` são LOCAL ONLY — nunca publicados
93
+ **Este passo NÃO é opcional**. Tomar decisão baseada em arquivo:
98
94
 
99
- Ver `.github/skills/sf-publish.md`.
95
+ | Detecção | Ação |
96
+ |----------|------|
97
+ | `sfw.config.yml` NÃO existe | Pular silenciosamente. Registrar: "publish: skipped (no sfw.config.yml)" |
98
+ | `sfw.config.yml` existe | **Chamar `/sf-publish $ARGUMENTS Progresso`** — sem condicional. Execute. |
99
+
100
+ `/sf-publish` respeita `mode` de cada target. Ver `.github/skills/sf-publish/SKILL.md`.
101
+
102
+ **Nota**: `tasks.md`, `specs/`, `docs/`, `projetos.yaml` são LOCAL ONLY — `/sf-publish` nunca toca neles.
103
+
104
+ ### 8. Saída obrigatória
105
+
106
+ Antes de terminar, a skill DEVE reportar:
107
+
108
+ ```
109
+ /sf-plan $ARGUMENTS — completo
110
+
111
+ Artefatos locais:
112
+ - specs/$ARGUMENTS/tasks.md ({N} tasks em {F} fases, áreas: [{lista}])
113
+ - workspace/Output/$ARGUMENTS/Progresso.md
114
+
115
+ Publish:
116
+ - {target-name}: {CREATED|UPDATED|SKIPPED|CONFLICT|ERROR} — ver .ai/sf-publish-log.md
117
+ OU
118
+ - SKIPPED (no sfw.config.yml)
119
+
120
+ Próximo passo:
121
+ /sf-dev $ARGUMENTS ← implementa tudo
122
+ /sf-dev $ARGUMENTS --fase 1 ← só fase 1
123
+ ```
100
124
 
101
125
  ## Saídas
102
126
  - `specs/{nome}/tasks.md` — tabela única