@polymorphism-tech/morph-spec 8.46.0 → 9.0.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/CLAUDE.md +53 -44
- package/README.md +3 -4
- package/bin/morph-spec.js +38 -55
- package/bin/validate.js +5 -134
- package/claude-plugin.json +1 -1
- package/docs/CHEATSHEET.md +2 -2
- package/docs/QUICKSTART.md +1 -1
- package/framework/CLAUDE.md +41 -101
- package/framework/MORPH.md +95 -252
- package/framework/agents.json +75 -18
- package/framework/commands/create-umbraco-lp.md +2 -0
- package/framework/commands/migrate-lp-to-umbraco.md +2 -0
- package/framework/commands/morph-apply.md +5 -28
- package/framework/commands/morph-archive.md +2 -2
- package/framework/commands/morph-hotfix.md +8 -8
- package/framework/commands/morph-infra.md +17 -203
- package/framework/commands/morph-media.md +3 -0
- package/framework/commands/morph-preflight.md +7 -31
- package/framework/commands/morph-proposal.md +2 -50
- package/framework/commands/morph-status.md +3 -3
- package/framework/commands/morph-troubleshoot.md +2 -14
- package/framework/docs/CLI.md +585 -286
- package/framework/evals/review-checklist.md +82 -41
- package/framework/hooks/README.md +10 -11
- package/framework/hooks/claude-code/core/comment-guard.js +1 -1
- package/framework/hooks/claude-code/core/denylist.json +33 -3
- package/framework/hooks/claude-code/core/enforce-phase-writes.js +16 -20
- package/framework/hooks/claude-code/core/gate-guard.js +2 -11
- package/framework/hooks/claude-code/core/pre-bash-denylist.js +38 -0
- package/framework/hooks/claude-code/core/protect-spec-files.js +30 -242
- package/framework/hooks/claude-code/core/state-sync.js +17 -19
- package/framework/hooks/claude-code/core/telemetry-log.js +3 -3
- package/framework/hooks/claude-code/core/validate-completion.js +33 -97
- package/framework/hooks/claude-code/core/warn-bash-source-write.js +31 -0
- package/framework/hooks/claude-code/core/worktree-context.js +5 -4
- package/framework/hooks/claude-code/statusline.py +55 -41
- package/framework/hooks/package.json +3 -0
- package/framework/hooks/shared/activity-logger.js +1 -1
- package/framework/hooks/shared/build-check.js +10 -6
- package/framework/hooks/shared/command-tokens.js +169 -0
- package/framework/hooks/shared/comment-rules.js +1 -1
- package/framework/hooks/shared/comment-scanner.js +10 -23
- package/framework/hooks/shared/comment-stripper.js +1 -1
- package/framework/hooks/shared/e2e-check.js +67 -31
- package/framework/hooks/shared/errata.js +72 -0
- package/framework/hooks/shared/feature-locator.js +1 -1
- package/framework/hooks/shared/frontend-locations.js +6 -0
- package/framework/hooks/shared/gate-question.js +18 -0
- package/framework/hooks/shared/phase-utils.js +15 -32
- package/framework/hooks/shared/slice-progress.js +118 -0
- package/framework/hooks/shared/spawn-command.js +23 -0
- package/framework/hooks/shared/state-reader.js +61 -87
- package/framework/hooks/shared/state-writer.js +3 -3
- package/framework/mcp/registry.json +3 -4
- package/framework/phases.json +23 -39
- package/framework/rules/ai-agents-standards.md +18 -16
- package/framework/rules/asaas-standards.md +3 -1
- package/framework/rules/csharp-standards.md +10 -8
- package/framework/rules/data-standards.md +5 -5
- package/framework/rules/dotnet-templates.md +1 -1
- package/framework/rules/frontend-standards.md +4 -2
- package/framework/rules/gsap-standards.md +10 -5
- package/framework/rules/hangfire-standards.md +3 -1
- package/framework/rules/infrastructure-standards.md +4 -2
- package/framework/rules/neon-auth-standards.md +3 -1
- package/framework/rules/neon-standards.md +6 -4
- package/framework/rules/nextjs-standards.md +13 -11
- package/framework/rules/nextjs-templates.md +1 -1
- package/framework/rules/resend-standards.md +3 -1
- package/framework/schemas/config.schema.json +14 -9
- package/framework/schemas/feature.schema.json +15 -52
- package/framework/skills/README.md +4 -5
- package/framework/skills/core/create-umbraco-lp/SKILL.md +3 -3
- package/framework/skills/core/migrate-lp-to-umbraco/SKILL.md +3 -3
- package/framework/skills/core/morph-apply/SKILL.md +150 -223
- package/framework/skills/core/morph-hotfix/SKILL.md +34 -43
- package/framework/skills/core/morph-machine/SKILL.md +4 -4
- package/framework/skills/core/morph-media/SKILL.md +3 -3
- package/framework/skills/core/morph-plan/SKILL.md +138 -300
- package/framework/skills/core/morph-review/SKILL.md +112 -137
- package/framework/skills/core/morph-standards/SKILL.md +29 -41
- package/framework/skills/core/morph-uiux/SKILL.md +78 -153
- package/framework/standards/STANDARDS.json +90 -1219
- package/framework/standards/STANDARDS.meta.json +1305 -0
- package/framework/standards/ai-agents/evals-with-cache.md +2 -3
- package/framework/standards/ai-agents/llm-runtime-defaults.md +1 -1
- package/framework/standards/ai-agents/modalities-speech-to-text.md +36 -26
- package/framework/standards/ai-agents/prompt-sources.md +6 -4
- package/framework/standards/ai-agents/providers/model-registry.md +1 -1
- package/framework/standards/ai-agents/rag-custom-pgvector.md +67 -39
- package/framework/standards/ai-agents/setup.md +2 -2
- package/framework/standards/ai-agents/structured-output.md +1 -1
- package/framework/standards/ai-agents/sweet-spot.md +1 -1
- package/framework/standards/architecture/code-comments.md +8 -8
- package/framework/standards/architecture/vertical-slice/vertical-slice.md +18 -9
- package/framework/standards/backend/api/validation.md +135 -47
- package/framework/standards/backend/database/postgresql/database.md +11 -7
- package/framework/standards/backend/database/vector-search-rag.md +207 -324
- package/framework/standards/backend/dotnet/fluent-validation-vsa.md +14 -8
- package/framework/standards/backend/dotnet/result-pattern.md +40 -6
- package/framework/standards/backend/dotnet/scalar-ui.md +13 -7
- package/framework/standards/backend/dotnet/scrutor.md +1 -1
- package/framework/standards/backend/dotnet/testing.md +1 -1
- package/framework/standards/backend/dotnet/vsa-handler-patterns.md +7 -7
- package/framework/standards/backend/integrations/asaas/asaas-api.md +309 -165
- package/framework/standards/backend/integrations/hangfire/hangfire-jobs.md +134 -154
- package/framework/standards/data/nosql/cache/redis.md +120 -44
- package/framework/standards/data/nosql/cosmos-db.md +114 -71
- package/framework/standards/frontend/design-system/animations.md +1 -1
- package/framework/standards/frontend/design-system/naming.md +1 -1
- package/framework/standards/frontend/nextjs/motion-patterns.md +45 -29
- package/framework/standards/frontend/nextjs/naming-conventions.md +1 -1
- package/framework/standards/infrastructure/docker/coolify-deploy.md +8 -6
- package/framework/standards/infrastructure/neon/neon-pgvector.md +120 -75
- package/framework/standards/infrastructure/neon/neon-setup.md +53 -31
- package/framework/standards/integration/mcp/mcp-tools.md +7 -7
- package/framework/templates/README.md +2 -3
- package/framework/templates/REGISTRY.json +6 -170
- package/framework/templates/code/dotnet/contracts/contracts-vsa.cs +2 -2
- package/framework/templates/code/dotnet/extensions/database-extensions.cs +1 -1
- package/framework/templates/code/dotnet/extensions/result-extensions.cs +27 -0
- package/framework/templates/code/dotnet/feature/endpoint.cs.hbs +2 -2
- package/framework/templates/docs/plan.md +72 -0
- package/framework/templates/dotnet/ai-kit/README.md +1 -9
- package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/MediaDisclosureTests.cs +1 -1
- package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/Morph.AiKit.Tests.csproj +0 -10
- package/framework/templates/infrastructure/docker/coolify.template.json +3 -3
- package/framework/templates/infrastructure/github/README.md +2 -1
- package/framework/templates/infrastructure/github/workflows/deploy-coolify.yml.hbs +2 -1
- package/framework/templates/meta-prompts/squad-leaders/backend-squad.md +1 -1
- package/framework/templates/meta-prompts/squad-leaders/frontend-squad.md +1 -1
- package/framework/templates/meta-prompts/squad-leaders/squad-leader.md +1 -1
- package/framework/templates/meta-prompts/validators/pre-commit-validator.md +3 -4
- package/package.json +1 -1
- package/src/commands/e2e/e2e.js +2 -2
- package/src/commands/observability/cost.js +18 -60
- package/src/commands/observability/telemetry.js +3 -5
- package/src/commands/project/doctor-procs.js +1 -1
- package/src/commands/project/doctor.js +9 -9
- package/src/commands/project/fleet.js +4 -4
- package/src/commands/project/heavy.js +3 -3
- package/src/commands/project/init.js +6 -1
- package/src/commands/project/setup-infra-cmd.js +2 -1
- package/src/commands/project/stack-scan.js +58 -0
- package/src/commands/project/standards.js +79 -25
- package/src/commands/project/status.js +29 -69
- package/src/commands/project/update.js +33 -19
- package/src/commands/project/worktree.js +1 -1
- package/src/commands/state/advance.js +62 -46
- package/src/commands/state/approve.js +95 -138
- package/src/commands/state/archive.js +20 -84
- package/src/commands/state/auto-approval.js +68 -0
- package/src/commands/state/create.js +28 -1
- package/src/commands/state/delete.js +1 -1
- package/src/commands/state/finish.js +11 -23
- package/src/commands/state/gate-check.js +86 -95
- package/src/commands/state/gate-decision.js +6 -4
- package/src/commands/state/handoff.js +1 -1
- package/src/commands/state/list.js +9 -9
- package/src/commands/state/report-check.js +157 -311
- package/src/commands/state/retype.js +9 -3
- package/src/commands/validation/mutate.js +77 -14
- package/src/commands/validation/plan-check.js +81 -0
- package/src/commands/validation/validate-feature.js +60 -135
- package/src/commands/validation/verify.js +41 -82
- package/src/core/paths/output-schema.js +20 -67
- package/src/core/state/gate-order.js +5 -6
- package/src/core/state/lifecycle-audit.js +2 -2
- package/src/core/state/state-manager.js +17 -98
- package/src/core/templates/template-registry.js +2 -2
- package/src/core/templates/template-seed.js +22 -0
- package/src/core/work-types.js +10 -10
- package/src/dashboard/app/App.jsx +0 -2
- package/src/dashboard/app/components/ActivityFeed.jsx +2 -3
- package/src/dashboard/app/components/CommandPalette.jsx +7 -8
- package/src/dashboard/app/components/EntityLink.jsx +1 -2
- package/src/dashboard/app/components/Markdown.jsx +1 -1
- package/src/dashboard/app/components/Sidebar.jsx +1 -2
- package/src/dashboard/app/hooks/useMorphQuery.js +1 -1
- package/src/dashboard/app/lib/phases.js +2 -4
- package/src/dashboard/app/pages/Activity.jsx +1 -1
- package/src/dashboard/app/pages/FeatureDetail.jsx +139 -129
- package/src/dashboard/app/pages/Features.jsx +9 -9
- package/src/dashboard/app/pages/Guide.jsx +2 -2
- package/src/dashboard/app/pages/PhasePipeline.jsx +3 -4
- package/src/dashboard/app/pages/RulesMap.jsx +3 -3
- package/src/dashboard/app/pages/SkillsLibrary.jsx +3 -3
- package/src/dashboard/app/pages/Standards.jsx +1 -1
- package/src/dashboard/scanner/activity-scanner.js +6 -16
- package/src/dashboard/scanner/agents-scanner.js +1 -1
- package/src/dashboard/scanner/docs-scanner.js +5 -23
- package/src/dashboard/scanner/features-scanner.js +95 -60
- package/src/dashboard/scanner/index.js +0 -2
- package/src/dashboard/scanner/project-api.js +1 -1
- package/src/dashboard/scanner/rules-scanner.js +15 -10
- package/src/dashboard/scanner/skills-scanner.js +2 -3
- package/src/dashboard/scanner/standards-scanner.js +2 -1
- package/src/lib/ci/ci-verify.js +17 -1
- package/src/lib/ci/github-ci.js +1 -1
- package/src/lib/detectors/index.js +3 -8
- package/src/lib/generators/handoff-generator.js +34 -65
- package/src/lib/generators/settings-generator.js +11 -89
- package/src/lib/git/evidence-staleness.js +1 -1
- package/src/lib/git/tree-fingerprint.js +19 -7
- package/src/lib/git/tree-state.js +2 -2
- package/src/lib/heavy/cleanup.js +1 -5
- package/src/lib/installers/memory-installer.js +6 -8
- package/src/lib/mutation/commands.js +3 -2
- package/src/lib/{tasks/dotnet-test-introspection.js → mutation/dotnet-introspection.js} +17 -282
- package/src/lib/mutation/plan.js +14 -6
- package/src/lib/mutation/runner.js +1 -1
- package/src/lib/mutation/subset.js +46 -9
- package/src/lib/plan/artifact-vocabulary.js +60 -0
- package/src/lib/plan/checks.js +234 -0
- package/src/lib/plan/plan-parser.js +209 -0
- package/src/lib/plan/plan-template.js +18 -0
- package/src/lib/review-reports.js +222 -0
- package/src/lib/risk-detector.js +134 -135
- package/src/lib/specs/adr-index.js +50 -69
- package/src/lib/specs/design-seed.js +18 -0
- package/src/lib/specs/frontmatter.js +44 -0
- package/src/lib/specs/gfm-table.js +17 -0
- package/src/lib/specs/old-format.js +68 -0
- package/src/lib/specs/revocations.js +37 -95
- package/src/lib/specs/screen-checklist.js +18 -17
- package/src/lib/stack/dotnet-build-ignores.js +47 -0
- package/src/lib/stack/stack-profile.js +1 -1
- package/src/lib/stack/stack-scan.js +267 -0
- package/src/lib/standards/registry.js +43 -0
- package/src/lib/standards/sections.js +58 -0
- package/src/lib/tasks/eval-node.js +4 -12
- package/src/lib/tasks/test-nodes.js +1 -74
- package/src/lib/tasks/test-runner.js +75 -117
- package/src/lib/telemetry/metrics.js +8 -69
- package/src/lib/telemetry/telemetry-reader.js +5 -118
- package/src/lib/telemetry/verify-event.js +5 -7
- package/src/lib/validators/code-budget/code-budget-validator.js +1 -1
- package/src/lib/validators/contracts/contract-compliance-validator.js +2 -2
- package/src/lib/validators/reuse/reuse-validator.js +24 -48
- package/src/lib/validators/reuse/symbol-scanner.js +2 -4
- package/src/lib/validators/traceability-check.js +85 -129
- package/src/lib/validators/validation-runner.js +8 -88
- package/src/lib/validators/verify-runner.js +134 -301
- package/src/lib/worktree/docker-audit.js +1 -2
- package/src/lib/worktree/fleet-scanner.js +25 -38
- package/src/scripts/setup-infra.js +42 -22
- package/src/utils/agents-installer.js +92 -13
- package/src/utils/claude-settings-manager.js +0 -35
- package/src/utils/file-copier.js +34 -6
- package/src/utils/hooks-installer.js +16 -9
- package/src/utils/skills-installer.js +1 -2
- package/framework/commands/commit.md +0 -166
- package/framework/evals/trace-schema.md +0 -67
- package/framework/hooks/claude-code/core/tasks-json-guard.js +0 -83
- package/framework/hooks/claude-code/core/trace-autogen.js +0 -277
- package/framework/hooks/git/pre-commit/specs.sh +0 -50
- package/framework/hooks/shared/tasks-validator.js +0 -111
- package/framework/rubrics/backend.json +0 -41
- package/framework/rubrics/default.json +0 -36
- package/framework/rubrics/frontend.json +0 -36
- package/framework/rules/morph-task-tracking.md +0 -54
- package/framework/rules/morph-workflow.md +0 -244
- package/framework/schemas/tasks.schema.json +0 -79
- package/framework/skills/core/morph-brainstorming/SKILL.md +0 -161
- package/framework/skills/core/morph-implement/SKILL.md +0 -194
- package/framework/skills/core/morph-proposal/SKILL.md +0 -152
- package/framework/skills/core/morph-stack-scan/SKILL.md +0 -145
- package/framework/templates/docs/proposal.md +0 -192
- package/framework/templates/docs/spec.md +0 -57
- package/framework/templates/docs/ui-components.md +0 -52
- package/framework/templates/docs/ui-design-system.md +0 -76
- package/framework/templates/docs/ui-flows.md +0 -167
- package/framework/templates/examples/spec-examples.md +0 -91
- package/framework/templates/feature/decisions.md +0 -124
- package/framework/templates/feature/recap.md +0 -145
- package/framework/templates/project/validate.js +0 -97
- package/framework/templates/tasks.template.json +0 -17
- package/src/commands/state/usecase.js +0 -143
- package/src/commands/tasks/dag.js +0 -181
- package/src/dashboard/app/pages/Rubrics.jsx +0 -97
- package/src/dashboard/scanner/rubrics-scanner.js +0 -12
- package/src/lib/agents/output-collector.js +0 -76
- package/src/lib/evaluator-report.js +0 -91
- package/src/lib/specs/acervo-format.js +0 -70
- package/src/lib/specs/acervo-lifecycle.js +0 -264
- package/src/lib/specs/done-criteria-check.js +0 -200
- package/src/lib/specs/usecase-check.js +0 -301
- package/src/lib/specs/usecase-promoter.js +0 -301
- package/src/lib/specs/usecase-registry.js +0 -237
- package/src/lib/tasks/dispatch-planner.js +0 -319
- package/src/lib/tasks/mermaid-renderer.js +0 -132
- package/src/lib/tasks/task-classifier.js +0 -30
- package/src/lib/tasks/task-parser.js +0 -209
- package/src/lib/tasks/tasks-json-parser.js +0 -296
- package/src/lib/tasks/test-scope.js +0 -597
- package/src/lib/validators/architecture/architecture-validator.js +0 -270
- package/src/lib/validators/architecture/index.js +0 -7
- package/src/lib/validators/css/css-validator.js +0 -340
- package/src/lib/validators/css/index.js +0 -7
- package/src/lib/validators/design-system/design-system-validator.js +0 -237
- package/src/lib/validators/design-system/index.js +0 -7
- package/src/lib/validators/score-aggregator.js +0 -244
- package/src/lib/validators/ui/index.js +0 -7
- package/src/lib/validators/ui/ui-contrast-validator.js +0 -422
package/framework/MORPH.md
CHANGED
|
@@ -1,359 +1,202 @@
|
|
|
1
1
|
# MORPH.md — Natural Language Harness
|
|
2
2
|
|
|
3
|
-
> Leia
|
|
4
|
-
> Ele define papéis, fases, outputs, standards, gates e skills do morph-spec.
|
|
5
|
-
> Não procure instruções em hooks — o harness vive aqui.
|
|
3
|
+
> Leia uma vez por sessão (e de novo após `/compact`). Os comandos imprimem a própria mecânica (sinais, vereditos, próximo passo); referência completa em `.morph/framework/CLI.md`.
|
|
6
4
|
>
|
|
7
|
-
> **Depois de ler:**
|
|
5
|
+
> **Depois de ler:** `.morph/state.json` é um índice fino e gitignored, reconstruído a cada load — use-o só para achar a feature ativa e nunca o edite (a edição se perde no próximo load). O estado autoritativo e commitado é `.morph/features/{feature}/feature.json`. Feature `in_progress` → assuma o papel da fase e continue; sem feature ativa → pergunte qual trabalhar.
|
|
8
6
|
|
|
9
7
|
---
|
|
10
8
|
|
|
11
9
|
## 0. Contrato de Autonomia
|
|
12
10
|
|
|
13
|
-
Entre gates, você opera
|
|
11
|
+
Entre gates, você opera sozinho: o dev valida, você executa.
|
|
14
12
|
|
|
15
13
|
| Situação | O que você faz |
|
|
16
|
-
|
|
|
17
|
-
| Gate
|
|
18
|
-
|
|
|
19
|
-
| Ambiguidade de escopo coberta pelo plano |
|
|
20
|
-
| Ambiguidade bloqueante (requisito ausente ou contraditório) |
|
|
21
|
-
|
|
|
22
|
-
| Verify verde e
|
|
23
|
-
| Verify vermelho ou
|
|
24
|
-
| 3 tentativas sem fechar |
|
|
25
|
-
| `verify` exit 3 (fila pesada cheia) | A fila já esperou: no máximo uma chamada nova, depois avise
|
|
14
|
+
| --- | --- |
|
|
15
|
+
| Gate aprovado (plano / uiux / review) | Avança para a próxima fase na hora |
|
|
16
|
+
| Fatia relatada na fase implement | Despacha a próxima fatia pronta sem esperar instrução |
|
|
17
|
+
| Ambiguidade de escopo coberta pelo plano | Resolve pelo lado conservador e registra no relatório |
|
|
18
|
+
| Ambiguidade bloqueante (requisito ausente ou contraditório) | Uma pergunta via `AskUserQuestion` |
|
|
19
|
+
| Todas as fatias relatadas | `morph-spec verify <feature>` uma vez, sem filtro, e cada cenário `Cn` com a evidência que o prova |
|
|
20
|
+
| Verify verde e cenários provados | Segue para a review, sem anúncio |
|
|
21
|
+
| Verify vermelho ou cenário sem evidência | Loop de correção autônomo com o feedback, até 3 tentativas, sem pausa humana |
|
|
22
|
+
| 3 tentativas sem fechar | `AskUserQuestion` (aceitar/continuar/pular) — o único ponto de pausa do loop. Nunca uma 4ª tentativa por conta própria nem re-dispatch: sem informação nova, ela repete o erro |
|
|
23
|
+
| `verify` exit 3 (fila pesada cheia) | A fila já esperou: no máximo uma chamada nova, depois avise. Nunca laço de espera |
|
|
26
24
|
|
|
27
|
-
**Regra de ouro:** dúvida que não bloqueia →
|
|
25
|
+
**Regra de ouro:** dúvida que não bloqueia → resolva e registre; dúvida que bloqueia → uma pergunta, no máximo. Vale **depois** do gate do plano: na abertura, o **modo entrevista** (`morph-plan` §3) pergunta até fechar o entendimento, e esse é o comportamento desejado.
|
|
28
26
|
|
|
29
|
-
**A prova é o código:** `morph-spec verify`
|
|
27
|
+
**A prova é o código:** `morph-spec verify` prova o determinístico; o cenário `Cn` do `checks.json` prova o comportamento (no CI: `verify {f} --ci`, mesmo stamp). Estilo é nota do revisor, nunca bloqueio.
|
|
30
28
|
|
|
31
29
|
---
|
|
32
30
|
|
|
33
31
|
## Stack baked-in
|
|
34
32
|
|
|
35
|
-
O harness conhece o stack
|
|
33
|
+
O harness conhece o stack. Só pergunte sobre tecnologia com ambiguidade real.
|
|
36
34
|
|
|
37
35
|
| Camada | Stack |
|
|
38
|
-
|
|
|
36
|
+
| --- | --- |
|
|
39
37
|
| Backend | .NET 10 + VSA (feature-folder: handler + validator + endpoint + errors + tests) |
|
|
40
38
|
| ORM/DB | EF Core + Neon (Postgres) |
|
|
41
|
-
|
|
|
42
|
-
|
|
|
43
|
-
| Erros | Result pattern com `result.Match()` (nunca exceptions como fluxo) |
|
|
44
|
-
| IA | Microsoft Agent Framework (MAF) — quando houver agentes |
|
|
39
|
+
| Erros | Result pattern com `result.Match()` |
|
|
40
|
+
| IA | Microsoft Agent Framework (MAF), quando houver agentes |
|
|
45
41
|
| Frontend | Next.js App Router + Tailwind + Framer Motion + Shadcn |
|
|
46
|
-
| Jobs async | Hangfire
|
|
42
|
+
| Jobs async | Hangfire, só com razão real |
|
|
47
43
|
|
|
48
44
|
Padrões proibidos (valem em todo código; os standards detalham):
|
|
49
|
-
- `Guid.NewGuid()` → `Guid.CreateVersion7()
|
|
50
|
-
-
|
|
51
|
-
-
|
|
52
|
-
- Camada de Service/Manager entre handler e dados
|
|
53
|
-
- Repository genérico (`IRepository<T>`/`IUnitOfWork`)
|
|
54
|
-
- SQL cru (`FromSqlRaw`, `ExecuteQuery(string)`) sem
|
|
55
|
-
- Redeclarar tipo/componente que já existe
|
|
56
|
-
|
|
57
|
-
Acesso a dados em VSA: `ApplicationDbContext` direto no slice (`DbSet<T>` já é repository, `DbContext` já é unit of work). Concorrência ou SQL específico → store dedicado hand-written com justificativa em `decisions.md`.
|
|
45
|
+
- `Guid.NewGuid()` → `Guid.CreateVersion7()`: o v7 é ordenado no tempo e não fragmenta o índice do Postgres.
|
|
46
|
+
- Classe não-`sealed` sem justificativa: herança aberta por acidente vira contrato que ninguém desenhou.
|
|
47
|
+
- Exception como fluxo de controle: o Result deixa o erro esperado no tipo, e a exception fica para o inesperado.
|
|
48
|
+
- Camada de Service/Manager entre handler e dados: no VSA o handler fala com o `ApplicationDbContext` direto; a camada só repassa chamada.
|
|
49
|
+
- Repository genérico (`IRepository<T>`/`IUnitOfWork`): `DbSet<T>` já é repository e `DbContext` já é unit of work.
|
|
50
|
+
- SQL cru (`FromSqlRaw`, `ExecuteQuery(string)`) sem ADR no `plan.md`: o LINQ é tipado e parametrizado; SQL específico ou concorrência vão para um store dedicado com o porquê no ADR.
|
|
51
|
+
- Redeclarar tipo/componente que já existe: duas definições divergem em silêncio. Antes de criar, `morph-spec graph explain <nome>` (sem grafo: `grep -rn`); criar exige `CRIAR` com `why` em `## Reuso` do `plan.md`.
|
|
58
52
|
|
|
59
53
|
---
|
|
60
54
|
|
|
61
55
|
## 1. Papéis
|
|
62
56
|
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
**Orchestrator** — ativo na abertura de uma feature e nas transições de fase. Lê o mandato, entende o escopo, propõe o plano de ataque, identifica dependências entre tarefas, garante que gates sejam respeitados antes de avançar. Anti-padrão: não escreve código — se percebe que começou a implementar, pare, você transitou de papel sem intenção.
|
|
57
|
+
A transição entre papéis é explícita: conclua ou registre no relatório antes de mudar.
|
|
66
58
|
|
|
67
|
-
**
|
|
59
|
+
**Orchestrator** — abertura e transições de fase: escopo, plano, gates. Não escreve código: se começou a implementar, trocou de papel sem querer.
|
|
68
60
|
|
|
69
|
-
**
|
|
61
|
+
**Specialist** — implementação: executa as fatias do plano, consulta os standards da fatia, grava `3-implement/reports/F{n}.md`. Não cria fatia nova: acréscimo pequeno vai no relatório; fato errado do plano vai em `## Errata` (§3); escopo mudou → `morph-spec unapprove {f} plan`, porque o plano aprovado está congelado.
|
|
70
62
|
|
|
71
|
-
|
|
63
|
+
**Evaluator** — o Gate 3 são sub-agents com contexto fresco, nunca quem implementou: `morph-verifier` prova cada `Cn` (default NÃO PROVADO), `morph-reviewer` julga o diff (escopo, arquitetura, regressão) e `morph-security` (opus, só com caminho sensível) procura o caminho de exploração. Revisor e segurança leem só o SHA revisado; a mutação do verificador espera os dois. Seguem `.morph/framework/evals/review-checklist.md`: `SHIP`/`FIX`, bloqueador só com evidência tipada. Não rodam a suíte nem reescrevem código.
|
|
72
64
|
|
|
73
65
|
---
|
|
74
66
|
|
|
75
67
|
## 2. Fases
|
|
76
68
|
|
|
77
|
-
|
|
69
|
+
Cada fase tem pasta em `.morph/features/{feature}/`. Identidade do projeto: `.morph/config/config.json` (commitado).
|
|
78
70
|
|
|
79
71
|
| Fase | Pasta | Gate | O que termina a fase |
|
|
80
|
-
|
|
|
81
|
-
|
|
|
82
|
-
|
|
|
83
|
-
| implement | `3-implement/` |
|
|
84
|
-
| review | `4-review/` | Gate 3 (trust-aware) | `
|
|
85
|
-
|
|
86
|
-
A fase `proposal` tem dois **modos de descoberta**, escolhidos pelo usuário na abertura (só `workType: feature`/`bug` — `chore`/`hotfix` nascem em `implement`): **entrevista** (uma pergunta por vez até a árvore de decisões abertas zerar; Gate 1 pausa sempre) e **automático** (até 4 perguntas em lote; Gate 1 trust-aware). Nos dois modos a varredura do ambiente roda **antes** de qualquer pergunta — fato que `morph-stack-scan` ou o acervo de use cases responde não vira pergunta. Detalhes em `morph-brainstorming`.
|
|
72
|
+
| --- | --- | --- | --- |
|
|
73
|
+
| plan | `2-plan/` | plano (trust-aware) | `plan.md` + `checks.json` (`plan-check`) aprovados |
|
|
74
|
+
| uiux (opcional) | `1-design/` | uiux (trust-aware) | design e checklist de tela aprovados |
|
|
75
|
+
| implement | `3-implement/` | nenhum | toda fatia com relatório final em `reports/F{n}.md` |
|
|
76
|
+
| review | `4-review/` | Gate 3 (trust-aware) | `verifier.md` + `reviewer.md` (+ `security.md`) e o gate aprovado |
|
|
87
77
|
|
|
88
|
-
|
|
78
|
+
Sequência: `plan → [uiux] → implement → review`. Não avance sem o gate da fase.
|
|
89
79
|
|
|
90
|
-
|
|
80
|
+
A fase `plan` abre com a escolha do **modo de descoberta** (só `feature`/`bug`): **entrevista** (uma pergunta por vez até a árvore de decisões zerar; o gate do plano pausa sempre, porque confirmar o entendimento compartilhado é o gate) ou **automático** (até 4 perguntas, só sobre nós abertos; gate trust-aware). Nos dois, a varredura roda antes de qualquer pergunta: fato que `morph-spec stack-scan`, o contexto ou os ADRs respondem não vira pergunta. Detalhes em `morph-plan`.
|
|
91
81
|
|
|
92
82
|
### 2.1 Roteamento por tipo de trabalho
|
|
93
83
|
|
|
94
|
-
|
|
84
|
+
Toda feature nasce com `description` obrigatória e um `workType`: `morph-spec create <f> --description "<o quê/porquê>" --type <tipo>` (ou `--request "<pedido>"`, que classifica e semeia a descrição).
|
|
95
85
|
|
|
96
86
|
| Tipo | Pipeline | Gates |
|
|
97
|
-
|
|
|
98
|
-
| `feature` |
|
|
99
|
-
| `bug` |
|
|
100
|
-
| `chore` |
|
|
101
|
-
| `hotfix` | scout (diagnóstico read-only) → fix cirúrgico →
|
|
102
|
-
|
|
103
|
-
**Ramo uiux (critério objetivo):** feature/bug que cria ou altera superfície de UI (componente, página, tela, estilo, fluxo de navegação) toma o ramo `1-design/` via `morph-spec advance {feature} --design`; sem superfície de UI, direto para plan. Skill: `morph-uiux`. Avaliado por `morph-proposal`/`morph-brainstorming` no fecho do Gate 1 — não redecida em nenhum outro ponto do pipeline.
|
|
87
|
+
| --- | --- | --- |
|
|
88
|
+
| `feature` | plan → [uiux] → implement → review | plano, [uiux], review |
|
|
89
|
+
| `bug` | plano enxuto (repro + diagnóstico) → implement → review | plano, review |
|
|
90
|
+
| `chore` | `plan.md` curto, gate do plano carimbado por política → implement → review leve | só review |
|
|
91
|
+
| `hotfix` | scout (diagnóstico read-only) → fix cirúrgico → aprovação humana obrigatória → test loop → ship | 3, sempre humano |
|
|
104
92
|
|
|
105
|
-
**
|
|
93
|
+
**Ramo uiux (critério objetivo):** feature/bug que cria ou altera superfície de UI (componente, página, tela, estilo, navegação) toma o ramo `1-design/` depois do gate do plano (`morph-spec advance {feature} --design`, também com o gate já aprovado pelo humano; nunca `1-design/` à mão); sem superfície de UI, direto para implement. Skill: `morph-uiux`. A `morph-plan` §6 decide uma vez; nenhum outro ponto redecide.
|
|
106
94
|
|
|
107
|
-
**
|
|
95
|
+
**Router:** `create --request` classifica por palavra-chave. Exit 2 (empate ou nenhum sinal) imprime os candidatos: você decide como roteador e re-roda com `--type`. `AskUserQuestion` só quando o pedido é genuinamente indeterminado.
|
|
108
96
|
|
|
109
|
-
**
|
|
97
|
+
**Skip:** `chore`/`hotfix` nascem com o gate `plan` carimbado por política e começam em `implement`; escrevem um `2-plan/plan.md` curto (uma fatia; no hotfix, C1 = sintoma ausente, C2 = regressão) e rodam `plan-check`. Mudança: `morph-spec retype <f> <tipo>` (só antes do Gate 3; o esqueleto intocado do plano sai junto).
|
|
110
98
|
|
|
111
|
-
**
|
|
99
|
+
**Branch:** toda feature nasce em `morph/{f}`, ramificada da default, com ou sem `--worktree`, e fecha igual nos dois com `morph-spec finish <f> --pr|--merge` (§2.2).
|
|
112
100
|
|
|
113
101
|
### 2.2 Desenvolvimento paralelo por worktree (frota)
|
|
114
102
|
|
|
115
|
-
Features independentes
|
|
103
|
+
Features independentes rodam em paralelo, uma por worktree e uma instância de Claude Code por worktree: `create <f> --worktree` (ou `worktree setup <f>`) na branch `morph/{f}`.
|
|
116
104
|
|
|
117
|
-
- **Uma feature = um worktree = uma instância.**
|
|
118
|
-
- `feature.json` viaja
|
|
119
|
-
- **Só o morph cria worktree:** `worktree setup <f>` (feature) ou `worktree provision <n>` (isolamento de
|
|
120
|
-
- **Só o morph remove worktree.**
|
|
121
|
-
- **Ambiente dedicado:** setup escreve `.morph/worktree.env` (`PORT`, `API_PORT
|
|
122
|
-
- **
|
|
123
|
-
-
|
|
124
|
-
- **
|
|
125
|
-
- **Ownership
|
|
126
|
-
- **Fechamento:** aprove o Gate 3
|
|
105
|
+
- **Uma feature = um worktree = uma instância.** Duas instâncias na mesma feature: o setup recusa (exit 3).
|
|
106
|
+
- `feature.json` viaja commitado em `morph/{f}`; a cópia da raiz é esqueleto. Mutadores recusam gravar fora da árvore dona.
|
|
107
|
+
- **Só o morph cria worktree:** `worktree setup <f>` (feature) ou `worktree provision <n>` (isolamento de fatia, branch `morph-task/<n>`). `git worktree add` cru é bloqueado; `EnterWorktree`/`-w`/`isolation:"worktree"` passam pelo hook `WorktreeCreate` e caem no contêiner (`worktrees/` ou `worktree.root`); fora dele = criado sem o morph (`doctor --worktrees`). Já existe: abra o `claude` DENTRO dela; `EnterWorktree(path)` sempre pede aprovação. Infra (`node_modules`, `.claude`, `.morph/framework`) entra por junction; faltou → `worktree link --all`.
|
|
108
|
+
- **Só o morph remove worktree.** `git worktree remove` (com ou sem `--force`), `rm -rf`, `Remove-Item -Recurse` e o explorador **atravessam a junction** e apagam o conteúdo real da raiz (`.claude`, `node_modules`, `.morph/framework`), saindo com sucesso. Só o morph desmonta a junction antes de remover: fechar a feature = `morph-spec finish <f> --pr|--merge`; só desmontar = `morph-spec worktree remove <f>` (ou `--target <path>`). Sobra de sub-agent (`agent-<hex>`): `worktree reap` remove só a que parou limpa e sem commit exclusivo.
|
|
109
|
+
- **Ambiente dedicado:** o setup escreve `.morph/worktree.env` (`PORT`, `API_PORT`, `POSTGRES_PORT`, `COMPOSE_PROJECT_NAME=morph-{f}`) e cada worktree sobe o seu compose; o hook de Bash injeta as variáveis (fora do Claude, `eval "$(morph-spec env)"`). Porta fixa ou `container_name` no compose reprova o nó e2e. `finish` derruba o stack com volumes (`--keep-volumes` preserva). Build/testes/e2e disputam 2 slots por usuário (`heavy status`): exit 3 é fila cheia, não vermelho; fora do `verify`, `heavy run -- <cmd>`.
|
|
110
|
+
- **Migração destrutiva → integre antes de abrir irmãos:** os irmãos ramificam do schema velho e quebram no merge.
|
|
111
|
+
- **`node_modules` é junction compartilhada:** dependência mudada afeta todos os irmãos; integre antes de seguir em paralelo.
|
|
112
|
+
- **Handoff:** `.morph/features/{f}/handoff.md` (regenerável por `morph-spec handoff <f>`): leia antes de re-derivar contexto; nunca edite.
|
|
113
|
+
- **Ownership:** sem lock; colisão se resolve no plano (ondas do `plan-check`) e por construção (uma feature = um escritor). Visão agregada: `fleet`.
|
|
114
|
+
- **Fechamento:** aprove o Gate 3 e rode `morph-spec finish <f> --pr|--merge`. `--merge` integra na hora (`--no-ff` local, sem push). **`--pr` não integra:** só abre o PR, e a feature fica `aguardando-merge` até alguém mergear — nunca "entregue" só por `finished: true`. Nos dois, o worktree é desmontado e as portas liberadas.
|
|
127
115
|
|
|
128
116
|
---
|
|
129
117
|
|
|
130
118
|
## 3. Contratos de Output
|
|
131
119
|
|
|
132
|
-
Cada fase salva seus artefatos nos caminhos exatos abaixo — não invente alternativos.
|
|
133
|
-
|
|
134
|
-
### Proposal (`0-proposal/`)
|
|
135
|
-
|
|
136
|
-
- `proposal.md` — descrição da feature, problema que resolve, escopo, riscos. **Sem critérios de aceite:** o comportamento verificável mora nos use cases (`2-plan/usecases/`), destilados na fase plan — duplicar aqui produz duas fontes que divergem no primeiro ajuste. Máximo ~2 páginas; além disso, o escopo pede corte antes de avançar.
|
|
137
|
-
|
|
138
120
|
### Plan (`2-plan/`)
|
|
139
121
|
|
|
140
|
-
- `
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
`id` sequencial **no projeto**, não na feature — alocado por `morph-spec usecase reserve`, nunca por scan manual. Status: `draft` → `approved` (Gate 2) → `implemented` (promoção no `finish`) — descritivo, quem trava fase é o gate. **Editável depois do Gate 2**, por design (muda comportamento, re-roda `implement`, auditoria no git). Obrigatoriedade por tipo de trabalho: ver `morph-plan`.
|
|
145
|
-
|
|
146
|
-
- `spec.md` — especificação técnica, lida uma vez por sessão (relida após `/compact`): arquitetura, componentes, integrações, fluxos de dados, edge cases **técnicos**. Responde **como** os use cases serão realizados — não repete o comportamento. Deve bastar para implementar sem perguntas básicas. Inclui `## Contrato de implementação`: standards, proibições da feature, **verificação de runtime** (como o stack sobe, que fluxos são exercitados, setup de auth) — baseline como comando, pré-requisito como predicado. Lido uma vez por sessão (relido após `/compact`).
|
|
147
|
-
|
|
148
|
-
- `tasks.json` — validada contra `.morph/framework/schemas/tasks.schema.json`. Cada task: `id` (T1, T2...), `title`, `description`, `dependencies` (IDs), `effort`, `doneCriteria`, `status`, `outputs` (paths esperados), `usecase` (opcional — **ID** do use case, `UC-07`, nunca o nome do arquivo). `doneCriteria` de task com `usecase` carrega a **pós-condição literal**, com rótulo (`"P2 — cada veterinário traz..."`). Toda entrada do recap.md referencia um ID do tasks.json.
|
|
122
|
+
- `plan.md` — fonte única da feature, esqueleto escrito pelo `create` (chore/hotfix: você o cria), gramática em `morph-spec plan-check --help`: problema, fora de escopo, suposições, cenários `C1..Cn` (observáveis em teste, com `prova:`), decisões em ADR (`**Alcance:** feature|projeto`; conflitos sempre presentes), arquitetura, reuso, fatias `F1..Fn` (persona, standards, ≤ 8 arquivos, `cobre:`) e contrato de implementação (baseline como comando, pré-requisito como predicado). Lido uma vez por sessão e pós-`/compact`.
|
|
123
|
+
- `checks.json` — extraído do `plan.md` por `morph-spec plan-check`, o único escritor; é a régua que o verificador prova item a item.
|
|
124
|
+
- `stack-scan.md` e `scout-map.md` (§6) — insumos do plano.
|
|
149
125
|
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
**Errata no spec congelado:** congelar o CONTRATO não é congelar um ERRO DE FATO. Se a spec afirma sobre o código algo que o código desmente, acrescente um bloco `## Errata` no FIM do arquivo — corpo intacto, append-only, aceito pelo `protect-spec-files` sem revogar gate. Mudança de ESCOPO continua exigindo revogar o gate e re-aprovar.
|
|
126
|
+
**Congelamento:** aprovado o gate do plano, o corpo do `plan.md` trava: quem implementa não afrouxa o critério que prova o trabalho. Congelar o contrato não é congelar um erro de fato: o que o código desmente vai num bloco `## Errata` no fim do arquivo, append-only e fora do `planHash`. Mudança de escopo exige `morph-spec unapprove {f} plan`, `plan-check` e re-aprovar.
|
|
153
127
|
|
|
154
128
|
### Implement (`3-implement/`)
|
|
155
129
|
|
|
156
|
-
- `
|
|
157
|
-
- `evidencias/{
|
|
130
|
+
- `3-implement/reports/F{n}.md` — um por fatia, do sub-agent ou do orquestrador quando inline; ausente = pendente, `PARCIAL` na 1ª linha = parcial. São o registro da implementação (`**Arquivos:**`, `**Standards:**`; não há recap). Formato em `morph-apply`.
|
|
131
|
+
- `3-implement/evidencias/{Cn}.md` — no cenário `prova: eval` (entrada, modelo, saída, veredito) ou `prova: manual` (passo e resultado).
|
|
158
132
|
|
|
159
133
|
### Review (`4-review/`)
|
|
160
134
|
|
|
161
|
-
- `
|
|
162
|
-
- `review-report.md` — síntese do orquestrador: `**Reviewed-SHA:**`, veredito, bloqueadores e o resultado do e2e.
|
|
163
|
-
|
|
164
|
-
### Acervo de use cases (`.morph/specs/usecases/`)
|
|
165
|
-
|
|
166
|
-
Acervo permanente do projeto: `UC-{nn}-{slug}.md`, **commitado**. Descrição viva do comportamento do sistema, sobrevive ao arquivamento — diferente dos traces, **faz parte da entrega**.
|
|
167
|
-
|
|
168
|
-
- **Quem escreve:** `morph-spec finish` promove os use cases da feature para cá **dentro do commit de arquivamento**, na branch `morph/{f}`, com `status: implemented` — com o estado arquivado (§2.2), nunca pós-merge.
|
|
169
|
-
- **O que é cobrado mecanicamente:** `morph-spec dag {feature}` cruza `tasks.json` com os use cases — `UC-{nn}` inexistente é **erro** (não despacha); pós-condição órfã, `doneCriteria` parafraseado e vocabulário de artefato sem `Por que artefato:` são avisos. Cobre o *encanamento*; se a pós-condição é observável em teste continua sendo critério do Gate 2 e do avaliador.
|
|
170
|
-
- **Via única de escrita:** a promoção lê **só** de `{feature}/2-plan/usecases/`. Nunca edite `.morph/specs/usecases/` à mão — pula `status: implemented`, a sobrescrita por ID e o commit escopado, criando duas verdades. Mudar um UC existente (caso `bug`): copie para `2-plan/usecases/` da feature, corrija lá, deixe o `finish` sobrescrever.
|
|
171
|
-
- **Quando chega na default:** em `--merge`, no merge `--no-ff`; em `--pr`, só quando mergeado — o acervo descreve o que foi **integrado**, não proposto.
|
|
172
|
-
- **Sobrescrita por ID:** `UC-07` existente é substituído pela versão integrada, mesmo com slug novo — exatamente um arquivo por ID.
|
|
173
|
-
- **Fail-open:** feature sem `2-plan/usecases/` promove nada, em silêncio — a promoção nunca impede o fechamento.
|
|
174
|
-
- **Colisão entre features paralelas:** `usecase reserve` aloca de um contador comum aos worktrees; colisão residual faz o `finish` recusar promover só aquele UC (recuperação que ele prescreve: renumere e promova à mão).
|
|
175
|
-
|
|
176
|
-
### Traces (`.morph/traces/`)
|
|
177
|
-
|
|
178
|
-
Cada fase produz um trace JSON em `.morph/traces/YYYY-MM-DD-{feature}-{phase}.json` (formato em `.morph/framework/evals/trace-schema.md`). **Gerado automaticamente pelo hook `trace-autogen`** a cada write de `tasks.json`, nunca à mão. Ignorado pelo git: análise do harness, não entrega da feature.
|
|
135
|
+
- `verifier.md`, `reviewer.md`, `security.md` (só com caminho sensível) — `**Verdict:** SHIP|FIX`, `**Reviewed-SHA:**`, `## Bloqueadores` (tipo + evidência), notas. O do verificador traz `## Checks` (`| Cn | PROVADO|NÃO PROVADO|FALHA | evidência |`). Append-only: vale o último veredito.
|
|
179
136
|
|
|
180
137
|
---
|
|
181
138
|
|
|
182
139
|
## 4. Como consultar Standards
|
|
183
140
|
|
|
184
|
-
|
|
141
|
+
Nunca carregue todos os standards: custa contexto em toda chamada e você não sabe quais importam antes de começar. Disclosure progressivo, por fatia:
|
|
185
142
|
|
|
186
|
-
|
|
143
|
+
1. `morph-spec standards --find "<domínio/tecnologia da fatia>"` → top 3 como `id · path · digest`, com as âncoras de seção. O `digest` costuma bastar.
|
|
144
|
+
2. Não bastou → `morph-spec standards --show <id>#<âncora>` imprime só aquela seção.
|
|
145
|
+
3. Só então o arquivo inteiro (campo `path`), quando precisar do exemplo completo.
|
|
146
|
+
4. Registre no `**Standards:**` do relatório qual standard aplicou. Dois em conflito → o mais específico ao stack, com o conflito no relatório. Nenhum cobre o caso → registre o critério adotado; não invente standard, porque padrão não documentado é dívida disfarçada.
|
|
187
147
|
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
1. Antes de iniciar uma tarefa, identifique 1-3 standards relevantes — rode `morph-spec standards --find "<domínio/tecnologia da task>"` (devolve o top 3 como `id · path · digest`) em vez de filtrar `id`/`tags` à mão no JSON.
|
|
191
|
-
2. Leia apenas o arquivo `.md` daquele standard (campo `path`).
|
|
192
|
-
3. Aplique durante a implementação. Se precisar de mais contexto, leia mais um standard.
|
|
193
|
-
4. Registre no recap.md qual standard foi consultado e como foi aplicado.
|
|
194
|
-
|
|
195
|
-
**Como identificar o standard certo:** filtre por `category` primeiro (ex: "architecture", "contracts", "testing"), depois por `tags` (ex: "dotnet", "nextjs", "blazor"). Dois standards relevantes em conflito → adote o mais específico ao stack do projeto e registre o conflito no decisions.md.
|
|
196
|
-
|
|
197
|
-
O agente responsável por um domínio está em `.morph/framework/agents.json` (fonte única — os subagents `morph-{id}` são gerados dele). O campo `persona` define o ponto de vista e o nível de rigor a adotar ao aplicar os standards daquele domínio trabalhando inline (um agente de arquitetura é mais rígido que um de suporte mensal).
|
|
198
|
-
|
|
199
|
-
**Quando não há standard adequado:** registre no decisions.md que nenhum cobre o caso, descreva o critério adotado, sinalize para revisão futura. Não invente um standard — padrão não documentado é dívida técnica disfarçada.
|
|
148
|
+
Inline, o campo `persona` do domínio em `.morph/framework/agents.json` dá o ponto de vista e o rigor.
|
|
200
149
|
|
|
201
150
|
---
|
|
202
151
|
|
|
203
152
|
## 5. Gates de Aprovação (Trust Mode)
|
|
204
153
|
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
```
|
|
208
|
-
- "aprovado, prosseguir"
|
|
209
|
-
- "preciso ajustar"
|
|
210
|
-
- "cancelar feature" (Gate 3 usa "rollback" em vez de "cancelar")
|
|
211
|
-
```
|
|
212
|
-
|
|
213
|
-
**Sinais de risco que forçam pausa em auto** (`gate-check` decide via `shouldPauseGate` — fonte única; sinal que só a sessão conhece escala via `gate-decision` manual):
|
|
154
|
+
Em `trust: "auto"` (default, `.morph/config/config.json → trust`), um gate sem sinal de risco passa com um resumo curto. Em `trust: "manual"` ou com sinal de risco, pausa via `AskUserQuestion` com as opções `"aprovado, prosseguir"` / `"preciso ajustar"` / `"cancelar feature"` (no Gate 3, `"rollback"` no lugar de cancelar).
|
|
214
155
|
|
|
215
|
-
|
|
216
|
-
|---|---|---|
|
|
217
|
-
| `designSystemDivergence` | true | Fontes de design conflitantes |
|
|
218
|
-
| `standardsViolations` | array.length > 0 | Plano ou código viola padrões proibidos |
|
|
219
|
-
| `evaluatorVerdict` | ≠ SHIP, bloqueador, ou ausente | Veredito do `evaluator-report`: `FIX`, bloqueador aberto, bloqueador sem tipo, ou relatório sem `**Verdict:**`. Só no **ship** |
|
|
220
|
-
| `verificationStatus` | === 'fail' | `verify` vermelho — build, testes, validadores **ou e2e**. Vale em **qualquer** gate |
|
|
221
|
-
| `verificationStale` | true | Stamp do `verify` com sha != HEAD: o verde é de outro código. Só no **ship** |
|
|
222
|
-
| `e2eSkipClass` (derivada) | environment/requested/unknown | e2e pulou sem dispensa legítima (só `project`/`scope`). Só no **ship** |
|
|
223
|
-
| `verificationScope` | !== `feature` (presente) | Stamp do `verify` é de escopo parcial (`task:{id}`) — não cobre a feature inteira. Só no **ship** |
|
|
224
|
-
| `promptModel` | prompt/modelo tocado | Sem nó `evals` declarado, ou eval pulado neste verify. Só no **ship** |
|
|
225
|
-
| `mediaClaims` | seção ausente | Feature que gera mídia, relatório sem `## Mídia gerada`. Só no **ship** |
|
|
226
|
-
| `screenChecklist` | item em aberto | **uiux**: tela sem checklist completo, ou nenhuma `## Tela:`. **ship**: item decidido sem linha em `## Checklist de tela` |
|
|
227
|
-
| `taskCount` | > 20 | Escopo grande — revise antes de implementar |
|
|
228
|
-
| `oversizedTasks` | > 8 `outputs` | Task não cabe num dispatch. Só no **plano** |
|
|
229
|
-
| `workType` | === 'hotfix' | Gate 3 pausa SEMPRE (ver "Gates por tipo de trabalho") |
|
|
156
|
+
**Quem decide é o código:** `morph-spec gate-check <feature> <gate>` coleta os sinais do disco, decide a pausa (`shouldPauseGate`), grava `gateDecisions` e imprime o sinal que pausou. Só o que a sessão sabe e o disco não mostra entra por `--signals`:
|
|
230
157
|
|
|
231
|
-
|
|
|
232
|
-
|
|
233
|
-
|
|
|
234
|
-
|
|
|
235
|
-
| uiux — Design | `screenChecklist` | `morph-uiux` |
|
|
236
|
-
| 3 — Review | `evaluatorVerdict`, `standardsViolations` em implementation, `verificationStale`, `verificationScope`, `e2eSkipClass`, `promptModel`, `mediaClaims`, `screenChecklist` | `morph-review` |
|
|
158
|
+
| Sinal | Quando você o passa |
|
|
159
|
+
| --- | --- |
|
|
160
|
+
| `designSystemDivergence` | fontes de design conflitantes (tokens, versão, fonte aprovada) |
|
|
161
|
+
| `standardsViolations` | plano ou código viola um padrão proibido (lista não vazia) |
|
|
237
162
|
|
|
238
|
-
|
|
163
|
+
Risco que nenhum sinal representa: `morph-spec gate-decision <feature> <gate> --pause <bool> --reason <txt>`. Nunca edite `gateDecisions` à mão — colide com o hook `state-sync`. A tabela completa de sinais está em CLI.md (`gate-check`).
|
|
239
164
|
|
|
240
|
-
|
|
165
|
+
**Gates por tipo:** `chore`/`hotfix` pulam o gate do plano (carimbado por política no nascimento); o Gate 3 vale para todos. Em `hotfix` o Gate 3 é sempre humano, mesmo em `trust: auto` (`approve … review --mode auto` recusa; use `--approver`), e exige só `4-review/verifier.md`, escrito pelo orquestrador. Os demais exigem `verifier.md` e `reviewer.md` (+ `security.md` com caminho sensível), cobrados pelo `approve` — ou `--self-assessed`, que fica registrado e marcado no `list`.
|
|
241
166
|
|
|
242
|
-
**
|
|
243
|
-
|
|
244
|
-
**A aprovação de gate é unificada nos comandos da CLI — nunca edite o estado à mão.** Em `trust: "auto"` (sem `AskUserQuestion`): `morph-spec approve <feature> <gate> --mode auto`; `morph-spec advance <feature>` aprova o gate corrente **e** cria a pasta da próxima fase (`--design` = ramo opcional de uiux). **O hook state-sync.js** cobre o caminho manual: `AskUserQuestion` respondida com label "aprovado" → registra o gate no `feature.json` autoritativo com `approvedBy: "manual"`. **A feature é identificada pelo nome que a pergunta cita** — grava na árvore dona dela, nunca na "feature ativa" da sessão. Pergunta sem nome numa árvore com mais de uma feature: o hook **recusa gravar** e avisa — aprove por `morph-spec approve`.
|
|
245
|
-
|
|
246
|
-
**Registre quem aprovou (`approvedBy`):** objeto `{ approved, timestamp, approvedBy }`. `"auto"` — política `trust: auto` sem decisão humana. `"manual"` — humano aprovou (via `AskUserQuestion` ou, em headless, texto iniciado em "aprovado"); em `trust: manual` todo gate é `"manual"` — nunca `"auto"` num gate humano.
|
|
247
|
-
|
|
248
|
-
**O hook gate-guard.js** confere, sem bloquear, se a ação num gate (pausar vs auto-aprovar) bateu com a decisão persistida. **Default:** `gate-check <feature> <gate> [--signals <json>] [--json]` decide via `shouldPauseGate`; `--signals` sobrescreve só o que o disco não expõe (`designSystemDivergence`, `standardsViolations`). **Escape manual** (sinal que `shouldPauseGate` não representa): `gate-decision <feature> <gate> --pause <bool> [--reason <txt>] [--signals <json>]`. Ambos gravam `gateDecisions[gate] = { pause, reason, signals, trust, decidedAt }` server-side (`.morph/framework/schemas/feature.schema.json`). **Nunca edite `gateDecisions` à mão** — colide com state-sync. Divergência → o guard avisa no contexto.
|
|
167
|
+
**Aprovar é sempre pela CLI, nunca editando o estado:** em `trust: auto`, `morph-spec approve <feature> <gate> --mode auto`, ou `morph-spec advance <feature>` (aprova e cria a pasta da próxima fase; `--design` toma o ramo uiux). No caminho humano, o hook `state-sync` grava a resposta do `AskUserQuestion` que começa com "aprovado" ou contém "pode avançar", "pode implementar" ou "pode prosseguir"; outra frase não grava, e aí se aprova por `morph-spec approve`. **A pergunta nomeia a feature** ("Gate do plano — Plano de {feature} aprovado?"): é por esse nome que o hook acha o `feature.json` certo, e sem nome numa árvore com mais de uma feature ele recusa gravar.
|
|
249
168
|
|
|
250
169
|
---
|
|
251
170
|
|
|
252
171
|
## 6. Sub-agents
|
|
253
172
|
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
**Despache um sub-agent por padrão quando a tarefa atende a pelo menos um destes gatilhos:**
|
|
257
|
-
|
|
258
|
-
- **Domínio diferente do contexto corrente** (ver `agents.json → domains`) — ex: backend agora, próxima task é frontend/UI/dados. Gatilho mais importante: cada domínio tem sua persona e standards, e o sub-agent escopado os carrega sem inchar seu contexto.
|
|
259
|
-
- **Esforço L ou XL** (> 5 minutos).
|
|
260
|
-
- Mais de 3 tentativas de correção falharam no mesmo problema.
|
|
261
|
-
- Análise de arquivo com mais de 500 linhas.
|
|
262
|
-
- Tarefa repetitiva com mais de 3 instâncias do mesmo padrão.
|
|
263
|
-
- Risco de "contaminar" o contexto principal com detalhes de baixo nível irrelevantes.
|
|
264
|
-
|
|
265
|
-
Inline (sem dispatch) é aceitável para tasks curtas (S/M) **dentro do domínio já carregado em contexto**. Inline numa task que dispara um gatilho acima → **registre a justificativa em uma linha no decisions.md** — inline silencioso numa task pesada/multi-domínio é o anti-padrão.
|
|
173
|
+
Trabalho pesado ou de outro domínio vai para um sub-agent com persona e standards escopados — o modo padrão, porque ele carrega o domínio sem inchar o contexto principal. Despache quando houver:
|
|
266
174
|
|
|
267
|
-
**
|
|
175
|
+
- **domínio diferente do corrente** (backend agora, a próxima fatia é frontend/UI/dados) — o gatilho mais importante;
|
|
176
|
+
- esforço L/XL (> 5 min), arquivo com mais de 500 linhas, mais de 3 repetições do mesmo padrão, ou detalhe de baixo nível que contaminaria o contexto.
|
|
268
177
|
|
|
269
|
-
|
|
178
|
+
Inline vale para fatia pequena no domínio já carregado; inline numa fatia que dispara um gatilho exige uma linha de porquê no relatório. Não despache quando o overhead passa da economia ou a fatia muda arquitetura que você precisa validar antes.
|
|
270
179
|
|
|
271
|
-
**
|
|
180
|
+
**Mecanismo:** `subagent_type: "morph-{id}"` (ex.: `morph-dotnet-senior`); a persona é o system prompt, gerada de `agents.json` em `.claude/agents/`. `morph-verifier`, `morph-reviewer`, `morph-security` e `morph-scout` são read-only. Tipo não registrado: `general-purpose` com o `persona` colado no prompt, registrado no relatório da fatia.
|
|
272
181
|
|
|
273
|
-
**
|
|
182
|
+
**Scout:** `morph-scout` localiza com `morph-spec graph affected|explain` e cai para grep sem grafo. Obrigatório no início de um hotfix, default no plano de feature grande ou brownfield (`morph-plan` §4). Devolve um mapa (Observado/Inferido) em `2-plan/scout-map.md`; rode `morph-spec scout-check <mapa> --json` antes de usá-lo. Reprovado → re-despache uma vez com as falhas; segunda reprovação → grep você mesmo e escale.
|
|
274
183
|
|
|
275
|
-
**O
|
|
276
|
-
um `idle_notification` sem texto — a última mensagem **pode não chegar** inteira, por isso não é o
|
|
277
|
-
canal autoritativo. O sub-agent **sempre** grava o relatório num arquivo canônico:
|
|
184
|
+
**O prompt leva só o que muda por fatia** (`morph-apply` §3): cenários que ela cobre, arquivos, standards, caminho do relatório. As cláusulas fixas de todo dispatch de implementador vivem no corpo gerado da persona (`## Contrato de dispatch`), o único texto que todo dispatch carrega. Não passe histórico da conversa nem saída de outras tarefas.
|
|
278
185
|
|
|
279
|
-
|
|
280
|
-
- Avaliador do Gate 3 (`morph-evaluator`): `.morph/features/{feature}/4-review/evaluator-report.md` — relatório BRUTO; a `morph-review` o lê e sintetiza o `review-report.md` do Gate 3 (nunca colidem: um é saída crua do sub-agent, o outro é curadoria do orquestrador).
|
|
281
|
-
|
|
282
|
-
O orquestrador **lê o arquivo** ao retomar controle; a mensagem, se chegou inteira, só poupa a leitura.
|
|
186
|
+
**O arquivo é o retorno; a última mensagem é cortesia.** O evento de volta às vezes é só um `idle_notification` sem texto, então a mensagem pode não chegar. O sub-agent sempre grava o relatório no caminho canônico — `3-implement/reports/F{n}.md` por fatia; `4-review/{verifier,reviewer,security}.md` no Gate 3 — e o orquestrador lê o arquivo ao retomar o controle.
|
|
283
187
|
|
|
284
188
|
### Protocolo de auditoria do relatório
|
|
285
189
|
|
|
286
|
-
|
|
287
|
-
perdido o meio de gravá-lo (ex.: o worktree sumiu). E relatório PRESENTE também não
|
|
288
|
-
basta: um gravado cedo demais fica completo e desatualizado.
|
|
289
|
-
|
|
290
|
-
A pergunta que decide não é "o relatório chegou?", é **"o TRABALHO entrou, e é isto que ele diz?"** —
|
|
291
|
-
respondida por evidência, não pela palavra do agente:
|
|
292
|
-
|
|
293
|
-
```
|
|
294
|
-
morph-spec report-check <feature> [task...] --json
|
|
295
|
-
```
|
|
296
|
-
|
|
297
|
-
| veredito | o que significa | ação |
|
|
298
|
-
| --- | --- | --- |
|
|
299
|
-
| `ok` | relatório presente, com arquivos e critérios, e mais novo que o trabalho | siga o fluxo |
|
|
300
|
-
| `report-stale` | relatório completo mas **VELHO**: a task escreveu arquivos DEPOIS de ele ser gravado (o agente relatou cedo e continuou; ex.: "teste ainda não escrito" com os testes já no disco) | **não re-despache** — leia `observed` (writes reais do `events.jsonl`, não `outputs` auto-declarado) e atualize o relatório a partir dessa evidência |
|
|
301
|
-
| `report-incomplete` | relatório existe, faltam itens (ele lista quais) | complete a partir da mensagem de retorno, carimbe **DEGRADADO** |
|
|
302
|
-
| `work-landed-report-missing` | sem relatório, mas os `outputs` da task estão no disco | **não re-despache** — grave você mesmo o relatório canônico a partir da mensagem de retorno, carimbado **DEGRADADO** |
|
|
303
|
-
| `no-work-no-report` | sem relatório e sem output | re-despache **uma** vez com o mesmo prompt |
|
|
304
|
-
| `report-missing-evidence-unknown` | sem relatório e a task não declarou `outputs` | re-despache (sem evidência, o conservador é o certo) |
|
|
305
|
-
|
|
306
|
-
Sai 0 só em `ok`. Todo caminho degradado é **registrado** no recap e nas `notes` da task, nunca
|
|
307
|
-
aceito em silêncio. Segunda ausência sem trabalho entregue é falha real: escale ao humano.
|
|
190
|
+
Relatório ausente não prova que o agente falhou, e relatório presente não prova que ele está certo (um gravado cedo fica completo e velho). A pergunta é "o trabalho entrou, e é isto que ele diz?", respondida por evidência: `morph-spec report-check <feature> [F1 F2 …] --json` dá o veredito e a ação (`hint`) de cada fatia, e a tabela de ação está em `morph-apply` §5. `report-stale` e `work-landed-report-missing` nunca se resolvem re-despachando: o trabalho já entrou. Caminho degradado fica no relatório (DEGRADADO); segunda ausência sem trabalho é falha real, escale.
|
|
308
191
|
|
|
309
|
-
**
|
|
192
|
+
**Teto de turnos:** `maxTurns` por persona no `agents.json` (implementadores 120), anunciado no corpo da persona. O corte é cego: `wip` por marco e, a ~70% do teto, relatório `PARCIAL` — o `report-check` o lê como `report-incomplete` com ação `resume`: retome o mesmo agente, não carimbe DEGRADADO.
|
|
310
193
|
|
|
311
|
-
**
|
|
312
|
-
- O que foi feito (2-3 frases)
|
|
313
|
-
- **Arquivos:** lista
|
|
314
|
-
- **Critérios:** cada `doneCriteria`, atendido (com o teste ou `arquivo:linha`) ou não (por quê)
|
|
315
|
-
- Problemas encontrados e como foram resolvidos
|
|
316
|
-
|
|
317
|
-
**Contrato do relatório final:** as oito cláusulas que todo prompt de dispatch inclui vivem nos DOIS templates — `morph-implement` §4 e `morph-apply` §3b — e não são repetidas aqui: duas cópias da mesma regra divergem, e quem manda é a que o sub-agent recebe. **4-8** (escopo, sobrevivência, processos, retorno, mutação) são idênticas **palavra por palavra**, e um canário as compara; **1-3** (relatório, estado, teste) dizem o mesmo na redação de cada template.
|
|
318
|
-
|
|
319
|
-
**Teto de turnos:** `maxTurns` por persona no `agents.json` (sem o campo, 20; implementadores 120), anunciado ao sub-agent no corpo da persona. O corte é cego: a cláusula 5 manda `wip` por marco e, a ~70% do teto, relatório `PARCIAL` sem critério dado como atendido (`report-incomplete`): retome o agente, não carimbe DEGRADADO.
|
|
320
|
-
|
|
321
|
-
Sub-agent deve ser autossuficiente: se precisaria de mais contexto, refine a tarefa antes de despachar.
|
|
322
|
-
|
|
323
|
-
**Quando NÃO despachar:** tarefas curtas onde o overhead do dispatch custa mais que a economia de contexto principal; quando o feedback precisaria ser discutido em tempo real (dispatch é assíncrono); quando a task envolve mudança de arquitetura que o Orchestrator precisa validar antes de executar.
|
|
324
|
-
|
|
325
|
-
**Após o retorno:** a task só avança com `verify` verde e cada critério com evidência (§0).
|
|
326
|
-
|
|
327
|
-
**Dispatch em paralelo (multi-agent):** fluxos **genuinamente independentes** (ex: backend ‖ frontend, convergindo só no fim) → despache múltiplos sub-agents **ao mesmo tempo**, um por fluxo, em vez de série. `morph-spec dag {feature}` analisa o DAG (`dependencies`/`group`), **pondera o esforço** (raízes/fluxos só de tasks S não ganham dispatch próprio) e imprime a decisão; regras e cap de agentes simultâneos em `morph-apply` ("Análise de DAG"). Colisão de `outputs` entre fluxos → `dag` recomenda `isolation: "worktree"`, cada agente num worktree próprio, orquestrador integra por merge (`morph-apply` §3b-w). Sem colisão: working tree compartilhada, verificação única pós-batch.
|
|
194
|
+
**Paralelo:** fluxos genuinamente independentes (backend ‖ frontend) vão ao mesmo tempo, um agente por fatia, até 4. `morph-spec plan-check {feature}` imprime as ondas (fatias sem `depende:` comum e sem arquivo em comum). Colisão que escapou do plano → a segunda fatia vai num worktree próprio, em rolling: a cada relatório o orquestrador integra por merge e despacha a próxima pronta (`morph-apply` §4). A feature só segue para a review com `verify` verde e cada cenário com evidência (§0).
|
|
328
195
|
|
|
329
196
|
---
|
|
330
197
|
|
|
331
198
|
## 7. Skills disponíveis
|
|
332
199
|
|
|
333
|
-
Skills
|
|
334
|
-
Não invoque uma skill fora do momento indicado.
|
|
335
|
-
|
|
336
|
-
Path de cada skill: `.claude/skills/{nome}/SKILL.md`.
|
|
337
|
-
|
|
338
|
-
| Skill | Quando invocar |
|
|
339
|
-
|---|---|
|
|
340
|
-
| **morph-proposal** | **Orquestrador**: brainstorming → Gate 1 → plan → Gate 2 (entry point) |
|
|
341
|
-
| **morph-apply** | **Orquestrador**: DAG-adaptive implement loop → review → Gate 3 |
|
|
342
|
-
| morph-brainstorming | Invocada pela morph-proposal — entendimento de negócio + stack-scan |
|
|
343
|
-
| morph-stack-scan | Detecta stack atual; curto-circuita em greenfield |
|
|
344
|
-
| morph-uiux | Ramo opcional uiux (§2.1) — design system, mockups, componentes, fluxos |
|
|
345
|
-
| morph-plan | Invocada pela morph-proposal — produz use cases, spec.md e tasks.json |
|
|
346
|
-
| morph-implement | Invocada pela morph-apply — executa cada task |
|
|
347
|
-
| morph-review | Invocada pela morph-apply — produz review-report + Gate 3 |
|
|
348
|
-
| morph-hotfix | **Orquestrador**: ADW cirúrgico de hotfix (scout → fix → gate humano → ship) |
|
|
349
|
-
| morph-standards | Quando precisar localizar ou aplicar um standard específico |
|
|
350
|
-
| morph-media | Imagem/vídeo por IA — modelo, prompt versionado, custo, gate humano |
|
|
351
|
-
| morph-machine | Máquina lenta/sem RAM, "⏳ não rodou" ou exit 3, sobra de worktree de sub-agent, sub-agents pesados em paralelo |
|
|
352
|
-
|
|
353
|
-
Slash commands (`/morph-proposal`, `/morph-apply`, `/morph-hotfix`) são atalhos da `Skill()` correspondente; chame-a direto quando o usuário pedir "use /morph-proposal".
|
|
354
|
-
|
|
355
|
-
Cada skill traz instruções passo a passo: siga, e justifique desvio no recap.md. Só as skills **core** são instaladas; nenhum hook as invoca — você decide quando a situação pede o rigor dela.
|
|
356
|
-
|
|
357
|
-
---
|
|
200
|
+
**Skills core** (`.claude/skills/{nome}/SKILL.md`, invocadas no momento indicado na descrição de cada uma): `morph-plan` (entrada: roteia, varre, entrevista, `plan.md`, gate do plano) · `morph-apply` (fatias → verify → review) · `morph-uiux` · `morph-review` · `morph-hotfix` · `morph-standards` · `morph-media` · `morph-machine`.
|
|
358
201
|
|
|
359
|
-
|
|
202
|
+
`/morph-proposal` → `morph-plan`, `/morph-apply` e `/morph-hotfix` são atalhos da skill. Desvio do passo a passo vai justificado no relatório.
|