jarvis-ai-framework 8.1.0 → 8.2.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/README.md +3 -1
- package/agents/engineering/eng.agent.md +13 -11
- package/agents/engineering/eng.dev-code-reviewer.md +19 -4
- package/agents/engineering/eng.docs-writer.md +17 -2
- package/agents/engineering/qa/eng.qa.test-planner.md +20 -5
- package/agents/product/prod.pm-checker.md +16 -1
- package/bin/README.md +1 -1
- package/bin/commands/init.js +166 -31
- package/bin/lib/cli/program.js +4 -4
- package/bin/lib/core/sync-engine.js +7 -3
- package/package.json +2 -2
- package/rules-on-demand/engineering/eng.plan-rules.md +2 -0
- package/rules-on-demand/engineering/eng.pre-pr-rules.md +8 -3
- package/rules-on-demand/engineering/eng.start-rules.md +7 -5
- package/rules-on-demand/engineering/eng.transitions-rules.md +4 -3
- package/skills/SKILLS-ROADMAP.md +2 -2
- package/skills/jarvis-docs-central/SKILL.md +1 -1
- package/skills/jarvis-evolution-architect/references/exemplos.md +3 -3
- package/skills/jarvis-init/SKILL.md +71 -23
- package/skills/product-specs-update/SKILL.md +138 -121
- package/templates/ENV-template.md +57 -19
- package/templates/engineering/architecture-template.md +14 -1
- package/templates/engineering/plan-template.md +2 -0
- package/workflows/engineering/eng.plan.md +8 -5
- package/workflows/engineering/eng.pre-pr.md +84 -18
- package/workflows/engineering/eng.spec-consolidate.md +1 -1
- package/workflows/engineering/eng.start.md +13 -1
package/README.md
CHANGED
|
@@ -100,7 +100,9 @@ npm install -g jarvis-ai-framework@latest
|
|
|
100
100
|
jarvis init --upgrade --ide {ide} # assets + variáveis novas do ENV.md + documentos para as pastas novas
|
|
101
101
|
```
|
|
102
102
|
|
|
103
|
-
|
|
103
|
+
`jarvis init --ide {ide}` numa pasta já instalada mostra o menu **Atualizar** (Enter, o mesmo que o `--upgrade`) / **Reinstalar** (o mesmo que o `--force`) / **Cancelar**, com a versão instalada e a do pacote. No fim, ele só manda rodar o `/jarvis-init upgrade` quando há pendência.
|
|
104
|
+
|
|
105
|
+
Na IDE, o `/jarvis-init upgrade` vai direto ao Upgrade (C), cuida do que precisa de conversa (Central docs antigo e o passo das stacks) e, no fim, valida o `ENV.md` inteiro: pergunta cada problema e regrava o arquivo separado por assunto, na ordem do template. O `--upgrade` só **acrescenta** chaves ao `ENV.md`, no fim do arquivo: nenhuma chave existente muda. Ele mostra os documentos que estão em caminhos antigos e pergunta antes de movê-los (`--yes` move sem perguntar; sem terminal interativo, não move). Também lista os skills instalados que saíram do framework e pergunta antes de removê-los (`--remove-stale` remove sem perguntar só os listados; skills registrados em `*_SPECIALIZATIONS` nunca são listados).
|
|
104
106
|
|
|
105
107
|
**Instalou via clone local** (fluxo de [Desenvolvendo o Jarvis localmente](#desenvolvendo-o-jarvis-localmente)) — quando o repo no GitHub ganhar commits novos, sincronize assim:
|
|
106
108
|
|
|
@@ -175,20 +175,26 @@ Para detecção automática de contexto de tarefas:
|
|
|
175
175
|
- Uso: `/jarvis-context-detect [jira-key]` ou `/jarvis-context-detect --override tipo=hotfix`
|
|
176
176
|
- Chamado automaticamente pelo workflow `eng.start`
|
|
177
177
|
|
|
178
|
-
### eng-platform
|
|
179
|
-
Quando a tarefa envolver
|
|
178
|
+
### eng-platform
|
|
179
|
+
Quando a tarefa envolver infraestrutura, performance ou segurança de infraestrutura — base de platform, complementada pela especialização registrada em `PLATFORM_SPECIALIZATIONS`:
|
|
180
180
|
- Arquivo: `$IDE/skills/eng-platform/SKILL.md`
|
|
181
|
+
- Performance: análise ou otimização de performance, observabilidade, gargalos, latência, load testing, chaos engineering ou cache multi-camada (temas 7, 14, 15 e 16)
|
|
182
|
+
- Segurança: segurança de infraestrutura, fundamentos de segurança da informação (risco, ameaças, identidade, resposta a incidente, GRC, privacidade) ou auditoria de dependências/supply chain (temas 9 e 13)
|
|
183
|
+
- Segurança de código de aplicação (OWASP, inputs, auth) já é padrão embutido em `eng-backend`/`eng-frontend`
|
|
181
184
|
|
|
182
185
|
### eng-ai
|
|
183
186
|
Quando a tarefa envolver features com LLM, sistemas RAG, agentes de IA, chatbots, embeddings, busca vetorial ou integrações com modelos de IA:
|
|
184
187
|
- Arquivo: `$IDE/skills/eng-ai/SKILL.md`
|
|
185
188
|
|
|
186
|
-
###
|
|
187
|
-
Quando a tarefa envolver
|
|
188
|
-
-
|
|
189
|
-
- Frontend: `$IDE/skills/eng-frontend/SKILL.md` + itens de `FRONTEND_SPECIALIZATIONS`
|
|
189
|
+
### eng-backend
|
|
190
|
+
Quando a tarefa envolver backend (APIs, autenticação, workers e jobs assíncronos, filas e mensageria, integrações externas, cache, banco de dados). Não escolha o skill por nome: aplique a regra `$IDE/rules/engineering/eng.specializations-rules.md` para a área backend, que carrega o skill base e as especializações de `BACKEND_SPECIALIZATIONS` do `ENV.md`:
|
|
191
|
+
- Arquivo: `$IDE/skills/eng-backend/SKILL.md`
|
|
190
192
|
- Workflows relacionados: `eng.start` (arquitetura), `eng.work` (implementação), `eng.debug` (troubleshooting)
|
|
191
|
-
|
|
193
|
+
|
|
194
|
+
### eng-frontend
|
|
195
|
+
Quando a tarefa envolver frontend (componentes, estado, estilos, performance de UI, acessibilidade, testes de interface). Não escolha o skill por nome: aplique a regra `$IDE/rules/engineering/eng.specializations-rules.md` para a área frontend, que carrega o skill base e as especializações de `FRONTEND_SPECIALIZATIONS` do `ENV.md`:
|
|
196
|
+
- Arquivo: `$IDE/skills/eng-frontend/SKILL.md`
|
|
197
|
+
- Para ver o que está instalado e registrado (backend e frontend): `/jarvis-list-specializations`
|
|
192
198
|
|
|
193
199
|
### eng-automation
|
|
194
200
|
Quando a tarefa envolver web scraping, extração de dados de páginas web, automação de browser com Puppeteer, parsing de HTML/XML/PDF, pipelines ETL leves ou monitoramento de mudanças em sites:
|
|
@@ -200,10 +206,6 @@ Quando precisar planejar estratégia de testes, validar fluxos completos de usu
|
|
|
200
206
|
- Arquivo: `$IDE/skills/eng-qa/SKILL.md`
|
|
201
207
|
- Workflows relacionados: `eng.pr` (validação pré-PR), `eng.pre-pr` (cobertura de testes E2E)
|
|
202
208
|
|
|
203
|
-
### eng-platform
|
|
204
|
-
Quando a tarefa envolver segurança de infraestrutura, fundamentos de segurança da informação (risco, ameaças, identidade, resposta a incidente, GRC, privacidade) ou auditoria de dependências/supply chain — base de platform, complementada pela especialização registrada em `PLATFORM_SPECIALIZATIONS`:
|
|
205
|
-
- Arquivo: `$IDE/skills/eng-platform/SKILL.md` (temas 9 e 13)
|
|
206
|
-
- Segurança de código de aplicação (OWASP, inputs, auth) já é padrão embutido em `eng-backend`/`eng-frontend`
|
|
207
209
|
|
|
208
210
|
---
|
|
209
211
|
|
|
@@ -6,18 +6,18 @@ model: opus
|
|
|
6
6
|
color: green
|
|
7
7
|
---
|
|
8
8
|
|
|
9
|
-
# code-
|
|
9
|
+
# code-reviewer
|
|
10
10
|
Você é um especialista em revisão de código responsável por analisar mudanças de código em preparação para a abertura de um Pull Request.
|
|
11
11
|
Seu objetivo é fornecer feedback abrangente e acionável, ajudando a garantir qualidade de código e prontidão para PR.
|
|
12
12
|
|
|
13
13
|
Processo de Revisão
|
|
14
14
|
1. Coleta de Informações sobre as Mudanças
|
|
15
|
-
Primeiro, entenda exatamente o que foi alterado:
|
|
15
|
+
Primeiro, entenda exatamente o que foi alterado (`{BRANCH_BASE}` é a branch base recebida de quem chama (o `/eng.pre-pr` passa a `Branch base:` do `architecture.md`); sem ela, `origin/main`.):
|
|
16
16
|
- Execute git status para verificar mudanças não commitadas
|
|
17
17
|
- Execute git diff para visualizar mudanças não staged
|
|
18
18
|
- Execute git diff --staged para visualizar mudanças staged
|
|
19
|
-
- Execute git log
|
|
20
|
-
- Execute git diff
|
|
19
|
+
- Execute git log {BRANCH_BASE}..HEAD --oneline para ver os commits da branch atual
|
|
20
|
+
- Execute git diff {BRANCH_BASE}...HEAD para ver todas as mudanças comparadas com a branch base
|
|
21
21
|
|
|
22
22
|
2. Análise das Mudanças de Código
|
|
23
23
|
Para cada arquivo alterado, avalie:
|
|
@@ -71,6 +71,21 @@ Avalie os testes:
|
|
|
71
71
|
|
|
72
72
|
Nenhuma — agente autocontido, não depende de skill
|
|
73
73
|
|
|
74
|
+
## Quando chamado pelo `/eng.pre-pr`
|
|
75
|
+
|
|
76
|
+
O `/eng.pre-pr` passa a branch base (a `Branch base:` do `architecture.md`) e, da rodada 2 em diante, o diff incremental desde a rodada anterior. Use essa base no lugar de `origin/main` nos comandos de diff e log. Só aponte: não edite nem grave arquivos.
|
|
77
|
+
|
|
78
|
+
Devolva uma lista de lacunas, uma por item, com os campos da tabela de lacunas do `gate-checklist.md`:
|
|
79
|
+
|
|
80
|
+
- **Lacuna**: o que falta ou está errado, terminando com "(item 2)", o número deste gate na lista do `/eng.pre-pr`.
|
|
81
|
+
- **Onde**: `arquivo:linha` com o trecho, ou o comando que a revelou e o resultado.
|
|
82
|
+
- **Por que importa**: o impacto, em linguagem simples.
|
|
83
|
+
- **Refutação**: o que derrubaria esta lacuna, com o lugar a conferir.
|
|
84
|
+
- **Sugestão**: como resolver.
|
|
85
|
+
- **Severidade**: 🔴 Bloqueador, 🟡 Importante ou ⚪ Menor (redação é ⚪).
|
|
86
|
+
|
|
87
|
+
Lista vazia é uma resposta válida. Fora do `/eng.pre-pr`, vale o formato de resposta deste arquivo.
|
|
88
|
+
|
|
74
89
|
## Formato da Resposta
|
|
75
90
|
Forneça uma revisão estruturada no seguinte formato:
|
|
76
91
|
|
|
@@ -17,6 +17,21 @@ Fonte de verdade do processo e do formato de entrega da documentação:
|
|
|
17
17
|
|
|
18
18
|
---
|
|
19
19
|
|
|
20
|
+
## Quando chamado pelo `/eng.pre-pr`
|
|
21
|
+
|
|
22
|
+
O `/eng.pre-pr` passa a branch base (a `Branch base:` do `architecture.md`) e, da rodada 2 em diante, o diff incremental desde a rodada anterior. Use essa base no lugar de `origin/main` nos comandos de diff e log. Só aponte: não edite nem grave arquivos. Não proponha aplicar as atualizações nem pergunte se deve aplicá-las: cada documentação desatualizada vira uma lacuna.
|
|
23
|
+
|
|
24
|
+
Devolva uma lista de lacunas, uma por item, com os campos da tabela de lacunas do `gate-checklist.md`:
|
|
25
|
+
|
|
26
|
+
- **Lacuna**: o que falta ou está errado, terminando com "(item 9)", o número deste gate na lista do `/eng.pre-pr`.
|
|
27
|
+
- **Onde**: `arquivo:linha` com o trecho, ou o comando que a revelou e o resultado.
|
|
28
|
+
- **Por que importa**: o impacto, em linguagem simples.
|
|
29
|
+
- **Refutação**: o que derrubaria esta lacuna, com o lugar a conferir.
|
|
30
|
+
- **Sugestão**: como resolver.
|
|
31
|
+
- **Severidade**: 🔴 Bloqueador, 🟡 Importante ou ⚪ Menor (redação é ⚪).
|
|
32
|
+
|
|
33
|
+
Lista vazia é uma resposta válida. Fora do `/eng.pre-pr`, vale o formato de resposta deste arquivo.
|
|
34
|
+
|
|
20
35
|
## Fluxo de Trabalho
|
|
21
36
|
|
|
22
37
|
### 1. Analisar Mudanças de Código
|
|
@@ -26,8 +41,8 @@ Comece entendendo exatamente o que mudou:
|
|
|
26
41
|
- Execute `git status` para verificar mudanças não commitadas
|
|
27
42
|
- Execute `git diff` para visualizar mudanças não staged
|
|
28
43
|
- Execute `git diff --staged` para visualizar mudanças staged
|
|
29
|
-
- Execute `git log
|
|
30
|
-
- Execute `git diff
|
|
44
|
+
- Execute `git log {BRANCH_BASE}..HEAD --oneline` para ver os commits da branch
|
|
45
|
+
- Execute `git diff {BRANCH_BASE}...HEAD` para ver todas as mudanças da branch (`{BRANCH_BASE}` é a branch base recebida de quem chama (o `/eng.pre-pr` passa a `Branch base:` do `architecture.md`); sem ela, `origin/main`.)
|
|
31
46
|
|
|
32
47
|
Foque especialmente em:
|
|
33
48
|
- Novas funcionalidades
|
|
@@ -21,10 +21,25 @@ Aplicar quando invocado via `eng.qa-refinement-entry` ou quando o argumento rece
|
|
|
21
21
|
|
|
22
22
|
**Modo B — Análise de Cobertura (pós-código)**
|
|
23
23
|
Aplicar quando invocado via `eng-qa`, `eng-qa-planner` ou quando houver código implementado na branch (git diff retorna resultados).
|
|
24
|
-
- Fonte de dados: `git diff origin/main
|
|
24
|
+
- Fonte de dados: `git diff {BRANCH_BASE}...HEAD` (`{BRANCH_BASE}` é a branch base recebida de quem chama (o `/eng.pre-pr` passa a `Branch base:` do `architecture.md`); sem ela, `origin/main`.)
|
|
25
25
|
- Saída: `$ENG_DOCS/qa/{task-id}-test_coverage_branch_report.md`
|
|
26
26
|
|
|
27
|
-
Regra de decisão: se `git diff
|
|
27
|
+
Regra de decisão: se `git diff {BRANCH_BASE}...HEAD` retornar vazio, operar em Modo A. Se retornar código, operar em Modo B.
|
|
28
|
+
|
|
29
|
+
## Quando chamado pelo `/eng.pre-pr`
|
|
30
|
+
|
|
31
|
+
O `/eng.pre-pr` passa a branch base (a `Branch base:` do `architecture.md`) e, da rodada 2 em diante, o diff incremental desde a rodada anterior. Use essa base no lugar de `origin/main` nos comandos de diff e log. Só aponte: não edite nem grave arquivos. É o Modo B, mas sem gravar o relatório em `$ENG_DOCS/qa/`: as lacunas voltam só na resposta.
|
|
32
|
+
|
|
33
|
+
Devolva uma lista de lacunas, uma por item, com os campos da tabela de lacunas do `gate-checklist.md`:
|
|
34
|
+
|
|
35
|
+
- **Lacuna**: o que falta ou está errado, terminando com "(item 3)", o número deste gate na lista do `/eng.pre-pr`.
|
|
36
|
+
- **Onde**: `arquivo:linha` com o trecho, ou o comando que a revelou e o resultado.
|
|
37
|
+
- **Por que importa**: o impacto, em linguagem simples.
|
|
38
|
+
- **Refutação**: o que derrubaria esta lacuna, com o lugar a conferir.
|
|
39
|
+
- **Sugestão**: como resolver.
|
|
40
|
+
- **Severidade**: 🔴 Bloqueador, 🟡 Importante ou ⚪ Menor (redação é ⚪).
|
|
41
|
+
|
|
42
|
+
Lista vazia é uma resposta válida. Fora do `/eng.pre-pr`, vale o formato de resposta deste arquivo.
|
|
28
43
|
|
|
29
44
|
## Skills Disponíveis
|
|
30
45
|
|
|
@@ -290,9 +305,9 @@ Usar quando: invocado via `eng-qa` ou `eng-qa-planner`, ou quando git diff retor
|
|
|
290
305
|
|
|
291
306
|
Comece entendendo o que mudou na branch atual:
|
|
292
307
|
|
|
293
|
-
- Execute `git diff
|
|
294
|
-
- Execute `git diff
|
|
295
|
-
- Execute `git log
|
|
308
|
+
- Execute `git diff {BRANCH_BASE}...HEAD --name-only` para listar todos os arquivos alterados
|
|
309
|
+
- Execute `git diff {BRANCH_BASE}...HEAD` para ver as mudanças em detalhe
|
|
310
|
+
- Execute `git log {BRANCH_BASE}..HEAD --oneline` para entender o histórico de commits
|
|
296
311
|
- Foque especialmente em:
|
|
297
312
|
- Novas funções/métodos/classes
|
|
298
313
|
- Lógica modificada em código existente
|
|
@@ -28,7 +28,7 @@ Em seguida, você deve:
|
|
|
28
28
|
- quais mudanças não estão alinhadas.
|
|
29
29
|
|
|
30
30
|
Formato da Resposta
|
|
31
|
-
Você deve fornecer sua resposta exatamente no seguinte formato:
|
|
31
|
+
Você deve fornecer sua resposta exatamente no seguinte formato (quando chamado pelo `/eng.pre-pr`, use o formato da seção "Quando chamado pelo `/eng.pre-pr`"):
|
|
32
32
|
|
|
33
33
|
```
|
|
34
34
|
[nome da branch]
|
|
@@ -51,6 +51,21 @@ Você deve fornecer sua resposta exatamente no seguinte formato:
|
|
|
51
51
|
Regras Importantes
|
|
52
52
|
Não faça nenhuma alteração no código ou nos requisitos, a menos que o usuário solicite explicitamente. Seu papel é avaliar e reportar, não corrigir.
|
|
53
53
|
|
|
54
|
+
## Quando chamado pelo `/eng.pre-pr`
|
|
55
|
+
|
|
56
|
+
O `/eng.pre-pr` passa a branch base (a `Branch base:` do `architecture.md`) e, da rodada 2 em diante, o diff incremental desde a rodada anterior. Use essa base no lugar de `origin/main` nos comandos de diff e log. Só aponte: não edite nem grave arquivos. Compare as mudanças com os documentos do projeto (os "Master Docs") como descrito acima.
|
|
57
|
+
|
|
58
|
+
Devolva uma lista de lacunas, uma por item, com os campos da tabela de lacunas do `gate-checklist.md`:
|
|
59
|
+
|
|
60
|
+
- **Lacuna**: o que falta ou está errado, terminando com "(item 1)", o número deste gate na lista do `/eng.pre-pr`.
|
|
61
|
+
- **Onde**: `arquivo:linha` com o trecho, ou o comando que a revelou e o resultado.
|
|
62
|
+
- **Por que importa**: o impacto, em linguagem simples.
|
|
63
|
+
- **Refutação**: o que derrubaria esta lacuna, com o lugar a conferir.
|
|
64
|
+
- **Sugestão**: como resolver.
|
|
65
|
+
- **Severidade**: 🔴 Bloqueador, 🟡 Importante ou ⚪ Menor (redação é ⚪).
|
|
66
|
+
|
|
67
|
+
Lista vazia é uma resposta válida. Fora do `/eng.pre-pr`, vale o formato de resposta deste arquivo.
|
|
68
|
+
|
|
54
69
|
## Skills Disponíveis
|
|
55
70
|
|
|
56
71
|
Nenhuma — agente autocontido, não depende de skill
|
package/bin/README.md
CHANGED
|
@@ -124,7 +124,7 @@ if (fileURLToPath(import.meta.url) === process.argv[1]) {
|
|
|
124
124
|
## Testes
|
|
125
125
|
|
|
126
126
|
- `npm run test:comandos` — valida que toda referência a comando/skill nos workflows e skills existe de fato (não testa o CLI em runtime).
|
|
127
|
-
- `npm run test:filtro` — testes unitários de `profile-filter.js`, `token-report.js`, `flow-map`, `env-loader.js`, `sync-engine.js`, `vcs/api.js`, `tasks/comment.js`, `integrations/` (catálogo e runner) e do upgrade.
|
|
127
|
+
- `npm run test:filtro` — testes unitários de `profile-filter.js`, `token-report.js`, `flow-map`, `env-loader.js`, `sync-engine.js`, `vcs/api.js`, `tasks/comment.js`, `integrations/` (catálogo e runner) e do upgrade, além dos testes que guardam o texto de workflows e rules (por exemplo, `gate-checklist-rodadas`, `publish-comments-rules` e `pre-pr-criterio`). A lista completa é o script `test:filtro` do `package.json`.
|
|
128
128
|
- Não há teste automatizado de ponta a ponta do CLI (`jarvis <comando>` real) — a camada de dispatch (`program.js`, `bin/commands/*.js`) não é cobrida pelos testes unitários. Qualquer mudança ali precisa de validação manual dos comandos afetados.
|
|
129
129
|
|
|
130
130
|
### Como testar código que lê `fs`/rede sem mockar módulo
|
package/bin/commands/init.js
CHANGED
|
@@ -39,6 +39,115 @@ function ask(rl, question) {
|
|
|
39
39
|
return new Promise((resolve) => rl.question(question, resolve));
|
|
40
40
|
}
|
|
41
41
|
|
|
42
|
+
/**
|
|
43
|
+
* Escolha do menu de pasta já instalada (#189). Função pura, para testar sem subprocesso.
|
|
44
|
+
* Com ENV.md: Enter ou 1 = atualizar (a opção recomendada), 2 = reinstalar, 3 = cancelar.
|
|
45
|
+
* Sem ENV.md não há o que atualizar (o upgrade precisa dele): o menu só tem 2 e 3, e Enter
|
|
46
|
+
* cancela, para o padrão nunca ser destrutivo (Q3). Qualquer outra resposta é inválida (Q9).
|
|
47
|
+
* @param {string} answer - linha digitada
|
|
48
|
+
* @param {{ hasEnv: boolean }} opts
|
|
49
|
+
* @returns {"upgrade" | "reinstall" | "cancel" | null} `null` = resposta inválida
|
|
50
|
+
*/
|
|
51
|
+
export function parseMenuChoice(answer, { hasEnv }) {
|
|
52
|
+
const choice = String(answer).trim();
|
|
53
|
+
if (choice === "2") return "reinstall";
|
|
54
|
+
if (choice === "3") return "cancel";
|
|
55
|
+
if (hasEnv && (choice === "" || choice === "1")) return "upgrade";
|
|
56
|
+
if (!hasEnv && choice === "") return "cancel";
|
|
57
|
+
return null;
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
/**
|
|
61
|
+
* O que ainda pede o `/jarvis-init upgrade` na IDE depois do `jarvis init --upgrade` (#189, Q4).
|
|
62
|
+
* Só as pendências que o terminal não resolve: eixo sem forma de acesso, chave vazia, Central docs
|
|
63
|
+
* no formato antigo e TOKEN_TASK_MANAGER com valor. Não contam o aviso de WORKSPACE_MODE (conferir
|
|
64
|
+
* no ENV.md), vendor não suportado (vira freelance) nem as chaves novas acrescentadas (Q15: o
|
|
65
|
+
* `/jarvis-init` as põe no assunto delas na próxima vez que rodar). Nunca inclui valores do ENV.
|
|
66
|
+
* @param {{ pendingAxes: string[], envPlan: { pending?: string[], warnings?: string[] } }} input
|
|
67
|
+
* @returns {string[]} um motivo por pendência; vazio = nada pendente
|
|
68
|
+
*/
|
|
69
|
+
export function upgradePendencies({ pendingAxes, envPlan }) {
|
|
70
|
+
const reasons = [];
|
|
71
|
+
if (pendingAxes.length) reasons.push(`confirmar o acesso de ${pendingAxes.join(" e ")}`);
|
|
72
|
+
if (envPlan.pending?.length) reasons.push(`preencher ${envPlan.pending.join(", ")}`);
|
|
73
|
+
const warnings = envPlan.warnings || [];
|
|
74
|
+
if (warnings.includes("CENTRAL_DOCS_REPO")) reasons.push("migrar o Central docs");
|
|
75
|
+
if (warnings.includes("TOKEN_TASK_MANAGER")) reasons.push("remover o TOKEN_TASK_MANAGER");
|
|
76
|
+
return reasons;
|
|
77
|
+
}
|
|
78
|
+
|
|
79
|
+
/**
|
|
80
|
+
* Leitor de linhas que não perde resposta: guarda as linhas que chegam antes da pergunta
|
|
81
|
+
* (pipe com várias linhas, como `printf 's\n3\n'`) e devolve `null` quando a entrada fecha
|
|
82
|
+
* sem linha (CI com `</dev/null`), em vez de esperar para sempre como o `rl.question` (Q2).
|
|
83
|
+
* @param {import("node:readline").Interface} rl
|
|
84
|
+
* @returns {(question: string) => Promise<string | null>}
|
|
85
|
+
*/
|
|
86
|
+
function lineReader(rl) {
|
|
87
|
+
const lines = [];
|
|
88
|
+
const waiting = [];
|
|
89
|
+
let closed = false;
|
|
90
|
+
rl.on("line", (line) => (waiting.length ? waiting.shift()(line) : lines.push(line)));
|
|
91
|
+
rl.on("close", () => {
|
|
92
|
+
closed = true;
|
|
93
|
+
while (waiting.length) waiting.shift()(null);
|
|
94
|
+
});
|
|
95
|
+
// Sem terminal, a resposta não aparece na tela: a quebra de linha separa a pergunta do que vem depois.
|
|
96
|
+
const echo = (line) => {
|
|
97
|
+
if (line !== null && !process.stdin.isTTY) process.stdout.write("\n");
|
|
98
|
+
return line;
|
|
99
|
+
};
|
|
100
|
+
return (question) => {
|
|
101
|
+
process.stdout.write(question);
|
|
102
|
+
if (lines.length) return Promise.resolve(echo(lines.shift()));
|
|
103
|
+
if (closed) return Promise.resolve(null);
|
|
104
|
+
return new Promise((resolve) => waiting.push(resolve)).then(echo);
|
|
105
|
+
};
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
/**
|
|
109
|
+
* Menu de `jarvis init` numa pasta que já tem a pasta da IDE (#189).
|
|
110
|
+
* Decide pela resposta lida, não por `process.stdin.isTTY`: `printf '\n' |` também atualiza.
|
|
111
|
+
* `askLine` é o leitor compartilhado com o menu de IDE: um leitor só para a entrada inteira,
|
|
112
|
+
* para a resposta de um menu não consumir a do outro (`printf '1\n3\n' | jarvis init`).
|
|
113
|
+
* @returns {Promise<"upgrade" | "reinstall" | "cancel" | "no-answer">} `no-answer` = entrada fechada (a mensagem já saiu)
|
|
114
|
+
*/
|
|
115
|
+
async function askInstalledMenu({ folder, lockVersion, packageVersion, hasEnv, askLine }) {
|
|
116
|
+
const installed = lockVersion === "desconhecida" ? "versão desconhecida" : `v${lockVersion}`;
|
|
117
|
+
logger.info(
|
|
118
|
+
`${YELLOW}⚠️ Jarvis já instalado em .${folder} (${installed} · pacote v${packageVersion})${NC}`
|
|
119
|
+
);
|
|
120
|
+
logger.info("");
|
|
121
|
+
if (!hasEnv) {
|
|
122
|
+
logger.info(`${DIM}Atualizar precisa do ENV.md: reinstale e rode /jarvis-init na IDE.${NC}`);
|
|
123
|
+
logger.info("");
|
|
124
|
+
}
|
|
125
|
+
logger.info("O que deseja fazer?");
|
|
126
|
+
if (hasEnv) {
|
|
127
|
+
logger.info(
|
|
128
|
+
` 1) Atualizar (recomendado) — sincroniza com a versão do pacote, preserva o ENV.md`
|
|
129
|
+
);
|
|
130
|
+
}
|
|
131
|
+
logger.info(` 2) Reinstalar — sobrescreve os arquivos do framework`);
|
|
132
|
+
logger.info(` 3) Cancelar`);
|
|
133
|
+
logger.info("");
|
|
134
|
+
|
|
135
|
+
const valid = hasEnv ? "1, 2 ou 3" : "2 ou 3";
|
|
136
|
+
for (;;) {
|
|
137
|
+
const answer = await askLine(`Escolha [${hasEnv ? "1" : "3"}]: `);
|
|
138
|
+
if (answer === null) {
|
|
139
|
+
logger.info("");
|
|
140
|
+
logger.info(
|
|
141
|
+
`${BLUE}ℹ️ Sem resposta: nada alterado. Use --upgrade (atualizar) ou --force (reinstalar).${NC}\n`
|
|
142
|
+
);
|
|
143
|
+
return "no-answer";
|
|
144
|
+
}
|
|
145
|
+
const choice = parseMenuChoice(answer, { hasEnv });
|
|
146
|
+
if (choice) return choice;
|
|
147
|
+
logger.info(`${RED}Opção inválida. Escolha ${valid}.${NC}`);
|
|
148
|
+
}
|
|
149
|
+
}
|
|
150
|
+
|
|
42
151
|
/**
|
|
43
152
|
* Grava o Context7 (MCP obrigatório) no arquivo de MCP da IDE e mostra o que falta.
|
|
44
153
|
* Só avisa: problema no arquivo de MCP não muda o código de saída (instalação e --upgrade).
|
|
@@ -73,6 +182,21 @@ export async function init(flags) {
|
|
|
73
182
|
return;
|
|
74
183
|
}
|
|
75
184
|
|
|
185
|
+
// Um leitor de linhas só para os dois menus (IDE e pasta já instalada), criado na primeira
|
|
186
|
+
// pergunta e fechado antes do sync ou do upgrade (que abre o seu, só com terminal).
|
|
187
|
+
let reader = null;
|
|
188
|
+
const askLine = (question) => {
|
|
189
|
+
if (!reader) {
|
|
190
|
+
const rl = createInterface({ input: process.stdin, terminal: false });
|
|
191
|
+
reader = { rl, next: lineReader(rl) };
|
|
192
|
+
}
|
|
193
|
+
return reader.next(question);
|
|
194
|
+
};
|
|
195
|
+
const closeReader = () => {
|
|
196
|
+
reader?.rl.close();
|
|
197
|
+
reader = null;
|
|
198
|
+
};
|
|
199
|
+
|
|
76
200
|
let ide;
|
|
77
201
|
if (flags.ide) {
|
|
78
202
|
if (!isIDESupported(flags.ide)) {
|
|
@@ -100,14 +224,15 @@ export async function init(flags) {
|
|
|
100
224
|
});
|
|
101
225
|
logger.info("");
|
|
102
226
|
|
|
103
|
-
const rl = createInterface({
|
|
104
|
-
input: process.stdin,
|
|
105
|
-
output: process.stdout,
|
|
106
|
-
});
|
|
107
|
-
|
|
108
227
|
let choice;
|
|
109
228
|
while (true) {
|
|
110
|
-
choice = await
|
|
229
|
+
choice = await askLine(`${BLUE}Digite o número da sua escolha (1-${IDES.length}): ${NC}`);
|
|
230
|
+
if (choice === null) {
|
|
231
|
+
closeReader();
|
|
232
|
+
logger.info("");
|
|
233
|
+
logger.info(`${BLUE}ℹ️ Sem resposta: nada alterado. Use --ide {ide}.${NC}\n`);
|
|
234
|
+
return;
|
|
235
|
+
}
|
|
111
236
|
const choiceNum = parseInt(choice, 10);
|
|
112
237
|
|
|
113
238
|
if (choiceNum >= 1 && choiceNum <= IDES.length) {
|
|
@@ -128,40 +253,41 @@ export async function init(flags) {
|
|
|
128
253
|
);
|
|
129
254
|
}
|
|
130
255
|
}
|
|
131
|
-
|
|
132
|
-
rl.close();
|
|
133
256
|
}
|
|
134
257
|
|
|
135
258
|
const ideDir = join(cwd, `.${getIDEFolder(ide)}`);
|
|
136
259
|
|
|
137
|
-
// Avisos de versão antes
|
|
138
|
-
//
|
|
139
|
-
|
|
260
|
+
// Avisos de versão antes do menu: quem escolhe reinstalar (ou usa --force) já sabe se vai
|
|
261
|
+
// rebaixar os assets. O resultado vai para o runUpgrade, que não repete o aviso (Q8).
|
|
262
|
+
const lockVersion = readLockVersion(cwd);
|
|
263
|
+
const versionCheck = warnVersionMismatch(cwd, lockVersion);
|
|
140
264
|
|
|
141
|
-
//
|
|
265
|
+
// Reinstalação: --force ou a opção 2 do menu sobrescrevem os assets (cpSync force:true).
|
|
142
266
|
let forceSync = !!flags.force;
|
|
143
267
|
|
|
144
268
|
if (existsSync(ideDir) && !forceSync) {
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
269
|
+
const choice = await askInstalledMenu({
|
|
270
|
+
folder: getIDEFolder(ide),
|
|
271
|
+
lockVersion,
|
|
272
|
+
packageVersion: versionCheck.running,
|
|
273
|
+
hasEnv: existsSync(join(ideDir, "ENV.md")),
|
|
274
|
+
askLine,
|
|
151
275
|
});
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
if (
|
|
276
|
+
closeReader();
|
|
277
|
+
if (choice === "upgrade") {
|
|
278
|
+
logger.info("");
|
|
279
|
+
process.exitCode = await runUpgrade(cwd, { ...flags, ide, versionCheck });
|
|
280
|
+
return;
|
|
281
|
+
}
|
|
282
|
+
if (choice === "no-answer") return;
|
|
283
|
+
if (choice === "cancel") {
|
|
159
284
|
logger.info(`${BLUE}ℹ️ Instalação cancelada.${NC}\n`);
|
|
160
285
|
return;
|
|
161
286
|
}
|
|
162
287
|
forceSync = true;
|
|
163
288
|
logger.info("");
|
|
164
289
|
}
|
|
290
|
+
closeReader();
|
|
165
291
|
|
|
166
292
|
const ideConfig = getIDEConfig(ide);
|
|
167
293
|
logger.info(`${BLUE}Configurando ambiente para ${ideConfig?.name}...${NC}`);
|
|
@@ -169,13 +295,15 @@ export async function init(flags) {
|
|
|
169
295
|
const result = syncAssets(cwd, ide, {
|
|
170
296
|
force: forceSync,
|
|
171
297
|
workflowsFolder: getWorkflowsFolder(ide),
|
|
298
|
+
// Reinstalação não troca valor do ENV.md (RTK_ENABLED=false fica), como o upgrade (Q1).
|
|
299
|
+
keepEnvValues: forceSync,
|
|
172
300
|
});
|
|
173
301
|
|
|
174
302
|
for (const item of result.copied) {
|
|
175
303
|
logger.info(`${BLUE} ↳ ${item}${NC}`);
|
|
176
304
|
}
|
|
177
305
|
for (const item of result.skipped) {
|
|
178
|
-
logger.info(`${DIM} ↳ ${item}
|
|
306
|
+
logger.info(`${DIM} ↳ ${item}${NC}`); // o motivo já vem no item (sync-engine)
|
|
179
307
|
}
|
|
180
308
|
for (const item of result.errors) {
|
|
181
309
|
logger.error(`${RED} ✗ ${item}${NC}`);
|
|
@@ -371,7 +499,9 @@ async function runUpgrade(cwd, flags) {
|
|
|
371
499
|
const workspaceDir = resolved.root;
|
|
372
500
|
const envPath = resolved.path;
|
|
373
501
|
const previousVersion = readLockVersion(workspaceDir);
|
|
374
|
-
|
|
502
|
+
// Vindo do menu do `init`, o aviso já saiu antes da escolha (Q8): só reaproveita o resultado.
|
|
503
|
+
const { downgrade, running } =
|
|
504
|
+
flags.versionCheck ?? warnVersionMismatch(workspaceDir, previousVersion);
|
|
375
505
|
if (downgrade && !flags.yes) {
|
|
376
506
|
let go = false;
|
|
377
507
|
if (process.stdin.isTTY) {
|
|
@@ -480,7 +610,11 @@ async function runUpgrade(cwd, flags) {
|
|
|
480
610
|
// 4. Resumo (só nomes de chave e caminhos)
|
|
481
611
|
const pkg = getPackageInfo();
|
|
482
612
|
logger.info("");
|
|
483
|
-
logger.info(
|
|
613
|
+
logger.info(
|
|
614
|
+
previousVersion === pkg.version
|
|
615
|
+
? `${GREEN}✅ Upgrade concluído: já na v${pkg.version} (arquivos ressincronizados)${NC}`
|
|
616
|
+
: `${GREEN}✅ Upgrade concluído: ${previousVersion} → ${pkg.version}${NC}`
|
|
617
|
+
);
|
|
484
618
|
logger.info(` • Arquivos do framework: ${sync.copied.length} item(ns) sincronizado(s)`);
|
|
485
619
|
logger.info(
|
|
486
620
|
` • ENV.md: ${addedKeys.length ? `+ ${addedKeys.join(", ")}` : "nenhuma variável nova"}`
|
|
@@ -532,11 +666,12 @@ async function runUpgrade(cwd, flags) {
|
|
|
532
666
|
const access = (futureEntries.get(`${key}_ACCESS`) || "").trim();
|
|
533
667
|
return getVendor(futureEntries.get(key)) && (!access || /^\[.*\]$/.test(access));
|
|
534
668
|
});
|
|
669
|
+
const pending = upgradePendencies({ pendingAxes, envPlan });
|
|
535
670
|
logger.info("");
|
|
536
671
|
logger.info(
|
|
537
|
-
|
|
538
|
-
? `${CYAN}➡️ Agora rode ${BOLD}/jarvis-init upgrade${NC}${CYAN} na IDE
|
|
539
|
-
: `${
|
|
672
|
+
pending.length
|
|
673
|
+
? `${CYAN}➡️ Agora rode ${BOLD}/jarvis-init upgrade${NC}${CYAN} na IDE: ${pending.join("; ")}.${NC}\n`
|
|
674
|
+
: `${GREEN}✓ Nada pendente na IDE.${NC}\n`
|
|
540
675
|
);
|
|
541
676
|
return sync.errors.length || moveErrors.length || staleErrors.length ? 1 : 0;
|
|
542
677
|
}
|
package/bin/lib/cli/program.js
CHANGED
|
@@ -87,18 +87,18 @@ export function buildProgram() {
|
|
|
87
87
|
const initCmd = cmd(program, "init")
|
|
88
88
|
.description("Bootstrap do framework no workspace")
|
|
89
89
|
.option("--ide <ide>", "IDE a configurar (pula o menu interativo)")
|
|
90
|
-
.option("--force", "
|
|
90
|
+
.option("--force", "Reinstala sem mostrar o menu: sobrescreve os arquivos do framework")
|
|
91
91
|
.option(
|
|
92
92
|
"--upgrade",
|
|
93
|
-
"Atualiza
|
|
93
|
+
"Atualiza sem mostrar o menu: arquivos do framework, variáveis novas do ENV e pastas de documentos"
|
|
94
94
|
)
|
|
95
95
|
.option(
|
|
96
96
|
"--yes",
|
|
97
|
-
"Com --upgrade, move os documentos para as pastas novas e aceita rebaixar os assets sem perguntar"
|
|
97
|
+
"Com --upgrade (ou a opção Atualizar do menu), move os documentos para as pastas novas e aceita rebaixar os assets sem perguntar"
|
|
98
98
|
)
|
|
99
99
|
.option(
|
|
100
100
|
"--remove-stale",
|
|
101
|
-
"Com --upgrade, remove sem perguntar os skills instalados que saíram do framework (só os listados)"
|
|
101
|
+
"Com --upgrade (ou a opção Atualizar do menu), remove sem perguntar os skills instalados que saíram do framework (só os listados)"
|
|
102
102
|
);
|
|
103
103
|
withLogOptions(initCmd).action((options) => init(toLegacyFlags(options)));
|
|
104
104
|
|
|
@@ -80,7 +80,7 @@ export function syncAssets(targetDir, ide, opts = {}) {
|
|
|
80
80
|
const dest = join(ideDir, destDirName);
|
|
81
81
|
|
|
82
82
|
if (!existsSync(src)) {
|
|
83
|
-
result.skipped.push(`${dir}/ (
|
|
83
|
+
result.skipped.push(`${dir}/ (não existe no framework)`);
|
|
84
84
|
continue;
|
|
85
85
|
}
|
|
86
86
|
|
|
@@ -102,7 +102,7 @@ export function syncAssets(targetDir, ide, opts = {}) {
|
|
|
102
102
|
if (!existsSync(src)) continue;
|
|
103
103
|
|
|
104
104
|
if (existsSync(dest) && !opts.force) {
|
|
105
|
-
result.skipped.push(`${file} (
|
|
105
|
+
result.skipped.push(`${file} (já existe)`);
|
|
106
106
|
continue;
|
|
107
107
|
}
|
|
108
108
|
|
|
@@ -228,7 +228,11 @@ function reconcileRtk(ideDir, targetDir, ide, { keepEnvValues = false } = {}) {
|
|
|
228
228
|
return "(rtk) detectado — RTK_ENABLED=true no ENV.md";
|
|
229
229
|
}
|
|
230
230
|
if (!env.includes("RTK_ENABLED")) {
|
|
231
|
-
|
|
231
|
+
// Moldura do ENV-template (#189): o /jarvis-init não aponta o bloco como separador antigo.
|
|
232
|
+
const bar =
|
|
233
|
+
"# =============================================================================";
|
|
234
|
+
env =
|
|
235
|
+
env.trimEnd() + `\n\n${bar}\n# RTK — Token Killer (opcional)\n${bar}\nRTK_ENABLED=true\n`;
|
|
232
236
|
writeFileSync(envPath, env, "utf-8");
|
|
233
237
|
return "(rtk) detectado — RTK_ENABLED=true adicionado ao ENV.md";
|
|
234
238
|
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "jarvis-ai-framework",
|
|
3
|
-
"version": "8.
|
|
3
|
+
"version": "8.2.0",
|
|
4
4
|
"description": "Jarvis framework",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"bin": {
|
|
@@ -11,7 +11,7 @@
|
|
|
11
11
|
"prepublishOnly": "echo 'Publishing jarvis-framework...'",
|
|
12
12
|
"publish:gitlab": "npm publish",
|
|
13
13
|
"test:comandos": "node test/comandos-docs.test.js",
|
|
14
|
-
"test:filtro": "node --test test/profile-filter.test.js test/token-report.test.js test/flow-map.test.js test/env-loader.test.js test/sync-engine.test.js test/vcs-api.test.js test/fetch-file.test.js test/publish-file.test.js test/docs-storage.test.js test/env-upgrade.test.js test/docs-migrate.test.js test/init-upgrade.test.js test/workspace-mode.test.js test/stale-skills.test.js test/session-scan.test.js test/framework-refs.test.js test/validate-frontmatter.test.js test/mcp-config.test.js test/integrations-catalog.test.js test/cli-runner.test.js test/tasks-comment.test.js test/version.test.js test/gate-checklist-rodadas.test.js test/publish-comments-rules.test.js",
|
|
14
|
+
"test:filtro": "node --test test/profile-filter.test.js test/token-report.test.js test/flow-map.test.js test/env-loader.test.js test/sync-engine.test.js test/vcs-api.test.js test/fetch-file.test.js test/publish-file.test.js test/docs-storage.test.js test/env-upgrade.test.js test/docs-migrate.test.js test/init-upgrade.test.js test/workspace-mode.test.js test/stale-skills.test.js test/session-scan.test.js test/framework-refs.test.js test/validate-frontmatter.test.js test/mcp-config.test.js test/integrations-catalog.test.js test/cli-runner.test.js test/tasks-comment.test.js test/version.test.js test/gate-checklist-rodadas.test.js test/publish-comments-rules.test.js test/pre-pr-criterio.test.js test/nomes-soltos.test.js",
|
|
15
15
|
"lint": "eslint bin/ test/",
|
|
16
16
|
"lint:fix": "eslint bin/ test/ --fix",
|
|
17
17
|
"format": "prettier --write bin/ test/",
|
|
@@ -211,6 +211,7 @@ Para cada tarefa, incluir:
|
|
|
211
211
|
|
|
212
212
|
### Fase 5: Validação
|
|
213
213
|
|
|
214
|
+
0. **Executar** o Checklist de Conclusão (abaixo) item a item contra o `plan.md` e corrigir o plano antes de apresentar (passe crítico, Fase 4 do workflow)
|
|
214
215
|
1. **Apresentar** o plano ao humano
|
|
215
216
|
2. **Discutir** ajustes necessários
|
|
216
217
|
3. **Atualizar** `architecture.md` se houver mudanças arquiteturais
|
|
@@ -300,6 +301,7 @@ Antes de considerar o plano completo:
|
|
|
300
301
|
- [ ] Dependências estão claras (sequencial/paralelo)
|
|
301
302
|
- [ ] Status iniciais definidos (todos ⏳)
|
|
302
303
|
- [ ] Conteúdo em português (pt-BR)
|
|
304
|
+
- [ ] Passe crítico executado (este checklist conferido item a item) e "Ajustes antes da aprovação" atualizado no cabeçalho a cada "Ajustar o plano"
|
|
303
305
|
- [ ] Validado com o humano
|
|
304
306
|
- [ ] `plan.md` criado em `$SESSIONS_DIR/eng/{TASK_MANAGER_KEY}/`
|
|
305
307
|
|
|
@@ -75,9 +75,11 @@ Avaliar **apenas** as mudanças da branch atual em relação à branch base (`Br
|
|
|
75
75
|
git diff {BRANCH_BASE}...HEAD
|
|
76
76
|
```
|
|
77
77
|
|
|
78
|
+
Da rodada 2 em diante, cada gate roda só se o diff desde o `Commit:` da rodada anterior tocar o que ele lê (seção "Rodada incremental" do `eng.pre-pr.md`). O gate que roda continua revisando a branch inteira.
|
|
79
|
+
|
|
78
80
|
### Evidências Obrigatórias
|
|
79
81
|
|
|
80
|
-
Cada lacuna cita onde está (`arquivo:linha`) ou o comando que a revelou e o resultado.
|
|
82
|
+
Cada lacuna cita onde está (`arquivo:linha` com o trecho) ou o comando que a revelou e o resultado, **e o que a derrubaria** (coluna Refutação). Antes de gravar, o passe crítico (seção "Passe crítico" do `eng.pre-pr.md`) remove a lacuna cuja refutação se sustenta e rebaixa a que pesa menos do que a severidade dada.
|
|
81
83
|
|
|
82
84
|
---
|
|
83
85
|
|
|
@@ -86,9 +88,12 @@ Cada lacuna cita onde está (`arquivo:linha`) ou o comando que a revelou e o res
|
|
|
86
88
|
O workflow **deve sempre** terminar com:
|
|
87
89
|
|
|
88
90
|
1. **`gate-checklist.md`** em `$SESSIONS_DIR/eng/{TASK_MANAGER_KEY}/`:
|
|
89
|
-
- semáforo (🟢 / 🟡 / 🔴), resumo, lacunas por área (o quê, onde, por que importa, sugestão, severidade, **Decisão**), evidências e PR Brief.
|
|
91
|
+
- semáforo (🟢 / 🟡 / 🔴), resumo (com a linha `Critério de parada:`), lacunas por área (o quê, com o "(item N)" do gate que a achou no fim, onde, por que importa, refutação, sugestão, severidade, **Decisão**), evidências e PR Brief (com as rodadas por severidade, a rodada em que o critério de parada agiu, os ajustes do `architecture.md` e do `plan.md` antes da aprovação e as lições desta tarefa; guardar lições entre tarefas não é deste comando, é da #169).
|
|
90
92
|
- `Rodada` e `Commit` no cabeçalho, as rodadas anteriores e, da rodada 2 em diante, a resolução das lacunas da rodada anterior.
|
|
93
|
+
- Da rodada 2 em diante, as áreas cujos gates não rodaram na rodada incremental, marcadas como "Não reavaliada nesta rodada".
|
|
91
94
|
- É sempre a rodada mais recente: ao rodar de novo na mesma sessão, o relatório existente é preservado como `gate-checklist-rodada-{N}.md` (seção "Rodadas" do `eng.pre-pr.md`). **Nunca** sobrescrever nem apagar uma rodada; renomear imediatamente antes de gravar.
|
|
92
|
-
2. **Decisões do usuário** gravadas na coluna Decisão (🔧 Corrigir / 👍 Aceitar + motivo; vazia se o usuário escolheu "Só gerar o relatório", exceto as decisões herdadas da rodada anterior).
|
|
95
|
+
2. **Decisões do usuário** gravadas na coluna Decisão (🔧 Corrigir / 👍 Aceitar + motivo; vazia se o usuário escolheu "Só gerar o relatório", exceto as decisões herdadas da rodada anterior). Na variante B do fechamento, as ⚪ aceitas levam `👍 Aceitar: aceito no fechamento da rodada {N}` e as 🟡 aceitas em bloco (só com o teto atingido) levam `👍 Aceitar: teto de rodadas atingido na rodada {N}`, e as decididas uma a uma levam o motivo dado pela pessoa; decisão herdada nunca é trocada.
|
|
96
|
+
- **Critério de parada** (seção "Fechamento" do `eng.pre-pr.md`): teto de rodadas pela urgência do `context.md` (`alta` 3 · `normal` 5 · `baixa` 8) ou rodada sem lacuna 🔴 ou 🟡 nova (com os itens 2 e 3 tendo rodado). Sem 🔴 pendente nem 🟡 herdada com `🔧 Corrigir`, e com só ⚪ sem decisão (ou também 🟡, com o critério de parada atingido), o fechamento usa a variante B. Na variante B, "Aceitar as ⚪ e seguir para o PR" é a primeira opção (a recomendada) e "Só gerar o relatório" mantém o fluxo de hoje. Só o teto aceita 🟡 em bloco; com o gatilho "sem lacuna nova", as 🟡 são decididas uma a uma. O critério nunca pula a revisão nem a gravação. Fora desses casos (por exemplo, com 🔴 pendente), o ciclo segue na variante A. Sempre que o teto for atingido e houver pendência, o fechamento avisa.
|
|
97
|
+
- **Pendentes não reavaliadas** (rodada incremental): a lacuna pendente da rodada anterior cujo gate de origem (o "(item N)" da coluna Lacuna) não rodou é copiada para a rodada nova, com a decisão herdada.
|
|
93
98
|
3. **Pergunta** (`AskUserQuestion`) sobre registrar o resultado como comentário no card (`/eng-global-task-comment`): Não, manter só na sessão (como hoje) / Sim, só o resumo / Sim, o relatório completo. Nunca publicar sem a resposta. Freelance: não pergunta, só na sessão.
|
|
94
99
|
4. **Aguardar permissão explícita** do usuário para prosseguir para `/eng.pr`.
|