@mindfoldhq/trellis 0.4.0 → 0.5.0-beta.10
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/dist/cli/index.js +0 -1
- package/dist/cli/index.js.map +1 -1
- package/dist/commands/init.d.ts +10 -1
- package/dist/commands/init.d.ts.map +1 -1
- package/dist/commands/init.js +382 -120
- package/dist/commands/init.js.map +1 -1
- package/dist/commands/update.d.ts +5 -0
- package/dist/commands/update.d.ts.map +1 -1
- package/dist/commands/update.js +178 -61
- package/dist/commands/update.js.map +1 -1
- package/dist/configurators/antigravity.d.ts +3 -4
- package/dist/configurators/antigravity.d.ts.map +1 -1
- package/dist/configurators/antigravity.js +17 -10
- package/dist/configurators/antigravity.js.map +1 -1
- package/dist/configurators/claude.d.ts +5 -28
- package/dist/configurators/claude.d.ts.map +1 -1
- package/dist/configurators/claude.js +30 -51
- package/dist/configurators/claude.js.map +1 -1
- package/dist/configurators/codebuddy.d.ts +6 -7
- package/dist/configurators/codebuddy.d.ts.map +1 -1
- package/dist/configurators/codebuddy.js +23 -51
- package/dist/configurators/codebuddy.js.map +1 -1
- package/dist/configurators/codex.d.ts +3 -6
- package/dist/configurators/codex.d.ts.map +1 -1
- package/dist/configurators/codex.js +29 -12
- package/dist/configurators/codex.js.map +1 -1
- package/dist/configurators/copilot.d.ts +6 -5
- package/dist/configurators/copilot.d.ts.map +1 -1
- package/dist/configurators/copilot.js +42 -13
- package/dist/configurators/copilot.js.map +1 -1
- package/dist/configurators/cursor.d.ts +6 -1
- package/dist/configurators/cursor.d.ts.map +1 -1
- package/dist/configurators/cursor.js +22 -45
- package/dist/configurators/cursor.js.map +1 -1
- package/dist/configurators/droid.d.ts +6 -1
- package/dist/configurators/droid.d.ts.map +1 -1
- package/dist/configurators/droid.js +23 -41
- package/dist/configurators/droid.js.map +1 -1
- package/dist/configurators/gemini.d.ts +8 -4
- package/dist/configurators/gemini.d.ts.map +1 -1
- package/dist/configurators/gemini.js +28 -47
- package/dist/configurators/gemini.js.map +1 -1
- package/dist/configurators/index.d.ts +1 -1
- package/dist/configurators/index.d.ts.map +1 -1
- package/dist/configurators/index.js +146 -100
- package/dist/configurators/index.js.map +1 -1
- package/dist/configurators/kilo.d.ts +3 -4
- package/dist/configurators/kilo.d.ts.map +1 -1
- package/dist/configurators/kilo.js +19 -46
- package/dist/configurators/kilo.js.map +1 -1
- package/dist/configurators/kiro.d.ts +4 -4
- package/dist/configurators/kiro.d.ts.map +1 -1
- package/dist/configurators/kiro.js +18 -14
- package/dist/configurators/kiro.js.map +1 -1
- package/dist/configurators/opencode.d.ts +7 -25
- package/dist/configurators/opencode.d.ts.map +1 -1
- package/dist/configurators/opencode.js +57 -56
- package/dist/configurators/opencode.js.map +1 -1
- package/dist/configurators/qoder.d.ts +6 -3
- package/dist/configurators/qoder.d.ts.map +1 -1
- package/dist/configurators/qoder.js +27 -46
- package/dist/configurators/qoder.js.map +1 -1
- package/dist/configurators/shared.d.ts +68 -3
- package/dist/configurators/shared.d.ts.map +1 -1
- package/dist/configurators/shared.js +274 -3
- package/dist/configurators/shared.js.map +1 -1
- package/dist/configurators/windsurf.d.ts +3 -4
- package/dist/configurators/windsurf.d.ts.map +1 -1
- package/dist/configurators/windsurf.js +17 -10
- package/dist/configurators/windsurf.js.map +1 -1
- package/dist/configurators/workflow.d.ts +0 -3
- package/dist/configurators/workflow.d.ts.map +1 -1
- package/dist/configurators/workflow.js +1 -7
- package/dist/configurators/workflow.js.map +1 -1
- package/dist/migrations/manifests/0.4.0.json +1 -1
- package/dist/migrations/manifests/0.5.0-beta.0.json +1646 -0
- package/dist/migrations/manifests/0.5.0-beta.1.json +9 -0
- package/dist/migrations/manifests/0.5.0-beta.2.json +9 -0
- package/dist/migrations/manifests/0.5.0-beta.3.json +9 -0
- package/dist/migrations/manifests/0.5.0-beta.4.json +9 -0
- package/dist/migrations/manifests/0.5.0-beta.5.json +222 -0
- package/dist/migrations/manifests/0.5.0-beta.6.json +9 -0
- package/dist/migrations/manifests/0.5.0-beta.7.json +9 -0
- package/dist/migrations/manifests/0.5.0-beta.8.json +9 -0
- package/dist/migrations/manifests/0.5.0-beta.9.json +48 -0
- package/dist/templates/claude/agents/{check.md → trellis-check.md} +3 -31
- package/dist/templates/claude/agents/{implement.md → trellis-implement.md} +1 -2
- package/dist/templates/claude/agents/trellis-research.md +137 -0
- package/dist/templates/claude/index.d.ts +5 -37
- package/dist/templates/claude/index.d.ts.map +1 -1
- package/dist/templates/claude/index.js +3 -42
- package/dist/templates/claude/index.js.map +1 -1
- package/dist/templates/claude/settings.json +6 -4
- package/dist/templates/{iflow/agents/check.md → codebuddy/agents/trellis-check.md} +3 -31
- package/dist/templates/{iflow/agents/implement.md → codebuddy/agents/trellis-implement.md} +1 -2
- package/dist/templates/codebuddy/agents/trellis-research.md +137 -0
- package/dist/templates/codebuddy/index.d.ts +6 -16
- package/dist/templates/codebuddy/index.d.ts.map +1 -1
- package/dist/templates/codebuddy/index.js +6 -36
- package/dist/templates/codebuddy/index.js.map +1 -1
- package/dist/templates/codebuddy/settings.json +59 -0
- package/dist/templates/codex/agents/trellis-check.toml +38 -0
- package/dist/templates/codex/agents/{implement.toml → trellis-implement.toml} +1 -1
- package/dist/templates/codex/agents/trellis-research.toml +60 -0
- package/dist/templates/codex/config.toml +10 -0
- package/dist/templates/codex/hooks/session-start.py +65 -29
- package/dist/templates/codex/hooks.json +11 -0
- package/dist/templates/codex/index.d.ts +0 -1
- package/dist/templates/codex/index.d.ts.map +1 -1
- package/dist/templates/codex/index.js +1 -8
- package/dist/templates/codex/index.js.map +1 -1
- package/dist/templates/codex/skills/start/SKILL.md +1 -1
- package/dist/templates/common/commands/continue.md +51 -0
- package/dist/templates/common/commands/finish-work.md +32 -0
- package/dist/templates/common/commands/start.md +56 -0
- package/dist/templates/common/index.d.ts +28 -0
- package/dist/templates/common/index.d.ts.map +1 -0
- package/dist/templates/common/index.js +55 -0
- package/dist/templates/common/index.js.map +1 -0
- package/dist/templates/{droid/commands/trellis → common/skills}/brainstorm.md +51 -12
- package/dist/templates/{iflow/commands/trellis → common/skills}/break-loop.md +4 -4
- package/dist/templates/common/skills/check.md +87 -0
- package/dist/templates/{codebuddy/commands/trellis → common/skills}/update-spec.md +18 -21
- package/dist/templates/copilot/hooks/session-start.py +65 -29
- package/dist/templates/copilot/hooks.json +8 -0
- package/dist/templates/copilot/prompts/start.prompt.md +13 -16
- package/dist/templates/cursor/agents/trellis-check.md +94 -0
- package/dist/templates/cursor/agents/trellis-implement.md +94 -0
- package/dist/templates/cursor/agents/trellis-research.md +137 -0
- package/dist/templates/cursor/hooks.json +24 -0
- package/dist/templates/cursor/index.d.ts +6 -17
- package/dist/templates/cursor/index.d.ts.map +1 -1
- package/dist/templates/cursor/index.js +6 -37
- package/dist/templates/cursor/index.js.map +1 -1
- package/dist/templates/droid/droids/trellis-check.md +94 -0
- package/dist/templates/droid/droids/trellis-implement.md +94 -0
- package/dist/templates/droid/droids/trellis-research.md +137 -0
- package/dist/templates/droid/index.d.ts +7 -19
- package/dist/templates/droid/index.d.ts.map +1 -1
- package/dist/templates/droid/index.js +7 -39
- package/dist/templates/droid/index.js.map +1 -1
- package/dist/templates/droid/settings.json +59 -0
- package/dist/templates/extract.d.ts +7 -193
- package/dist/templates/extract.d.ts.map +1 -1
- package/dist/templates/extract.js +7 -310
- package/dist/templates/extract.js.map +1 -1
- package/dist/templates/gemini/agents/trellis-check.md +94 -0
- package/dist/templates/gemini/agents/trellis-implement.md +94 -0
- package/dist/templates/gemini/agents/trellis-research.md +137 -0
- package/dist/templates/gemini/index.d.ts +6 -14
- package/dist/templates/gemini/index.d.ts.map +1 -1
- package/dist/templates/gemini/index.js +6 -37
- package/dist/templates/gemini/index.js.map +1 -1
- package/dist/templates/gemini/settings.json +28 -0
- package/dist/templates/kiro/agents/trellis-check.json +13 -0
- package/dist/templates/kiro/agents/trellis-implement.json +13 -0
- package/dist/templates/kiro/agents/trellis-research.json +21 -0
- package/dist/templates/kiro/index.d.ts +11 -11
- package/dist/templates/kiro/index.d.ts.map +1 -1
- package/dist/templates/kiro/index.js +11 -33
- package/dist/templates/kiro/index.js.map +1 -1
- package/dist/templates/opencode/agents/{check.md → trellis-check.md} +3 -30
- package/dist/templates/opencode/agents/{implement.md → trellis-implement.md} +1 -1
- package/dist/templates/opencode/agents/{research.md → trellis-research.md} +1 -2
- package/dist/templates/opencode/plugins/inject-subagent-context.js +18 -190
- package/dist/templates/opencode/plugins/inject-workflow-state.js +172 -0
- package/dist/templates/opencode/plugins/session-start.js +76 -39
- package/dist/templates/qoder/agents/trellis-check.md +94 -0
- package/dist/templates/qoder/agents/trellis-implement.md +94 -0
- package/dist/templates/qoder/agents/trellis-research.md +137 -0
- package/dist/templates/qoder/index.d.ts +7 -10
- package/dist/templates/qoder/index.d.ts.map +1 -1
- package/dist/templates/qoder/index.js +7 -32
- package/dist/templates/qoder/index.js.map +1 -1
- package/dist/templates/qoder/settings.json +47 -0
- package/dist/templates/shared-hooks/index.d.ts +19 -0
- package/dist/templates/shared-hooks/index.d.ts.map +1 -0
- package/dist/templates/shared-hooks/index.js +30 -0
- package/dist/templates/shared-hooks/index.js.map +1 -0
- package/dist/templates/{iflow/hooks → shared-hooks}/inject-subagent-context.py +77 -266
- package/dist/templates/shared-hooks/inject-workflow-state.py +244 -0
- package/dist/templates/{claude/hooks → shared-hooks}/session-start.py +172 -55
- package/dist/templates/template-utils.d.ts +26 -0
- package/dist/templates/template-utils.d.ts.map +1 -0
- package/dist/templates/template-utils.js +60 -0
- package/dist/templates/template-utils.js.map +1 -0
- package/dist/templates/trellis/config.yaml +6 -0
- package/dist/templates/trellis/index.d.ts +1 -15
- package/dist/templates/trellis/index.d.ts.map +1 -1
- package/dist/templates/trellis/index.js +2 -29
- package/dist/templates/trellis/index.js.map +1 -1
- package/dist/templates/trellis/scripts/common/cli_adapter.py +31 -8
- package/dist/templates/trellis/scripts/common/config.py +126 -1
- package/dist/templates/trellis/scripts/common/git_context.py +25 -2
- package/dist/templates/trellis/scripts/common/task_context.py +23 -28
- package/dist/templates/trellis/scripts/common/task_store.py +0 -12
- package/dist/templates/trellis/scripts/common/types.py +0 -2
- package/dist/templates/trellis/scripts/common/workflow_phase.py +176 -0
- package/dist/templates/trellis/scripts/task.py +13 -35
- package/dist/templates/trellis/workflow.md +283 -298
- package/dist/types/ai-tools.d.ts +30 -3
- package/dist/types/ai-tools.d.ts.map +1 -1
- package/dist/types/ai-tools.js +119 -15
- package/dist/types/ai-tools.js.map +1 -1
- package/dist/types/migration.d.ts +8 -1
- package/dist/types/migration.d.ts.map +1 -1
- package/dist/utils/project-detector.d.ts +2 -0
- package/dist/utils/project-detector.d.ts.map +1 -1
- package/dist/utils/project-detector.js +120 -11
- package/dist/utils/project-detector.js.map +1 -1
- package/dist/utils/task-json.d.ts +46 -0
- package/dist/utils/task-json.d.ts.map +1 -0
- package/dist/utils/task-json.js +49 -0
- package/dist/utils/task-json.js.map +1 -0
- package/package.json +3 -2
- package/dist/configurators/iflow.d.ts +0 -33
- package/dist/configurators/iflow.d.ts.map +0 -1
- package/dist/configurators/iflow.js +0 -99
- package/dist/configurators/iflow.js.map +0 -1
- package/dist/templates/antigravity/index.d.ts +0 -12
- package/dist/templates/antigravity/index.d.ts.map +0 -1
- package/dist/templates/antigravity/index.js +0 -29
- package/dist/templates/antigravity/index.js.map +0 -1
- package/dist/templates/claude/agents/debug.md +0 -106
- package/dist/templates/claude/agents/dispatch.md +0 -213
- package/dist/templates/claude/agents/plan.md +0 -396
- package/dist/templates/claude/agents/research.md +0 -120
- package/dist/templates/claude/commands/trellis/brainstorm.md +0 -487
- package/dist/templates/claude/commands/trellis/break-loop.md +0 -125
- package/dist/templates/claude/commands/trellis/check-cross-layer.md +0 -153
- package/dist/templates/claude/commands/trellis/check.md +0 -25
- package/dist/templates/claude/commands/trellis/create-command.md +0 -154
- package/dist/templates/claude/commands/trellis/finish-work.md +0 -153
- package/dist/templates/claude/commands/trellis/integrate-skill.md +0 -219
- package/dist/templates/claude/commands/trellis/onboard.md +0 -358
- package/dist/templates/claude/commands/trellis/parallel.md +0 -192
- package/dist/templates/claude/commands/trellis/record-session.md +0 -62
- package/dist/templates/claude/commands/trellis/start.md +0 -393
- package/dist/templates/claude/commands/trellis/update-spec.md +0 -354
- package/dist/templates/claude/hooks/inject-subagent-context.py +0 -803
- package/dist/templates/claude/hooks/ralph-loop.py +0 -396
- package/dist/templates/codebuddy/commands/trellis/before-dev.md +0 -29
- package/dist/templates/codebuddy/commands/trellis/brainstorm.md +0 -487
- package/dist/templates/codebuddy/commands/trellis/break-loop.md +0 -107
- package/dist/templates/codebuddy/commands/trellis/check-cross-layer.md +0 -153
- package/dist/templates/codebuddy/commands/trellis/check.md +0 -25
- package/dist/templates/codebuddy/commands/trellis/create-command.md +0 -154
- package/dist/templates/codebuddy/commands/trellis/finish-work.md +0 -143
- package/dist/templates/codebuddy/commands/trellis/integrate-skill.md +0 -219
- package/dist/templates/codebuddy/commands/trellis/onboard.md +0 -358
- package/dist/templates/codebuddy/commands/trellis/record-session.md +0 -61
- package/dist/templates/codebuddy/commands/trellis/start.md +0 -373
- package/dist/templates/codex/agents/check.toml +0 -23
- package/dist/templates/codex/agents/research.toml +0 -26
- package/dist/templates/codex/codex-skills/parallel/SKILL.md +0 -194
- package/dist/templates/cursor/commands/trellis-before-dev.md +0 -29
- package/dist/templates/cursor/commands/trellis-brainstorm.md +0 -487
- package/dist/templates/cursor/commands/trellis-break-loop.md +0 -107
- package/dist/templates/cursor/commands/trellis-check-cross-layer.md +0 -153
- package/dist/templates/cursor/commands/trellis-check.md +0 -25
- package/dist/templates/cursor/commands/trellis-create-command.md +0 -154
- package/dist/templates/cursor/commands/trellis-finish-work.md +0 -143
- package/dist/templates/cursor/commands/trellis-integrate-skill.md +0 -219
- package/dist/templates/cursor/commands/trellis-onboard.md +0 -358
- package/dist/templates/cursor/commands/trellis-record-session.md +0 -62
- package/dist/templates/cursor/commands/trellis-start.md +0 -373
- package/dist/templates/cursor/commands/trellis-update-spec.md +0 -354
- package/dist/templates/droid/commands/trellis/before-dev.md +0 -33
- package/dist/templates/droid/commands/trellis/break-loop.md +0 -111
- package/dist/templates/droid/commands/trellis/check-cross-layer.md +0 -157
- package/dist/templates/droid/commands/trellis/check.md +0 -29
- package/dist/templates/droid/commands/trellis/create-command.md +0 -158
- package/dist/templates/droid/commands/trellis/finish-work.md +0 -147
- package/dist/templates/droid/commands/trellis/integrate-skill.md +0 -223
- package/dist/templates/droid/commands/trellis/onboard.md +0 -362
- package/dist/templates/droid/commands/trellis/record-session.md +0 -66
- package/dist/templates/droid/commands/trellis/start.md +0 -377
- package/dist/templates/droid/commands/trellis/update-spec.md +0 -358
- package/dist/templates/gemini/commands/trellis/before-dev.toml +0 -33
- package/dist/templates/gemini/commands/trellis/brainstorm.toml +0 -435
- package/dist/templates/gemini/commands/trellis/break-loop.toml +0 -129
- package/dist/templates/gemini/commands/trellis/check-cross-layer.toml +0 -147
- package/dist/templates/gemini/commands/trellis/check.toml +0 -29
- package/dist/templates/gemini/commands/trellis/create-command.toml +0 -119
- package/dist/templates/gemini/commands/trellis/finish-work.toml +0 -133
- package/dist/templates/gemini/commands/trellis/integrate-skill.toml +0 -104
- package/dist/templates/gemini/commands/trellis/onboard.toml +0 -111
- package/dist/templates/gemini/commands/trellis/record-session.toml +0 -66
- package/dist/templates/gemini/commands/trellis/start.toml +0 -354
- package/dist/templates/gemini/commands/trellis/update-spec.toml +0 -132
- package/dist/templates/iflow/agents/debug.md +0 -106
- package/dist/templates/iflow/agents/dispatch.md +0 -213
- package/dist/templates/iflow/agents/plan.md +0 -396
- package/dist/templates/iflow/agents/research.md +0 -120
- package/dist/templates/iflow/commands/trellis/before-dev.md +0 -29
- package/dist/templates/iflow/commands/trellis/brainstorm.md +0 -487
- package/dist/templates/iflow/commands/trellis/check-cross-layer.md +0 -153
- package/dist/templates/iflow/commands/trellis/check.md +0 -25
- package/dist/templates/iflow/commands/trellis/create-command.md +0 -152
- package/dist/templates/iflow/commands/trellis/finish-work.md +0 -153
- package/dist/templates/iflow/commands/trellis/integrate-skill.md +0 -219
- package/dist/templates/iflow/commands/trellis/onboard.md +0 -358
- package/dist/templates/iflow/commands/trellis/parallel.md +0 -192
- package/dist/templates/iflow/commands/trellis/record-session.md +0 -62
- package/dist/templates/iflow/commands/trellis/start.md +0 -393
- package/dist/templates/iflow/commands/trellis/update-spec.md +0 -354
- package/dist/templates/iflow/hooks/ralph-loop.py +0 -395
- package/dist/templates/iflow/hooks/session-start.py +0 -403
- package/dist/templates/iflow/index.d.ts +0 -54
- package/dist/templates/iflow/index.d.ts.map +0 -1
- package/dist/templates/iflow/index.js +0 -85
- package/dist/templates/iflow/index.js.map +0 -1
- package/dist/templates/iflow/settings.json +0 -60
- package/dist/templates/kilo/index.d.ts +0 -16
- package/dist/templates/kilo/index.d.ts.map +0 -1
- package/dist/templates/kilo/index.js +0 -39
- package/dist/templates/kilo/index.js.map +0 -1
- package/dist/templates/kilo/workflows/before-dev.md +0 -29
- package/dist/templates/kilo/workflows/brainstorm.md +0 -487
- package/dist/templates/kilo/workflows/break-loop.md +0 -125
- package/dist/templates/kilo/workflows/check-cross-layer.md +0 -153
- package/dist/templates/kilo/workflows/check.md +0 -25
- package/dist/templates/kilo/workflows/create-command.md +0 -152
- package/dist/templates/kilo/workflows/finish-work.md +0 -129
- package/dist/templates/kilo/workflows/integrate-skill.md +0 -219
- package/dist/templates/kilo/workflows/onboard.md +0 -358
- package/dist/templates/kilo/workflows/parallel.md +0 -193
- package/dist/templates/kilo/workflows/record-session.md +0 -62
- package/dist/templates/kilo/workflows/start.md +0 -387
- package/dist/templates/kilo/workflows/update-spec.md +0 -285
- package/dist/templates/kiro/skills/before-dev/SKILL.md +0 -34
- package/dist/templates/kiro/skills/brainstorm/SKILL.md +0 -492
- package/dist/templates/kiro/skills/break-loop/SKILL.md +0 -130
- package/dist/templates/kiro/skills/check/SKILL.md +0 -30
- package/dist/templates/kiro/skills/check-cross-layer/SKILL.md +0 -158
- package/dist/templates/kiro/skills/create-command/SKILL.md +0 -101
- package/dist/templates/kiro/skills/finish-work/SKILL.md +0 -148
- package/dist/templates/kiro/skills/integrate-skill/SKILL.md +0 -221
- package/dist/templates/kiro/skills/onboard/SKILL.md +0 -363
- package/dist/templates/kiro/skills/record-session/SKILL.md +0 -67
- package/dist/templates/kiro/skills/start/SKILL.md +0 -351
- package/dist/templates/kiro/skills/update-spec/SKILL.md +0 -335
- package/dist/templates/markdown/spec/backend/directory-structure.md +0 -292
- package/dist/templates/markdown/spec/backend/index.md +0 -40
- package/dist/templates/markdown/spec/backend/script-conventions.md +0 -742
- package/dist/templates/markdown/spec/guides/code-reuse-thinking-guide.md +0 -118
- package/dist/templates/markdown/spec/guides/cross-platform-thinking-guide.md +0 -394
- package/dist/templates/opencode/agents/debug.md +0 -129
- package/dist/templates/opencode/agents/dispatch.md +0 -223
- package/dist/templates/opencode/agents/trellis-plan.md +0 -427
- package/dist/templates/opencode/commands/trellis/before-dev.md +0 -29
- package/dist/templates/opencode/commands/trellis/brainstorm.md +0 -487
- package/dist/templates/opencode/commands/trellis/break-loop.md +0 -125
- package/dist/templates/opencode/commands/trellis/check-cross-layer.md +0 -153
- package/dist/templates/opencode/commands/trellis/check.md +0 -25
- package/dist/templates/opencode/commands/trellis/create-command.md +0 -154
- package/dist/templates/opencode/commands/trellis/finish-work.md +0 -144
- package/dist/templates/opencode/commands/trellis/integrate-skill.md +0 -219
- package/dist/templates/opencode/commands/trellis/migrate-specs.md +0 -0
- package/dist/templates/opencode/commands/trellis/onboard.md +0 -358
- package/dist/templates/opencode/commands/trellis/parallel.md +0 -193
- package/dist/templates/opencode/commands/trellis/record-session.md +0 -62
- package/dist/templates/opencode/commands/trellis/start.md +0 -351
- package/dist/templates/opencode/commands/trellis/update-spec.md +0 -354
- package/dist/templates/qoder/skills/before-dev/SKILL.md +0 -34
- package/dist/templates/qoder/skills/brainstorm/SKILL.md +0 -492
- package/dist/templates/qoder/skills/break-loop/SKILL.md +0 -130
- package/dist/templates/qoder/skills/check/SKILL.md +0 -30
- package/dist/templates/qoder/skills/check-cross-layer/SKILL.md +0 -158
- package/dist/templates/qoder/skills/create-command/SKILL.md +0 -101
- package/dist/templates/qoder/skills/finish-work/SKILL.md +0 -134
- package/dist/templates/qoder/skills/integrate-skill/SKILL.md +0 -221
- package/dist/templates/qoder/skills/onboard/SKILL.md +0 -363
- package/dist/templates/qoder/skills/record-session/SKILL.md +0 -67
- package/dist/templates/qoder/skills/start/SKILL.md +0 -388
- package/dist/templates/qoder/skills/update-spec/SKILL.md +0 -290
- package/dist/templates/trellis/scripts/common/phase.py +0 -254
- package/dist/templates/trellis/scripts/common/registry.py +0 -335
- package/dist/templates/trellis/scripts/common/worktree.py +0 -305
- package/dist/templates/trellis/scripts/create_bootstrap.py +0 -298
- package/dist/templates/trellis/scripts/multi_agent/__init__.py +0 -5
- package/dist/templates/trellis/scripts/multi_agent/_bootstrap.py +0 -17
- package/dist/templates/trellis/scripts/multi_agent/cleanup.py +0 -398
- package/dist/templates/trellis/scripts/multi_agent/create_pr.py +0 -620
- package/dist/templates/trellis/scripts/multi_agent/plan.py +0 -213
- package/dist/templates/trellis/scripts/multi_agent/start.py +0 -539
- package/dist/templates/trellis/scripts/multi_agent/status.py +0 -76
- package/dist/templates/trellis/scripts/multi_agent/status_display.py +0 -542
- package/dist/templates/trellis/scripts/multi_agent/status_monitor.py +0 -225
- package/dist/templates/trellis/scripts-shell-archive/add-session.sh +0 -384
- package/dist/templates/trellis/scripts-shell-archive/common/developer.sh +0 -129
- package/dist/templates/trellis/scripts-shell-archive/common/git-context.sh +0 -263
- package/dist/templates/trellis/scripts-shell-archive/common/paths.sh +0 -208
- package/dist/templates/trellis/scripts-shell-archive/common/phase.sh +0 -150
- package/dist/templates/trellis/scripts-shell-archive/common/registry.sh +0 -247
- package/dist/templates/trellis/scripts-shell-archive/common/task-queue.sh +0 -142
- package/dist/templates/trellis/scripts-shell-archive/common/task-utils.sh +0 -151
- package/dist/templates/trellis/scripts-shell-archive/common/worktree.sh +0 -128
- package/dist/templates/trellis/scripts-shell-archive/create-bootstrap.sh +0 -299
- package/dist/templates/trellis/scripts-shell-archive/get-context.sh +0 -7
- package/dist/templates/trellis/scripts-shell-archive/get-developer.sh +0 -15
- package/dist/templates/trellis/scripts-shell-archive/init-developer.sh +0 -34
- package/dist/templates/trellis/scripts-shell-archive/multi-agent/cleanup.sh +0 -396
- package/dist/templates/trellis/scripts-shell-archive/multi-agent/create-pr.sh +0 -241
- package/dist/templates/trellis/scripts-shell-archive/multi-agent/plan.sh +0 -207
- package/dist/templates/trellis/scripts-shell-archive/multi-agent/start.sh +0 -317
- package/dist/templates/trellis/scripts-shell-archive/multi-agent/status.sh +0 -828
- package/dist/templates/trellis/scripts-shell-archive/task.sh +0 -1204
- package/dist/templates/trellis/worktree.yaml +0 -47
- package/dist/templates/windsurf/index.d.ts +0 -21
- package/dist/templates/windsurf/index.d.ts.map +0 -1
- package/dist/templates/windsurf/index.js +0 -44
- package/dist/templates/windsurf/index.js.map +0 -1
- package/dist/templates/windsurf/workflows/trellis-before-dev.md +0 -31
- package/dist/templates/windsurf/workflows/trellis-brainstorm.md +0 -491
- package/dist/templates/windsurf/workflows/trellis-break-loop.md +0 -111
- package/dist/templates/windsurf/workflows/trellis-check-cross-layer.md +0 -157
- package/dist/templates/windsurf/workflows/trellis-check.md +0 -27
- package/dist/templates/windsurf/workflows/trellis-create-command.md +0 -154
- package/dist/templates/windsurf/workflows/trellis-finish-work.md +0 -147
- package/dist/templates/windsurf/workflows/trellis-integrate-skill.md +0 -220
- package/dist/templates/windsurf/workflows/trellis-onboard.md +0 -362
- package/dist/templates/windsurf/workflows/trellis-record-session.md +0 -66
- package/dist/templates/windsurf/workflows/trellis-start.md +0 -373
- package/dist/templates/windsurf/workflows/trellis-update-spec.md +0 -358
- /package/dist/templates/{claude/commands/trellis → common/skills}/before-dev.md +0 -0
- /package/dist/templates/{claude/hooks → shared-hooks}/statusline.py +0 -0
|
@@ -0,0 +1,244 @@
|
|
|
1
|
+
#!/usr/bin/env python3
|
|
2
|
+
"""Trellis UserPromptSubmit hook: inject per-turn workflow breadcrumb.
|
|
3
|
+
|
|
4
|
+
Runs on every user prompt. Reads the active task (.trellis/.current-task)
|
|
5
|
+
and emits a short <workflow-state> block reminding the main AI what task
|
|
6
|
+
is active and its expected flow. Breadcrumb text is pulled from
|
|
7
|
+
workflow.md [workflow-state:STATUS] tag blocks (single source of truth
|
|
8
|
+
for users who fork the Trellis workflow), with hardcoded fallbacks so
|
|
9
|
+
the hook never breaks when workflow.md is missing or malformed.
|
|
10
|
+
|
|
11
|
+
Shared across all hook-capable platforms (Claude, Cursor, Codex, Qoder,
|
|
12
|
+
CodeBuddy, Droid, Gemini, Copilot). Kiro is not wired (no per-turn
|
|
13
|
+
hook entry point). Written to each platform's hooks directory via
|
|
14
|
+
writeSharedHooks() at init time.
|
|
15
|
+
|
|
16
|
+
Silent exit 0 cases (no output):
|
|
17
|
+
- No .trellis/ directory found (not a Trellis project)
|
|
18
|
+
- No .current-task file, or it's empty
|
|
19
|
+
- task.json malformed or missing status
|
|
20
|
+
|
|
21
|
+
Unknown status (no tag + no hardcoded fallback) emits a generic
|
|
22
|
+
breadcrumb rather than silent-exiting, so custom statuses surface in
|
|
23
|
+
the UI instead of appearing as "randomly broken".
|
|
24
|
+
"""
|
|
25
|
+
from __future__ import annotations
|
|
26
|
+
|
|
27
|
+
import json
|
|
28
|
+
import os
|
|
29
|
+
import re
|
|
30
|
+
import sys
|
|
31
|
+
from pathlib import Path
|
|
32
|
+
from typing import Optional, Tuple
|
|
33
|
+
|
|
34
|
+
|
|
35
|
+
# ---------------------------------------------------------------------------
|
|
36
|
+
# CWD-robust Trellis root discovery (fixes hook-path-robustness for this hook)
|
|
37
|
+
# ---------------------------------------------------------------------------
|
|
38
|
+
|
|
39
|
+
def find_trellis_root(start: Path) -> Optional[Path]:
|
|
40
|
+
"""Walk up from start to find directory containing .trellis/.
|
|
41
|
+
|
|
42
|
+
Handles CWD drift: subdirectory launches, monorepo packages, etc.
|
|
43
|
+
Returns None if no .trellis/ found (silent no-op).
|
|
44
|
+
"""
|
|
45
|
+
cur = start.resolve()
|
|
46
|
+
while cur != cur.parent:
|
|
47
|
+
if (cur / ".trellis").is_dir():
|
|
48
|
+
return cur
|
|
49
|
+
cur = cur.parent
|
|
50
|
+
return None
|
|
51
|
+
|
|
52
|
+
|
|
53
|
+
# ---------------------------------------------------------------------------
|
|
54
|
+
# Active task discovery
|
|
55
|
+
# ---------------------------------------------------------------------------
|
|
56
|
+
|
|
57
|
+
def _normalize_task_ref(task_ref: str) -> str:
|
|
58
|
+
"""Normalize .current-task path ref.
|
|
59
|
+
|
|
60
|
+
Accepts:
|
|
61
|
+
- Absolute paths (left as-is)
|
|
62
|
+
- Windows-style backslashes (converted to forward slash)
|
|
63
|
+
- Legacy relative refs like "tasks/foo" (prefixed with .trellis/)
|
|
64
|
+
"""
|
|
65
|
+
normalized = task_ref.strip()
|
|
66
|
+
if not normalized:
|
|
67
|
+
return ""
|
|
68
|
+
path_obj = Path(normalized)
|
|
69
|
+
if path_obj.is_absolute():
|
|
70
|
+
return str(path_obj)
|
|
71
|
+
normalized = normalized.replace("\\", "/")
|
|
72
|
+
while normalized.startswith("./"):
|
|
73
|
+
normalized = normalized[2:]
|
|
74
|
+
if normalized.startswith("tasks/"):
|
|
75
|
+
normalized = f".trellis/{normalized}"
|
|
76
|
+
return normalized
|
|
77
|
+
|
|
78
|
+
|
|
79
|
+
def get_active_task(root: Path) -> Optional[Tuple[str, str]]:
|
|
80
|
+
"""Return (task_id, status) from the current active task, else None.
|
|
81
|
+
|
|
82
|
+
Reads .trellis/.current-task (a path relative to root, e.g.
|
|
83
|
+
".trellis/tasks/04-17-foo") then that task's task.json.
|
|
84
|
+
Normalizes backslashes so Windows paths work on Unix and vice versa.
|
|
85
|
+
"""
|
|
86
|
+
ref_file = root / ".trellis" / ".current-task"
|
|
87
|
+
if not ref_file.is_file():
|
|
88
|
+
return None
|
|
89
|
+
try:
|
|
90
|
+
raw = ref_file.read_text(encoding="utf-8").strip()
|
|
91
|
+
except OSError:
|
|
92
|
+
return None
|
|
93
|
+
task_ref = _normalize_task_ref(raw)
|
|
94
|
+
if not task_ref:
|
|
95
|
+
return None
|
|
96
|
+
|
|
97
|
+
path_obj = Path(task_ref)
|
|
98
|
+
task_dir = path_obj if path_obj.is_absolute() else root / path_obj
|
|
99
|
+
task_json = task_dir / "task.json"
|
|
100
|
+
if not task_json.is_file():
|
|
101
|
+
return None
|
|
102
|
+
try:
|
|
103
|
+
data = json.loads(task_json.read_text(encoding="utf-8"))
|
|
104
|
+
except (json.JSONDecodeError, OSError):
|
|
105
|
+
return None
|
|
106
|
+
|
|
107
|
+
task_id = data.get("id") or task_dir.name
|
|
108
|
+
status = data.get("status", "")
|
|
109
|
+
if not isinstance(status, str) or not status:
|
|
110
|
+
return None
|
|
111
|
+
return task_id, status
|
|
112
|
+
|
|
113
|
+
|
|
114
|
+
# ---------------------------------------------------------------------------
|
|
115
|
+
# Breadcrumb loading: parse workflow.md, fall back to hardcoded defaults
|
|
116
|
+
# ---------------------------------------------------------------------------
|
|
117
|
+
|
|
118
|
+
# Supports STATUS values with letters, digits, underscores, hyphens
|
|
119
|
+
# (so "in-review" / "blocked-by-team" work alongside "in_progress").
|
|
120
|
+
_TAG_RE = re.compile(
|
|
121
|
+
r"\[workflow-state:([A-Za-z0-9_-]+)\]\s*\n(.*?)\n\s*\[/workflow-state:\1\]",
|
|
122
|
+
re.DOTALL,
|
|
123
|
+
)
|
|
124
|
+
|
|
125
|
+
# Hardcoded defaults for built-in Trellis statuses. Used when workflow.md is
|
|
126
|
+
# missing, malformed, or lacks the tag for this status.
|
|
127
|
+
#
|
|
128
|
+
# `no_task` is a pseudo-status emitted when .current-task is missing — it keeps
|
|
129
|
+
# the Next-Action reminder flowing per-turn even without an active task.
|
|
130
|
+
_FALLBACK_BREADCRUMBS = {
|
|
131
|
+
"no_task": (
|
|
132
|
+
"No active task.\n"
|
|
133
|
+
"Trigger words in the user message that REQUIRE creating a task "
|
|
134
|
+
"(non-negotiable, do NOT self-exempt): 重构 / 抽成 / 独立 / 分发 / "
|
|
135
|
+
"拆出来 / 搞一个 / 做成 / 接入 / 集成 / refactor / rewrite / extract / "
|
|
136
|
+
"productize / publish / build X / design Y.\n"
|
|
137
|
+
"Task is NOT required ONLY if ALL three hold: (a) zero file writes "
|
|
138
|
+
"this turn, (b) answer fits in one reply with no multi-round plan, "
|
|
139
|
+
"(c) no research beyond reading 1-2 repo files.\n"
|
|
140
|
+
"When in doubt: create task. Over-tasking is cheap; under-tasking "
|
|
141
|
+
"leaks plans and research into main context.\n"
|
|
142
|
+
"Flow: load `trellis-brainstorm` skill → it creates the task via "
|
|
143
|
+
"`python3 ./.trellis/scripts/task.py create` and drives requirements Q&A. "
|
|
144
|
+
"For research-heavy work (tool comparison, docs, cross-platform survey), "
|
|
145
|
+
"spawn `trellis-research` sub-agents via Task tool — NEVER do 3+ inline "
|
|
146
|
+
"WebFetch/WebSearch/`gh api` calls in the main conversation."
|
|
147
|
+
),
|
|
148
|
+
"planning": (
|
|
149
|
+
"Complete prd.md via trellis-brainstorm skill; then run task.py start.\n"
|
|
150
|
+
"Research belongs in `{task_dir}/research/*.md`, written by "
|
|
151
|
+
"`trellis-research` sub-agents. Do NOT inline WebFetch/WebSearch in "
|
|
152
|
+
"main session — PRD only links to research files."
|
|
153
|
+
),
|
|
154
|
+
"in_progress": (
|
|
155
|
+
"Flow: trellis-implement → trellis-check → trellis-update-spec → finish\n"
|
|
156
|
+
"Check conversation history + git status to determine current step; "
|
|
157
|
+
"do NOT skip trellis-check."
|
|
158
|
+
),
|
|
159
|
+
"completed": (
|
|
160
|
+
"User commits changes; then run task.py archive."
|
|
161
|
+
),
|
|
162
|
+
}
|
|
163
|
+
|
|
164
|
+
|
|
165
|
+
def load_breadcrumbs(root: Path) -> dict[str, str]:
|
|
166
|
+
"""Parse workflow.md for [workflow-state:STATUS] blocks.
|
|
167
|
+
|
|
168
|
+
Returns {status: body_text}. Missing tags fall back to hardcoded
|
|
169
|
+
defaults so the hook always has something to say for built-in
|
|
170
|
+
statuses. Custom statuses without tags fall to generic breadcrumb
|
|
171
|
+
downstream (see build_breadcrumb).
|
|
172
|
+
"""
|
|
173
|
+
result = dict(_FALLBACK_BREADCRUMBS)
|
|
174
|
+
|
|
175
|
+
workflow = root / ".trellis" / "workflow.md"
|
|
176
|
+
if not workflow.is_file():
|
|
177
|
+
return result
|
|
178
|
+
try:
|
|
179
|
+
content = workflow.read_text(encoding="utf-8")
|
|
180
|
+
except OSError:
|
|
181
|
+
return result
|
|
182
|
+
|
|
183
|
+
for match in _TAG_RE.finditer(content):
|
|
184
|
+
status = match.group(1)
|
|
185
|
+
body = match.group(2).strip()
|
|
186
|
+
if body:
|
|
187
|
+
result[status] = body
|
|
188
|
+
return result
|
|
189
|
+
|
|
190
|
+
|
|
191
|
+
def build_breadcrumb(
|
|
192
|
+
task_id: Optional[str], status: str, templates: dict[str, str]
|
|
193
|
+
) -> str:
|
|
194
|
+
"""Build the <workflow-state>...</workflow-state> block.
|
|
195
|
+
|
|
196
|
+
- Known status (in templates or fallback) → detailed template body
|
|
197
|
+
- Unknown status (no tag + no fallback) → generic "refer to workflow.md"
|
|
198
|
+
- `no_task` pseudo-status (task_id is None) → header omits task info
|
|
199
|
+
"""
|
|
200
|
+
body = templates.get(status)
|
|
201
|
+
if body is None:
|
|
202
|
+
body = "Refer to workflow.md for current step."
|
|
203
|
+
header = f"Status: {status}" if task_id is None else f"Task: {task_id} ({status})"
|
|
204
|
+
return f"<workflow-state>\n{header}\n{body}\n</workflow-state>"
|
|
205
|
+
|
|
206
|
+
|
|
207
|
+
# ---------------------------------------------------------------------------
|
|
208
|
+
# Entry
|
|
209
|
+
# ---------------------------------------------------------------------------
|
|
210
|
+
|
|
211
|
+
def main() -> int:
|
|
212
|
+
try:
|
|
213
|
+
data = json.load(sys.stdin)
|
|
214
|
+
except (json.JSONDecodeError, ValueError):
|
|
215
|
+
data = {}
|
|
216
|
+
|
|
217
|
+
cwd_str = data.get("cwd") or os.getcwd()
|
|
218
|
+
cwd = Path(cwd_str)
|
|
219
|
+
|
|
220
|
+
root = find_trellis_root(cwd)
|
|
221
|
+
if root is None:
|
|
222
|
+
return 0 # not a Trellis project
|
|
223
|
+
|
|
224
|
+
templates = load_breadcrumbs(root)
|
|
225
|
+
task = get_active_task(root)
|
|
226
|
+
if task is None:
|
|
227
|
+
# No active task — still emit a breadcrumb nudging AI toward
|
|
228
|
+
# trellis-brainstorm + task.py create when user describes real work.
|
|
229
|
+
breadcrumb = build_breadcrumb(None, "no_task", templates)
|
|
230
|
+
else:
|
|
231
|
+
breadcrumb = build_breadcrumb(*task, templates=templates)
|
|
232
|
+
|
|
233
|
+
output = {
|
|
234
|
+
"hookSpecificOutput": {
|
|
235
|
+
"hookEventName": "UserPromptSubmit",
|
|
236
|
+
"additionalContext": breadcrumb,
|
|
237
|
+
}
|
|
238
|
+
}
|
|
239
|
+
print(json.dumps(output))
|
|
240
|
+
return 0
|
|
241
|
+
|
|
242
|
+
|
|
243
|
+
if __name__ == "__main__":
|
|
244
|
+
sys.exit(main())
|
|
@@ -25,11 +25,20 @@ if sys.platform == "win32":
|
|
|
25
25
|
sys.stdout = _io.TextIOWrapper(sys.stdout.detach(), encoding="utf-8", errors="replace") # type: ignore[union-attr]
|
|
26
26
|
|
|
27
27
|
|
|
28
|
+
|
|
28
29
|
def should_skip_injection() -> bool:
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
30
|
+
"""Check if any platform's non-interactive flag is set."""
|
|
31
|
+
non_interactive_vars = [
|
|
32
|
+
"CLAUDE_NON_INTERACTIVE",
|
|
33
|
+
"QODER_NON_INTERACTIVE",
|
|
34
|
+
"CODEBUDDY_NON_INTERACTIVE",
|
|
35
|
+
"FACTORY_NON_INTERACTIVE",
|
|
36
|
+
"CURSOR_NON_INTERACTIVE",
|
|
37
|
+
"GEMINI_NON_INTERACTIVE",
|
|
38
|
+
"KIRO_NON_INTERACTIVE",
|
|
39
|
+
"COPILOT_NON_INTERACTIVE",
|
|
40
|
+
]
|
|
41
|
+
return any(os.environ.get(var) == "1" for var in non_interactive_vars)
|
|
33
42
|
|
|
34
43
|
|
|
35
44
|
def read_file(path: Path, fallback: str = "") -> str:
|
|
@@ -95,19 +104,37 @@ def _resolve_task_dir(trellis_dir: Path, task_ref: str) -> Path:
|
|
|
95
104
|
|
|
96
105
|
|
|
97
106
|
def _get_task_status(trellis_dir: Path) -> str:
|
|
98
|
-
"""Check current task status and return structured status string.
|
|
107
|
+
"""Check current task status and return structured status string with explicit next action.
|
|
108
|
+
|
|
109
|
+
Returns a block with three fields:
|
|
110
|
+
- Status: current state
|
|
111
|
+
- Task: task identifier (when applicable)
|
|
112
|
+
- Next-Action: explicit skill/command/tool call the AI should invoke
|
|
113
|
+
"""
|
|
99
114
|
current_task_file = trellis_dir / ".current-task"
|
|
100
|
-
|
|
101
|
-
|
|
115
|
+
|
|
116
|
+
# Case 1: No active task — waiting for user to describe intent
|
|
117
|
+
if not current_task_file.is_file() or not current_task_file.read_text(encoding="utf-8").strip():
|
|
118
|
+
return (
|
|
119
|
+
"Status: NO ACTIVE TASK\n"
|
|
120
|
+
"Next-Action: After the user describes their intent, load skill `trellis-brainstorm` "
|
|
121
|
+
"to clarify requirements and create a task via `python3 ./.trellis/scripts/task.py create`.\n"
|
|
122
|
+
"Research reminder: for research-heavy tasks (comparing tools, reading external docs, "
|
|
123
|
+
"cross-platform surveys), spawn `trellis-research` sub-agents via the Task tool — "
|
|
124
|
+
"they persist findings to `{TASK_DIR}/research/*.md` and keep main context clean. "
|
|
125
|
+
"Do NOT do 10+ inline WebFetch/WebSearch in the main conversation."
|
|
126
|
+
)
|
|
102
127
|
|
|
103
128
|
task_ref = _normalize_task_ref(current_task_file.read_text(encoding="utf-8").strip())
|
|
104
|
-
if not task_ref:
|
|
105
|
-
return "Status: NO ACTIVE TASK\nNext: Describe what you want to work on"
|
|
106
129
|
|
|
107
|
-
#
|
|
130
|
+
# Case 2: Stale pointer — task dir was deleted
|
|
108
131
|
task_dir = _resolve_task_dir(trellis_dir, task_ref)
|
|
109
132
|
if not task_dir.is_dir():
|
|
110
|
-
return
|
|
133
|
+
return (
|
|
134
|
+
f"Status: STALE POINTER\nTask: {task_ref}\n"
|
|
135
|
+
f"Next-Action: Run `python3 ./.trellis/scripts/task.py finish` to clear the stale pointer, "
|
|
136
|
+
"then ask the user what to work on next."
|
|
137
|
+
)
|
|
111
138
|
|
|
112
139
|
# Read task.json
|
|
113
140
|
task_json_path = task_dir / "task.json"
|
|
@@ -121,26 +148,37 @@ def _get_task_status(trellis_dir: Path) -> str:
|
|
|
121
148
|
task_title = task_data.get("title", task_ref)
|
|
122
149
|
task_status = task_data.get("status", "unknown")
|
|
123
150
|
|
|
151
|
+
# Case 3: Task completed — time to archive
|
|
124
152
|
if task_status == "completed":
|
|
125
|
-
return
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
jsonl_path = task_dir / jsonl_name
|
|
131
|
-
if jsonl_path.is_file() and jsonl_path.stat().st_size > 0:
|
|
132
|
-
has_context = True
|
|
133
|
-
break
|
|
153
|
+
return (
|
|
154
|
+
f"Status: COMPLETED\nTask: {task_title}\n"
|
|
155
|
+
f"Next-Action: Load skill `trellis-update-spec` to capture learnings, "
|
|
156
|
+
f"then archive with `python3 ./.trellis/scripts/task.py archive {task_dir.name}`."
|
|
157
|
+
)
|
|
134
158
|
|
|
135
159
|
has_prd = (task_dir / "prd.md").is_file()
|
|
136
160
|
|
|
161
|
+
# Case 4: No PRD — still in Plan phase
|
|
137
162
|
if not has_prd:
|
|
138
|
-
return
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
163
|
+
return (
|
|
164
|
+
f"Status: PLANNING\nTask: {task_title}\n"
|
|
165
|
+
"Next-Action: Load skill `trellis-brainstorm` to clarify requirements with the user "
|
|
166
|
+
"and produce prd.md in the task directory.\n"
|
|
167
|
+
"Research reminder: when the task needs external research (tool comparison, docs, "
|
|
168
|
+
"conventions survey), spawn `trellis-research` sub-agents — don't WebFetch/WebSearch "
|
|
169
|
+
"inline in the main session. Findings go to `{task_dir}/research/*.md`; PRD only links to them."
|
|
170
|
+
)
|
|
142
171
|
|
|
143
|
-
|
|
172
|
+
# Case 5: PRD ready — enter Execute phase
|
|
173
|
+
return (
|
|
174
|
+
f"Status: READY\nTask: {task_title}\n"
|
|
175
|
+
"Next-Action: Load skill `trellis-before-dev` to read relevant specs, "
|
|
176
|
+
"then spawn `trellis-implement` sub-agent via the Task tool. "
|
|
177
|
+
"After implementation, spawn `trellis-check` sub-agent for quality verification.\n"
|
|
178
|
+
"Sub-agent roster: `trellis-implement` (writes code), `trellis-check` (verifies + self-fixes), "
|
|
179
|
+
"`trellis-research` (persists findings to `research/*.md` — use when you'd otherwise do "
|
|
180
|
+
"multiple WebFetch/WebSearch inline)."
|
|
181
|
+
)
|
|
144
182
|
|
|
145
183
|
|
|
146
184
|
def _load_trellis_config(trellis_dir: Path) -> tuple:
|
|
@@ -288,37 +326,97 @@ def _resolve_spec_scope(
|
|
|
288
326
|
return None # Unknown scope type: full scan
|
|
289
327
|
|
|
290
328
|
|
|
291
|
-
def
|
|
292
|
-
"""
|
|
329
|
+
def _extract_range(content: str, start_header: str, end_header: str) -> str:
|
|
330
|
+
"""Extract lines starting at `## start_header` up to (but excluding) `## end_header`.
|
|
293
331
|
|
|
294
|
-
|
|
295
|
-
|
|
332
|
+
Both parameters are full header lines WITHOUT the `## ` prefix (e.g. "Phase Index").
|
|
333
|
+
Returns empty string if start header is not found.
|
|
334
|
+
End header missing → extracts to end of file.
|
|
335
|
+
"""
|
|
336
|
+
lines = content.splitlines()
|
|
337
|
+
start: int | None = None
|
|
338
|
+
end: int = len(lines)
|
|
339
|
+
start_match = f"## {start_header}"
|
|
340
|
+
end_match = f"## {end_header}"
|
|
341
|
+
for i, line in enumerate(lines):
|
|
342
|
+
stripped = line.strip()
|
|
343
|
+
if start is None and stripped == start_match:
|
|
344
|
+
start = i
|
|
345
|
+
continue
|
|
346
|
+
if start is not None and stripped == end_match:
|
|
347
|
+
end = i
|
|
348
|
+
break
|
|
349
|
+
if start is None:
|
|
350
|
+
return ""
|
|
351
|
+
return "\n".join(lines[start:end]).rstrip()
|
|
352
|
+
|
|
353
|
+
|
|
354
|
+
def _build_workflow_overview(workflow_path: Path) -> str:
|
|
355
|
+
"""Inject the workflow guide for the session.
|
|
356
|
+
|
|
357
|
+
Contents:
|
|
358
|
+
1. Section index (all `## ` headings — navigation)
|
|
359
|
+
2. Phase Index section (rules, skill routing table, anti-rationalization table)
|
|
360
|
+
3. Phase 1/2/3 step-level details (the actual how-to for each step)
|
|
361
|
+
|
|
362
|
+
The meta sections (Core Principles / Trellis System / Workflow State
|
|
363
|
+
Breadcrumbs) are NOT injected — Core Principles is short prose the AI can
|
|
364
|
+
Read on demand; Trellis System lists reference commands duplicated in
|
|
365
|
+
step bodies; Breadcrumbs are consumed by the UserPromptSubmit hook.
|
|
366
|
+
|
|
367
|
+
Total budget: Phase Index ~2 KB + Phase 1/2/3 ~7 KB = ~9 KB.
|
|
296
368
|
"""
|
|
297
369
|
content = read_file(workflow_path)
|
|
298
370
|
if not content:
|
|
299
371
|
return "No workflow.md found"
|
|
300
372
|
|
|
301
|
-
|
|
373
|
+
out_lines = [
|
|
302
374
|
"# Development Workflow — Section Index",
|
|
303
375
|
"Full guide: .trellis/workflow.md (read on demand)",
|
|
304
376
|
"",
|
|
377
|
+
"## Table of Contents",
|
|
305
378
|
]
|
|
306
379
|
for line in content.splitlines():
|
|
307
380
|
if line.startswith("## "):
|
|
308
|
-
|
|
381
|
+
out_lines.append(line)
|
|
382
|
+
out_lines += ["", "---", ""]
|
|
383
|
+
|
|
384
|
+
# Extract Phase Index through the end of Phase 3 (before Breadcrumbs).
|
|
385
|
+
# Since sections appear in order Phase Index → Phase 1 → Phase 2 → Phase 3
|
|
386
|
+
# → Workflow State Breadcrumbs, a single range grab captures all four.
|
|
387
|
+
phases = _extract_range(
|
|
388
|
+
content, "Phase Index", "Workflow State Breadcrumbs"
|
|
389
|
+
)
|
|
390
|
+
if phases:
|
|
391
|
+
out_lines.append(phases)
|
|
309
392
|
|
|
310
|
-
|
|
311
|
-
"",
|
|
312
|
-
"To read a section: use the Read tool on .trellis/workflow.md",
|
|
313
|
-
]
|
|
314
|
-
return "\n".join(toc_lines)
|
|
393
|
+
return "\n".join(out_lines).rstrip()
|
|
315
394
|
|
|
316
395
|
|
|
317
396
|
def main():
|
|
318
397
|
if should_skip_injection():
|
|
319
398
|
sys.exit(0)
|
|
320
399
|
|
|
321
|
-
|
|
400
|
+
# Try platform-specific env vars, fallback to cwd
|
|
401
|
+
project_dir_env_vars = [
|
|
402
|
+
"CLAUDE_PROJECT_DIR",
|
|
403
|
+
"QODER_PROJECT_DIR",
|
|
404
|
+
"CODEBUDDY_PROJECT_DIR",
|
|
405
|
+
"FACTORY_PROJECT_DIR",
|
|
406
|
+
"CURSOR_PROJECT_DIR",
|
|
407
|
+
"GEMINI_PROJECT_DIR",
|
|
408
|
+
"KIRO_PROJECT_DIR",
|
|
409
|
+
"COPILOT_PROJECT_DIR",
|
|
410
|
+
]
|
|
411
|
+
project_dir = None
|
|
412
|
+
for var in project_dir_env_vars:
|
|
413
|
+
val = os.environ.get(var)
|
|
414
|
+
if val:
|
|
415
|
+
project_dir = Path(val).resolve()
|
|
416
|
+
break
|
|
417
|
+
if project_dir is None:
|
|
418
|
+
project_dir = Path(".").resolve()
|
|
419
|
+
|
|
322
420
|
trellis_dir = project_dir / ".trellis"
|
|
323
421
|
|
|
324
422
|
# Load config for scope filtering and legacy detection
|
|
@@ -345,34 +443,43 @@ Read and follow all instructions below carefully.
|
|
|
345
443
|
output.write("\n</current-state>\n\n")
|
|
346
444
|
|
|
347
445
|
output.write("<workflow>\n")
|
|
348
|
-
output.write(
|
|
446
|
+
output.write(_build_workflow_overview(trellis_dir / "workflow.md"))
|
|
349
447
|
output.write("\n</workflow>\n\n")
|
|
350
448
|
|
|
351
449
|
output.write("<guidelines>\n")
|
|
352
|
-
output.write(
|
|
353
|
-
|
|
450
|
+
output.write(
|
|
451
|
+
"Project spec indexes are listed by path below. Each index contains a "
|
|
452
|
+
"**Pre-Development Checklist** listing the specific guideline files to "
|
|
453
|
+
"read before coding.\n\n"
|
|
454
|
+
"- If you're spawning an implement/check sub-agent, context is injected "
|
|
455
|
+
"automatically via `{task}/implement.jsonl` / `check.jsonl`. You do NOT "
|
|
456
|
+
"need to read these indexes yourself.\n"
|
|
457
|
+
"- If you're editing code directly in the main session, Read the relevant "
|
|
458
|
+
"index(es) on-demand and follow their Pre-Dev Checklist.\n\n"
|
|
459
|
+
)
|
|
460
|
+
|
|
461
|
+
# guides/ is cross-package thinking — always include inline (small, broadly useful)
|
|
462
|
+
guides_index = trellis_dir / "spec" / "guides" / "index.md"
|
|
463
|
+
if guides_index.is_file():
|
|
464
|
+
output.write("## guides (inlined — cross-package thinking guides)\n")
|
|
465
|
+
output.write(read_file(guides_index))
|
|
466
|
+
output.write("\n\n")
|
|
354
467
|
|
|
468
|
+
# Other spec indexes — paths only (main agent reads on demand;
|
|
469
|
+
# sub-agents get their specific specs via jsonl injection)
|
|
470
|
+
paths: list[str] = []
|
|
355
471
|
spec_dir = trellis_dir / "spec"
|
|
356
472
|
if spec_dir.is_dir():
|
|
357
473
|
for sub in sorted(spec_dir.iterdir()):
|
|
358
474
|
if not sub.is_dir() or sub.name.startswith("."):
|
|
359
475
|
continue
|
|
360
|
-
|
|
361
|
-
# Always include guides/ regardless of scope
|
|
362
476
|
if sub.name == "guides":
|
|
363
|
-
|
|
364
|
-
if index_file.is_file():
|
|
365
|
-
output.write(f"## {sub.name}\n")
|
|
366
|
-
output.write(read_file(index_file))
|
|
367
|
-
output.write("\n\n")
|
|
368
|
-
continue
|
|
477
|
+
continue # already inlined above
|
|
369
478
|
|
|
370
479
|
index_file = sub / "index.md"
|
|
371
480
|
if index_file.is_file():
|
|
372
481
|
# Flat spec dir (single-repo layer like spec/backend/)
|
|
373
|
-
|
|
374
|
-
output.write(read_file(index_file))
|
|
375
|
-
output.write("\n\n")
|
|
482
|
+
paths.append(f".trellis/spec/{sub.name}/index.md")
|
|
376
483
|
else:
|
|
377
484
|
# Nested package dirs (monorepo: spec/<pkg>/<layer>/index.md)
|
|
378
485
|
# Apply scope filter
|
|
@@ -383,10 +490,20 @@ Read and follow all instructions below carefully.
|
|
|
383
490
|
continue
|
|
384
491
|
nested_index = nested / "index.md"
|
|
385
492
|
if nested_index.is_file():
|
|
386
|
-
|
|
387
|
-
|
|
388
|
-
|
|
389
|
-
|
|
493
|
+
paths.append(
|
|
494
|
+
f".trellis/spec/{sub.name}/{nested.name}/index.md"
|
|
495
|
+
)
|
|
496
|
+
|
|
497
|
+
if paths:
|
|
498
|
+
output.write("## Available spec indexes (read on demand)\n")
|
|
499
|
+
for p in paths:
|
|
500
|
+
output.write(f"- {p}\n")
|
|
501
|
+
output.write("\n")
|
|
502
|
+
|
|
503
|
+
output.write(
|
|
504
|
+
"Discover more via: "
|
|
505
|
+
"`python3 ./.trellis/scripts/get_context.py --mode packages`\n"
|
|
506
|
+
)
|
|
390
507
|
output.write("</guidelines>\n\n")
|
|
391
508
|
|
|
392
509
|
# Check task status and inject structured tag
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Shared utilities for platform template modules.
|
|
3
|
+
* Eliminates boilerplate across qoder/, codebuddy/, droid/, cursor/, gemini/, kiro/ index.ts files.
|
|
4
|
+
*/
|
|
5
|
+
export interface AgentTemplate {
|
|
6
|
+
name: string;
|
|
7
|
+
content: string;
|
|
8
|
+
}
|
|
9
|
+
export interface HookTemplate {
|
|
10
|
+
targetPath: string;
|
|
11
|
+
content: string;
|
|
12
|
+
}
|
|
13
|
+
export interface TemplateReader {
|
|
14
|
+
readTemplate: (relativePath: string) => string;
|
|
15
|
+
listFiles: (dir: string) => string[];
|
|
16
|
+
listMdAgents: (dir?: string) => AgentTemplate[];
|
|
17
|
+
listJsonAgents: (dir?: string) => AgentTemplate[];
|
|
18
|
+
getSettings: (filename?: string) => HookTemplate;
|
|
19
|
+
getConfig: (filename: string) => string;
|
|
20
|
+
}
|
|
21
|
+
/**
|
|
22
|
+
* Create a template reader bound to the caller's directory.
|
|
23
|
+
* Usage: `const { readTemplate, listMdAgents, getSettings } = createTemplateReader(import.meta.url);`
|
|
24
|
+
*/
|
|
25
|
+
export declare function createTemplateReader(importMetaUrl: string): TemplateReader;
|
|
26
|
+
//# sourceMappingURL=template-utils.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"template-utils.d.ts","sourceRoot":"","sources":["../../src/templates/template-utils.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAMH,MAAM,WAAW,aAAa;IAC5B,IAAI,EAAE,MAAM,CAAC;IACb,OAAO,EAAE,MAAM,CAAC;CACjB;AAED,MAAM,WAAW,YAAY;IAC3B,UAAU,EAAE,MAAM,CAAC;IACnB,OAAO,EAAE,MAAM,CAAC;CACjB;AAED,MAAM,WAAW,cAAc;IAC7B,YAAY,EAAE,CAAC,YAAY,EAAE,MAAM,KAAK,MAAM,CAAC;IAC/C,SAAS,EAAE,CAAC,GAAG,EAAE,MAAM,KAAK,MAAM,EAAE,CAAC;IACrC,YAAY,EAAE,CAAC,GAAG,CAAC,EAAE,MAAM,KAAK,aAAa,EAAE,CAAC;IAChD,cAAc,EAAE,CAAC,GAAG,CAAC,EAAE,MAAM,KAAK,aAAa,EAAE,CAAC;IAClD,WAAW,EAAE,CAAC,QAAQ,CAAC,EAAE,MAAM,KAAK,YAAY,CAAC;IACjD,SAAS,EAAE,CAAC,QAAQ,EAAE,MAAM,KAAK,MAAM,CAAC;CACzC;AAED;;;GAGG;AACH,wBAAgB,oBAAoB,CAAC,aAAa,EAAE,MAAM,GAAG,cAAc,CAqD1E"}
|
|
@@ -0,0 +1,60 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Shared utilities for platform template modules.
|
|
3
|
+
* Eliminates boilerplate across qoder/, codebuddy/, droid/, cursor/, gemini/, kiro/ index.ts files.
|
|
4
|
+
*/
|
|
5
|
+
import { readdirSync, readFileSync } from "node:fs";
|
|
6
|
+
import { dirname, join } from "node:path";
|
|
7
|
+
import { fileURLToPath } from "node:url";
|
|
8
|
+
/**
|
|
9
|
+
* Create a template reader bound to the caller's directory.
|
|
10
|
+
* Usage: `const { readTemplate, listMdAgents, getSettings } = createTemplateReader(import.meta.url);`
|
|
11
|
+
*/
|
|
12
|
+
export function createTemplateReader(importMetaUrl) {
|
|
13
|
+
const __dirname = dirname(fileURLToPath(importMetaUrl));
|
|
14
|
+
function readTemplate(relativePath) {
|
|
15
|
+
return readFileSync(join(__dirname, relativePath), "utf-8");
|
|
16
|
+
}
|
|
17
|
+
function listFiles(dir) {
|
|
18
|
+
try {
|
|
19
|
+
return readdirSync(join(__dirname, dir)).sort();
|
|
20
|
+
}
|
|
21
|
+
catch {
|
|
22
|
+
return [];
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
/** Read all .md agent files from a subdirectory */
|
|
26
|
+
function listMdAgents(dir = "agents") {
|
|
27
|
+
return listFiles(dir)
|
|
28
|
+
.filter((f) => f.endsWith(".md"))
|
|
29
|
+
.map((f) => ({
|
|
30
|
+
name: f.replace(".md", ""),
|
|
31
|
+
content: readTemplate(`${dir}/${f}`),
|
|
32
|
+
}));
|
|
33
|
+
}
|
|
34
|
+
/** Read all .json agent files from a subdirectory (Kiro) */
|
|
35
|
+
function listJsonAgents(dir = "agents") {
|
|
36
|
+
return listFiles(dir)
|
|
37
|
+
.filter((f) => f.endsWith(".json"))
|
|
38
|
+
.map((f) => ({
|
|
39
|
+
name: f.replace(".json", ""),
|
|
40
|
+
content: readTemplate(`${dir}/${f}`),
|
|
41
|
+
}));
|
|
42
|
+
}
|
|
43
|
+
/** Read settings.json and return as HookTemplate */
|
|
44
|
+
function getSettings(filename = "settings.json") {
|
|
45
|
+
return { targetPath: filename, content: readTemplate(filename) };
|
|
46
|
+
}
|
|
47
|
+
/** Read a config file and return raw string */
|
|
48
|
+
function getConfig(filename) {
|
|
49
|
+
return readTemplate(filename);
|
|
50
|
+
}
|
|
51
|
+
return {
|
|
52
|
+
readTemplate,
|
|
53
|
+
listFiles,
|
|
54
|
+
listMdAgents,
|
|
55
|
+
listJsonAgents,
|
|
56
|
+
getSettings,
|
|
57
|
+
getConfig,
|
|
58
|
+
};
|
|
59
|
+
}
|
|
60
|
+
//# sourceMappingURL=template-utils.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"template-utils.js","sourceRoot":"","sources":["../../src/templates/template-utils.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,EAAE,WAAW,EAAE,YAAY,EAAE,MAAM,SAAS,CAAC;AACpD,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAC;AAC1C,OAAO,EAAE,aAAa,EAAE,MAAM,UAAU,CAAC;AAqBzC;;;GAGG;AACH,MAAM,UAAU,oBAAoB,CAAC,aAAqB;IACxD,MAAM,SAAS,GAAG,OAAO,CAAC,aAAa,CAAC,aAAa,CAAC,CAAC,CAAC;IAExD,SAAS,YAAY,CAAC,YAAoB;QACxC,OAAO,YAAY,CAAC,IAAI,CAAC,SAAS,EAAE,YAAY,CAAC,EAAE,OAAO,CAAC,CAAC;IAC9D,CAAC;IAED,SAAS,SAAS,CAAC,GAAW;QAC5B,IAAI,CAAC;YACH,OAAO,WAAW,CAAC,IAAI,CAAC,SAAS,EAAE,GAAG,CAAC,CAAC,CAAC,IAAI,EAAE,CAAC;QAClD,CAAC;QAAC,MAAM,CAAC;YACP,OAAO,EAAE,CAAC;QACZ,CAAC;IACH,CAAC;IAED,mDAAmD;IACnD,SAAS,YAAY,CAAC,GAAG,GAAG,QAAQ;QAClC,OAAO,SAAS,CAAC,GAAG,CAAC;aAClB,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC;aAChC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;YACX,IAAI,EAAE,CAAC,CAAC,OAAO,CAAC,KAAK,EAAE,EAAE,CAAC;YAC1B,OAAO,EAAE,YAAY,CAAC,GAAG,GAAG,IAAI,CAAC,EAAE,CAAC;SACrC,CAAC,CAAC,CAAC;IACR,CAAC;IAED,4DAA4D;IAC5D,SAAS,cAAc,CAAC,GAAG,GAAG,QAAQ;QACpC,OAAO,SAAS,CAAC,GAAG,CAAC;aAClB,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,QAAQ,CAAC,OAAO,CAAC,CAAC;aAClC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;YACX,IAAI,EAAE,CAAC,CAAC,OAAO,CAAC,OAAO,EAAE,EAAE,CAAC;YAC5B,OAAO,EAAE,YAAY,CAAC,GAAG,GAAG,IAAI,CAAC,EAAE,CAAC;SACrC,CAAC,CAAC,CAAC;IACR,CAAC;IAED,oDAAoD;IACpD,SAAS,WAAW,CAAC,QAAQ,GAAG,eAAe;QAC7C,OAAO,EAAE,UAAU,EAAE,QAAQ,EAAE,OAAO,EAAE,YAAY,CAAC,QAAQ,CAAC,EAAE,CAAC;IACnE,CAAC;IAED,+CAA+C;IAC/C,SAAS,SAAS,CAAC,QAAgB;QACjC,OAAO,YAAY,CAAC,QAAQ,CAAC,CAAC;IAChC,CAAC;IAED,OAAO;QACL,YAAY;QACZ,SAAS;QACT,YAAY;QACZ,cAAc;QACd,WAAW;QACX,SAAS;KACV,CAAC;AACJ,CAAC"}
|
|
@@ -48,6 +48,12 @@ max_journal_lines: 2000
|
|
|
48
48
|
# docs:
|
|
49
49
|
# path: docs-site
|
|
50
50
|
# type: submodule
|
|
51
|
+
# # For polyrepo / meta-repo layouts (independent .git in each subdir),
|
|
52
|
+
# # mark the package with `git: true`. The runtime treats it as an
|
|
53
|
+
# # independent repository for things like git-context display.
|
|
54
|
+
# webapp:
|
|
55
|
+
# path: ./webapp
|
|
56
|
+
# git: true
|
|
51
57
|
|
|
52
58
|
# Default package used when --package is not specified.
|
|
53
59
|
# default_package: frontend
|