@erclx/canon 4.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/LICENSE +21 -0
- package/README.md +129 -0
- package/claude/.claude-plugin/plugin.json +19 -0
- package/claude/skills/bash-cli-script/REQUIREMENT.md +42 -0
- package/claude/skills/bash-cli-script/SKILL.md +48 -0
- package/claude/skills/bash-cli-script/references/template.md +43 -0
- package/claude/skills/bash-script/REQUIREMENT.md +36 -0
- package/claude/skills/bash-script/SKILL.md +100 -0
- package/claude/skills/bash-script/references/patterns.md +349 -0
- package/claude/skills/canon-cli/REQUIREMENT.md +41 -0
- package/claude/skills/canon-cli/SKILL.md +103 -0
- package/claude/skills/canon-feedback-file/REQUIREMENT.md +40 -0
- package/claude/skills/canon-feedback-file/SKILL.md +80 -0
- package/claude/skills/canon-feedback-triage/REQUIREMENT.md +40 -0
- package/claude/skills/canon-feedback-triage/SKILL.md +63 -0
- package/claude/skills/canon-operator/REQUIREMENT.md +61 -0
- package/claude/skills/canon-operator/SKILL.md +108 -0
- package/claude/skills/canon-rollout/REQUIREMENT.md +59 -0
- package/claude/skills/canon-rollout/SKILL.md +147 -0
- package/claude/skills/canon-screencast/REQUIREMENT.md +39 -0
- package/claude/skills/canon-screencast/SKILL.md +167 -0
- package/claude/skills/canon-slides-draft/REQUIREMENT.md +39 -0
- package/claude/skills/canon-slides-draft/SKILL.md +62 -0
- package/claude/skills/ci-workflow/REQUIREMENT.md +40 -0
- package/claude/skills/ci-workflow/SKILL.md +65 -0
- package/claude/skills/ci-workflow/references/workflows.md +98 -0
- package/claude/skills/claude-address-review/REQUIREMENT.md +57 -0
- package/claude/skills/claude-address-review/SKILL.md +212 -0
- package/claude/skills/claude-address-review/references/rebase-conflicts.md +39 -0
- package/claude/skills/claude-autoship/REQUIREMENT.md +50 -0
- package/claude/skills/claude-autoship/SKILL.md +207 -0
- package/claude/skills/claude-design-extract/REQUIREMENT.md +42 -0
- package/claude/skills/claude-design-extract/SKILL.md +102 -0
- package/claude/skills/claude-diagram/REQUIREMENT.md +45 -0
- package/claude/skills/claude-diagram/SKILL.md +177 -0
- package/claude/skills/claude-docs/REQUIREMENT.md +60 -0
- package/claude/skills/claude-docs/SKILL.md +287 -0
- package/claude/skills/claude-docs/references/anchor-sweep.md +58 -0
- package/claude/skills/claude-docs/references/wireframe-sweep.md +45 -0
- package/claude/skills/claude-feature/REQUIREMENT.md +36 -0
- package/claude/skills/claude-feature/SKILL.md +115 -0
- package/claude/skills/claude-groundwork/REQUIREMENT.md +48 -0
- package/claude/skills/claude-groundwork/SKILL.md +142 -0
- package/claude/skills/claude-intake/REQUIREMENT.md +49 -0
- package/claude/skills/claude-intake/SKILL.md +114 -0
- package/claude/skills/claude-intake-answer/REQUIREMENT.md +48 -0
- package/claude/skills/claude-intake-answer/SKILL.md +90 -0
- package/claude/skills/claude-markdown-propose/REQUIREMENT.md +48 -0
- package/claude/skills/claude-markdown-propose/SKILL.md +118 -0
- package/claude/skills/claude-markdown-propose/references/format.md +107 -0
- package/claude/skills/claude-memory-capture/REQUIREMENT.md +50 -0
- package/claude/skills/claude-memory-capture/SKILL.md +101 -0
- package/claude/skills/claude-memory-review/REQUIREMENT.md +50 -0
- package/claude/skills/claude-memory-review/SKILL.md +210 -0
- package/claude/skills/claude-memory-review/references/receipt-format.md +48 -0
- package/claude/skills/claude-orchestrate/REQUIREMENT.md +121 -0
- package/claude/skills/claude-orchestrate/SKILL.md +241 -0
- package/claude/skills/claude-orchestrate/references/orchestrator-dispatch.md +132 -0
- package/claude/skills/claude-orchestrate/references/orchestrator-handoff.md +32 -0
- package/claude/skills/claude-orchestrate/references/orchestrator-parked.md +72 -0
- package/claude/skills/claude-orchestrate/references/orchestrator-poll.md +87 -0
- package/claude/skills/claude-orchestrate/references/orchestrator-resume.md +30 -0
- package/claude/skills/claude-orchestrate/references/orchestrator-sweep.md +21 -0
- package/claude/skills/claude-orchestrate/scripts/poll.sh +373 -0
- package/claude/skills/claude-orchestrate/scripts/watch.sh +181 -0
- package/claude/skills/claude-pr-review/REQUIREMENT.md +47 -0
- package/claude/skills/claude-pr-review/SKILL.md +295 -0
- package/claude/skills/claude-review/REQUIREMENT.md +39 -0
- package/claude/skills/claude-review/SKILL.md +142 -0
- package/claude/skills/claude-seed-sync/REQUIREMENT.md +45 -0
- package/claude/skills/claude-seed-sync/SKILL.md +156 -0
- package/claude/skills/claude-standards-audit/REQUIREMENT.md +33 -0
- package/claude/skills/claude-standards-audit/SKILL.md +99 -0
- package/claude/skills/claude-tasks/REQUIREMENT.md +43 -0
- package/claude/skills/claude-tasks/SKILL.md +161 -0
- package/claude/skills/claude-teach/REQUIREMENT.md +56 -0
- package/claude/skills/claude-teach/SKILL.md +196 -0
- package/claude/skills/claude-teach/references/lesson-craft.md +59 -0
- package/claude/skills/claude-teach/references/pedagogy.md +67 -0
- package/claude/skills/claude-teach/references/promotion.md +54 -0
- package/claude/skills/claude-ui-test/REQUIREMENT.md +40 -0
- package/claude/skills/claude-ui-test/SKILL.md +77 -0
- package/claude/skills/claude-ux-audit/REQUIREMENT.md +40 -0
- package/claude/skills/claude-ux-audit/SKILL.md +79 -0
- package/claude/skills/claude-ux-measure/REQUIREMENT.md +48 -0
- package/claude/skills/claude-ux-measure/SKILL.md +122 -0
- package/claude/skills/claude-worker/REQUIREMENT.md +54 -0
- package/claude/skills/claude-worker/SKILL.md +96 -0
- package/claude/skills/claude-worktree/REQUIREMENT.md +58 -0
- package/claude/skills/claude-worktree/SKILL.md +136 -0
- package/claude/skills/create-rule/REQUIREMENT.md +45 -0
- package/claude/skills/create-rule/SKILL.md +68 -0
- package/claude/skills/create-skill/REQUIREMENT.md +38 -0
- package/claude/skills/create-skill/SKILL.md +32 -0
- package/claude/skills/create-snippet/REQUIREMENT.md +39 -0
- package/claude/skills/create-snippet/SKILL.md +30 -0
- package/claude/skills/create-standard/REQUIREMENT.md +35 -0
- package/claude/skills/create-standard/SKILL.md +29 -0
- package/claude/skills/decision-escalate/REQUIREMENT.md +45 -0
- package/claude/skills/decision-escalate/SKILL.md +79 -0
- package/claude/skills/docs-sync/REQUIREMENT.md +41 -0
- package/claude/skills/docs-sync/SKILL.md +95 -0
- package/claude/skills/git-branch/REQUIREMENT.md +38 -0
- package/claude/skills/git-branch/SKILL.md +60 -0
- package/claude/skills/git-commit/REQUIREMENT.md +36 -0
- package/claude/skills/git-commit/SKILL.md +49 -0
- package/claude/skills/git-followup/REQUIREMENT.md +43 -0
- package/claude/skills/git-followup/SKILL.md +48 -0
- package/claude/skills/git-issue/REQUIREMENT.md +38 -0
- package/claude/skills/git-issue/SKILL.md +65 -0
- package/claude/skills/git-pr/REQUIREMENT.md +50 -0
- package/claude/skills/git-pr/SKILL.md +164 -0
- package/claude/skills/git-pr/references/labels.md +95 -0
- package/claude/skills/git-ship/REQUIREMENT.md +42 -0
- package/claude/skills/git-ship/SKILL.md +55 -0
- package/claude/skills/git-split/REQUIREMENT.md +39 -0
- package/claude/skills/git-split/SKILL.md +162 -0
- package/claude/skills/git-stage/REQUIREMENT.md +39 -0
- package/claude/skills/git-stage/SKILL.md +73 -0
- package/claude/skills/git-worktree/REQUIREMENT.md +38 -0
- package/claude/skills/git-worktree/SKILL.md +130 -0
- package/claude/skills/migration-claude-md/REQUIREMENT.md +40 -0
- package/claude/skills/migration-claude-md/SKILL.md +76 -0
- package/claude/skills/migration-context/REQUIREMENT.md +36 -0
- package/claude/skills/migration-context/SKILL.md +95 -0
- package/claude/skills/migration-standards-drop/REQUIREMENT.md +55 -0
- package/claude/skills/migration-standards-drop/SKILL.md +113 -0
- package/claude/skills/migration-superseded/REQUIREMENT.md +44 -0
- package/claude/skills/migration-superseded/SKILL.md +115 -0
- package/claude/skills/project-commands/REQUIREMENT.md +42 -0
- package/claude/skills/project-commands/SKILL.md +85 -0
- package/claude/skills/restate-plainly/REQUIREMENT.md +41 -0
- package/claude/skills/restate-plainly/SKILL.md +39 -0
- package/claude/skills/session-map/REQUIREMENT.md +57 -0
- package/claude/skills/session-map/SKILL.md +70 -0
- package/claude/skills/session-resume/REQUIREMENT.md +49 -0
- package/claude/skills/session-resume/SKILL.md +51 -0
- package/claude/skills/setup-gov/REQUIREMENT.md +37 -0
- package/claude/skills/setup-gov/SKILL.md +77 -0
- package/claude/skills/setup-indexes/REQUIREMENT.md +45 -0
- package/claude/skills/setup-indexes/SKILL.md +153 -0
- package/claude/skills/setup-init/REQUIREMENT.md +45 -0
- package/claude/skills/setup-init/SKILL.md +127 -0
- package/claude/skills/setup-plugins/REQUIREMENT.md +42 -0
- package/claude/skills/setup-plugins/SKILL.md +81 -0
- package/claude/skills/setup-plugins/references/plugin-catalog.md +53 -0
- package/claude/skills/setup-verify/REQUIREMENT.md +39 -0
- package/claude/skills/setup-verify/SKILL.md +51 -0
- package/claude/skills/systematic-debugging/REQUIREMENT.md +41 -0
- package/claude/skills/systematic-debugging/SKILL.md +70 -0
- package/claude/skills/write-human/REQUIREMENT.md +46 -0
- package/claude/skills/write-human/SKILL.md +68 -0
- package/claude/skills/write-human/references/density.md +38 -0
- package/claude/skills/write-human/references/machine-tells.md +107 -0
- package/claude/skills/write-human/references/source-material.md +37 -0
- package/claude/skills/youtube-transcripts/REQUIREMENT.md +38 -0
- package/claude/skills/youtube-transcripts/SKILL.md +34 -0
- package/docs/agents/audits.md +98 -0
- package/docs/agents/capture.md +37 -0
- package/docs/agents/census.md +23 -0
- package/docs/agents/commands.md +146 -0
- package/docs/agents/comments.md +34 -0
- package/docs/agents/context-audit-checks.md +120 -0
- package/docs/agents/context-audit.md +83 -0
- package/docs/agents/counts.md +76 -0
- package/docs/agents/demo.md +86 -0
- package/docs/agents/docs.md +17 -0
- package/docs/agents/gate.md +84 -0
- package/docs/agents/index.md +47 -0
- package/docs/agents/indexes.md +35 -0
- package/docs/agents/install-and-sync.md +385 -0
- package/docs/agents/intake.md +81 -0
- package/docs/agents/key-changes.md +103 -0
- package/docs/agents/label-coverage.md +73 -0
- package/docs/agents/markdown-audit.md +197 -0
- package/docs/agents/output-shape.md +70 -0
- package/docs/agents/overview.md +26 -0
- package/docs/agents/records.md +170 -0
- package/docs/agents/restated.md +81 -0
- package/docs/agents/review-classification.md +77 -0
- package/docs/agents/routing.md +61 -0
- package/docs/agents/rule-citations.md +98 -0
- package/docs/agents/sandbox.md +71 -0
- package/docs/agents/scripting.md +149 -0
- package/docs/agents/sessions.md +120 -0
- package/docs/agents/skills-audit.md +94 -0
- package/docs/agents/skills-reach.md +64 -0
- package/docs/agents/standards-audit.md +38 -0
- package/docs/agents/state-scoped-risk.md +105 -0
- package/docs/agents/superseded.md +85 -0
- package/docs/agents/targets.md +83 -0
- package/docs/agents/tasks.md +200 -0
- package/docs/agents/teach.md +158 -0
- package/docs/agents/test-order.md +56 -0
- package/docs/agents/worktrees.md +62 -0
- package/docs/ai-workflow.md +317 -0
- package/docs/index.md +23 -0
- package/docs/operating-model.md +223 -0
- package/docs/target-projects.md +258 -0
- package/docs/visual-design-workflow.md +151 -0
- package/docs/zshrc-aliases.md +65 -0
- package/governance/rules/ci/700-ci-workflow.md +44 -0
- package/governance/rules/claude/500-prose.md +15 -0
- package/governance/rules/claude/501-markdown.md +14 -0
- package/governance/rules/claude/510-context.md +28 -0
- package/governance/rules/claude/511-indexes.md +14 -0
- package/governance/rules/claude/520-wireframes.md +12 -0
- package/governance/rules/claude/530-requirements.md +11 -0
- package/governance/rules/claude/540-architecture.md +11 -0
- package/governance/rules/claude/550-design.md +11 -0
- package/governance/rules/claude/555-tasks.md +12 -0
- package/governance/rules/claude/556-groundwork.md +11 -0
- package/governance/rules/claude/557-intake.md +11 -0
- package/governance/rules/claude/558-plan.md +22 -0
- package/governance/rules/claude/559-memory.md +11 -0
- package/governance/rules/claude/560-diagrams.md +18 -0
- package/governance/rules/claude/561-teach.md +13 -0
- package/governance/rules/claude/562-session.md +15 -0
- package/governance/rules/claude/570-skill.md +24 -0
- package/governance/rules/claude/575-hooks.md +17 -0
- package/governance/rules/claude/576-settings.md +14 -0
- package/governance/rules/claude/580-readme.md +11 -0
- package/governance/rules/claude/590-rule-authoring.md +12 -0
- package/governance/rules/claude/591-standard-authoring.md +12 -0
- package/governance/rules/claude/592-claude-md.md +19 -0
- package/governance/rules/core/000-constitution.md +30 -0
- package/governance/rules/core/005-behavior.md +27 -0
- package/governance/rules/core/010-testing.md +35 -0
- package/governance/rules/core/015-output.md +20 -0
- package/governance/rules/core/020-concurrency.md +22 -0
- package/governance/rules/core/025-indexes.md +9 -0
- package/governance/rules/core/030-error-handling.md +31 -0
- package/governance/rules/core/035-tasks.md +13 -0
- package/governance/rules/core/040-performance.md +20 -0
- package/governance/rules/core/045-memory.md +12 -0
- package/governance/rules/core/050-logging.md +20 -0
- package/governance/rules/core/055-scratch.md +9 -0
- package/governance/rules/core/060-naming.md +19 -0
- package/governance/rules/core/065-spelling.md +19 -0
- package/governance/rules/core/070-planning.md +18 -0
- package/governance/rules/core/075-dependencies.md +25 -0
- package/governance/rules/core/080-config-comments.md +22 -0
- package/governance/rules/core/085-worktrees.md +17 -0
- package/governance/rules/core/087-git.md +11 -0
- package/governance/rules/core/090-code-comments.md +39 -0
- package/governance/rules/framework/200-react.md +51 -0
- package/governance/rules/framework/210-astro.md +41 -0
- package/governance/rules/framework/220-fastapi.md +43 -0
- package/governance/rules/framework/230-nextjs.md +48 -0
- package/governance/rules/framework/250-tailwind.md +32 -0
- package/governance/rules/framework/260-shadcn.md +34 -0
- package/governance/rules/lang/100-typescript.md +40 -0
- package/governance/rules/lang/110-python.md +42 -0
- package/governance/rules/lang/120-bash.md +19 -0
- package/governance/rules/lib/300-testing-ts.md +39 -0
- package/governance/rules/lib/305-e2e-reliability.md +34 -0
- package/governance/rules/lib/306-test-scope.md +25 -0
- package/governance/rules/lib/310-zod.md +25 -0
- package/governance/rules/lib/320-tanstack-query.md +32 -0
- package/governance/rules/lib/330-testing-py.md +44 -0
- package/governance/rules/lib/340-pydantic.md +38 -0
- package/governance/rules/lib/350-security-web.md +32 -0
- package/governance/rules/lib/360-security-server.md +39 -0
- package/governance/rules/lib/370-database.md +35 -0
- package/governance/rules/snippets/505-at-references.md +9 -0
- package/governance/rules/ui/400-ui.md +36 -0
- package/governance/rules/ui/410-a11y.md +48 -0
- package/governance/rules/ui/420-forms.md +36 -0
- package/governance/rules/ui/430-ux-completeness.md +65 -0
- package/governance/rules/ui/440-surface-capture.md +34 -0
- package/governance/rules/ui/450-link-behavior.md +19 -0
- package/governance/stacks/astro.toml +2 -0
- package/governance/stacks/base.toml +8 -0
- package/governance/stacks/node-server.toml +2 -0
- package/governance/stacks/node.toml +2 -0
- package/governance/stacks/python-fastapi.toml +2 -0
- package/governance/stacks/python.toml +2 -0
- package/governance/stacks/react.toml +2 -0
- package/package.json +69 -0
- package/scripts/config.sh +11 -0
- package/scripts/core/bootstrap.sh +81 -0
- package/scripts/core/check-color-source.sh +41 -0
- package/scripts/core/check-ignore-parity.sh +162 -0
- package/scripts/core/check-plugin-boundary.sh +45 -0
- package/scripts/core/check-seed-independence.sh +59 -0
- package/scripts/core/check-skill-paths.sh +24 -0
- package/scripts/core/clean.sh +36 -0
- package/scripts/core/install-check.sh +101 -0
- package/scripts/core/list-seed-roots.sh +18 -0
- package/scripts/core/regen-claude-copies.sh +10 -0
- package/scripts/core/regen-hero.sh +217 -0
- package/scripts/core/regen-indexes.sh +10 -0
- package/scripts/core/regen-tooling-paths.sh +61 -0
- package/scripts/core/repair-bare-flag.sh +19 -0
- package/scripts/core/snapshot.sh +134 -0
- package/scripts/core/update.sh +35 -0
- package/scripts/docs/list.sh +165 -0
- package/scripts/lib/frontmatter.sh +30 -0
- package/scripts/lib/gov.sh +14 -0
- package/scripts/lib/sandbox-fixtures.sh +191 -0
- package/scripts/lib/sandbox-git.sh +125 -0
- package/scripts/lib/sandbox-path.sh +206 -0
- package/scripts/lib/tooling.sh +35 -0
- package/scripts/lib/ui.sh +266 -0
- package/scripts/lib/worktree.sh +20 -0
- package/scripts/manage-sandbox.sh +466 -0
- package/scripts/snippets/create.sh +156 -0
- package/scripts/standards/list.sh +115 -0
- package/scripts/tooling/create.sh +109 -0
- package/scripts/tooling/verify.sh +179 -0
- package/snippets/align.md +12 -0
- package/snippets/claude/decision-memo.md +39 -0
- package/snippets/claude/feature-recap.md +19 -0
- package/snippets/claude/figma-steps.md +24 -0
- package/snippets/compact-summary.md +5 -0
- package/snippets/decision-help.md +6 -0
- package/snippets/meta-prompt.md +14 -0
- package/snippets/research-prompt.md +7 -0
- package/snippets/session-notes.md +11 -0
- package/snippets/snippets.toml +5 -0
- package/snippets/step-by-step.md +10 -0
- package/snippets/web-research.md +21 -0
- package/src/audits/baseline.ts +201 -0
- package/src/audits/catalog.ts +876 -0
- package/src/audits/run.ts +204 -0
- package/src/autoship/classify.ts +75 -0
- package/src/autoship/paths.ts +51 -0
- package/src/binary.ts +16 -0
- package/src/browser/engine.ts +40 -0
- package/src/census/count.ts +113 -0
- package/src/claude/cases/all.ts +24 -0
- package/src/claude/cases/authoring.ts +53 -0
- package/src/claude/cases/claude-workflow.ts +158 -0
- package/src/claude/cases/git.ts +44 -0
- package/src/claude/cases/misc.ts +27 -0
- package/src/claude/cases/setup.ts +94 -0
- package/src/claude/gitignore.ts +51 -0
- package/src/claude/routing.ts +283 -0
- package/src/claude/seeds-list.ts +47 -0
- package/src/claude/seeds.ts +150 -0
- package/src/claude/settings.ts +151 -0
- package/src/claude/skills-audit.ts +228 -0
- package/src/claude/skills-drift.ts +156 -0
- package/src/claude/skills-list.ts +99 -0
- package/src/claude/skills-rank.ts +320 -0
- package/src/claude/skills-reach.ts +227 -0
- package/src/cli-run.ts +43 -0
- package/src/cli.ts +200 -0
- package/src/commands/audits.ts +350 -0
- package/src/commands/autoship.ts +129 -0
- package/src/commands/capture.ts +133 -0
- package/src/commands/census.ts +105 -0
- package/src/commands/claude.ts +1286 -0
- package/src/commands/comments.ts +240 -0
- package/src/commands/context.ts +857 -0
- package/src/commands/demo.ts +389 -0
- package/src/commands/deps.ts +173 -0
- package/src/commands/design.ts +36 -0
- package/src/commands/docs.ts +60 -0
- package/src/commands/feedback-format.ts +23 -0
- package/src/commands/feedback.ts +112 -0
- package/src/commands/gate.ts +189 -0
- package/src/commands/gov.ts +1265 -0
- package/src/commands/indexes.ts +184 -0
- package/src/commands/init.ts +113 -0
- package/src/commands/intake.ts +406 -0
- package/src/commands/inventory.ts +256 -0
- package/src/commands/labels.ts +361 -0
- package/src/commands/markdown.ts +544 -0
- package/src/commands/migrate.ts +175 -0
- package/src/commands/pass-through.ts +39 -0
- package/src/commands/pr.ts +411 -0
- package/src/commands/records.ts +728 -0
- package/src/commands/sandbox.ts +468 -0
- package/src/commands/secrets.ts +132 -0
- package/src/commands/serve.ts +159 -0
- package/src/commands/sessions.ts +408 -0
- package/src/commands/slides.ts +126 -0
- package/src/commands/snippets.ts +84 -0
- package/src/commands/standards.ts +247 -0
- package/src/commands/sync.ts +428 -0
- package/src/commands/targets.ts +319 -0
- package/src/commands/tasks.ts +743 -0
- package/src/commands/teach.ts +786 -0
- package/src/commands/tooling.ts +573 -0
- package/src/commands/transcripts.ts +44 -0
- package/src/commands/upgrade.ts +231 -0
- package/src/commands/wiki.ts +100 -0
- package/src/commands/worktrees.ts +191 -0
- package/src/comments/scan.ts +338 -0
- package/src/comments/trend.ts +207 -0
- package/src/comments/vocabulary.ts +85 -0
- package/src/context/architecture.ts +364 -0
- package/src/context/audit.ts +790 -0
- package/src/context/citations.ts +196 -0
- package/src/context/folders.ts +186 -0
- package/src/context/gate.ts +57 -0
- package/src/context/index-drift.ts +64 -0
- package/src/context/narration.ts +99 -0
- package/src/copy.ts +30 -0
- package/src/counts/catalogs.ts +96 -0
- package/src/counts/numbers.ts +79 -0
- package/src/counts/scan.ts +314 -0
- package/src/demo/beats.ts +135 -0
- package/src/demo/compile.ts +326 -0
- package/src/demo/container.ts +63 -0
- package/src/demo/cursors.ts +55 -0
- package/src/demo/drive.ts +357 -0
- package/src/demo/pointer.ts +178 -0
- package/src/demo/theme.ts +112 -0
- package/src/deps/audit.ts +153 -0
- package/src/design/parse.ts +116 -0
- package/src/design/render.ts +249 -0
- package/src/docs/read.ts +77 -0
- package/src/exec.ts +16 -0
- package/src/exempt-marker.ts +43 -0
- package/src/frontmatter.ts +13 -0
- package/src/gate/measures.ts +682 -0
- package/src/gate/sequencer.ts +386 -0
- package/src/gate/stages.ts +412 -0
- package/src/git-env.ts +36 -0
- package/src/git-files.ts +105 -0
- package/src/git-ignore.ts +46 -0
- package/src/github-format.ts +13 -0
- package/src/github.ts +24 -0
- package/src/gov/adapter.ts +103 -0
- package/src/gov/citations.ts +514 -0
- package/src/gov/consumed.ts +129 -0
- package/src/gov/install.ts +132 -0
- package/src/gov/list.ts +106 -0
- package/src/gov/payload.ts +39 -0
- package/src/gov/restated.ts +814 -0
- package/src/gov/stacks.ts +205 -0
- package/src/gov/superseded.ts +415 -0
- package/src/gov/test-order.ts +407 -0
- package/src/indexes/frontmatter.ts +46 -0
- package/src/indexes/regen.ts +84 -0
- package/src/indexes/render.ts +201 -0
- package/src/indexes/walk.ts +83 -0
- package/src/init/flags.ts +60 -0
- package/src/init/plan.ts +114 -0
- package/src/init/run.ts +46 -0
- package/src/init/steps.ts +77 -0
- package/src/intake/folder.ts +320 -0
- package/src/intake/items.ts +174 -0
- package/src/inventory/config.ts +117 -0
- package/src/inventory/group.ts +76 -0
- package/src/inventory/subjects.ts +114 -0
- package/src/inventory/walk.ts +129 -0
- package/src/labels/audit.ts +82 -0
- package/src/labels/coverage.ts +79 -0
- package/src/labels/map.ts +101 -0
- package/src/labels/phase.ts +95 -0
- package/src/markdown/bans.ts +94 -0
- package/src/markdown/files.ts +102 -0
- package/src/markdown/gate.ts +28 -0
- package/src/markdown/scan.ts +295 -0
- package/src/markdown/structure.ts +730 -0
- package/src/migrate/apply.ts +115 -0
- package/src/migrate/plan.ts +103 -0
- package/src/migrate/rename.ts +183 -0
- package/src/pr/bijection.ts +145 -0
- package/src/pr/paths.ts +335 -0
- package/src/process/harness.ts +167 -0
- package/src/project-root.ts +19 -0
- package/src/records/backup.ts +455 -0
- package/src/records/migrate.ts +78 -0
- package/src/records/size.ts +260 -0
- package/src/records/validate.ts +1162 -0
- package/src/sandbox/census.ts +228 -0
- package/src/sandbox/coverage.ts +115 -0
- package/src/sandbox/expect.ts +629 -0
- package/src/sandbox/tree.ts +47 -0
- package/src/secrets/marker.ts +30 -0
- package/src/secrets/patterns.ts +142 -0
- package/src/secrets/scan.ts +123 -0
- package/src/secrets/shipped.ts +111 -0
- package/src/seed-marker.ts +74 -0
- package/src/serve/static.ts +322 -0
- package/src/sessions/claim.ts +85 -0
- package/src/sessions/live.ts +79 -0
- package/src/sessions/registry.ts +137 -0
- package/src/sessions/resolve.ts +333 -0
- package/src/slides/layouts.ts +391 -0
- package/src/slides/open.ts +18 -0
- package/src/slides/parse.ts +84 -0
- package/src/slides/render.ts +88 -0
- package/src/slides/styles.ts +44 -0
- package/src/snippets/categories.ts +66 -0
- package/src/snippets/list.ts +32 -0
- package/src/snippets/presets.ts +50 -0
- package/src/standards/audit.ts +132 -0
- package/src/standards/read.ts +100 -0
- package/src/sync/check.ts +692 -0
- package/src/sync/engine.ts +576 -0
- package/src/sync/git.ts +225 -0
- package/src/sync/history.ts +123 -0
- package/src/sync/layout.ts +140 -0
- package/src/sync/reverse.ts +268 -0
- package/src/sync/seeds-report.ts +126 -0
- package/src/sync/stamp.ts +358 -0
- package/src/sync/target.ts +70 -0
- package/src/sync/workflow.ts +200 -0
- package/src/target.ts +43 -0
- package/src/targets/pulls.ts +250 -0
- package/src/targets/registry.ts +203 -0
- package/src/targets/resolve.ts +145 -0
- package/src/targets/sweep.ts +246 -0
- package/src/tasks/archive.ts +506 -0
- package/src/tasks/record.ts +311 -0
- package/src/tasks/trunk.ts +89 -0
- package/src/tasks/validate.ts +1001 -0
- package/src/teach/lesson.ts +180 -0
- package/src/teach/workspace.ts +842 -0
- package/src/tooling/gitignore.ts +122 -0
- package/src/tooling/inject.ts +193 -0
- package/src/tooling/list.ts +39 -0
- package/src/tooling/manifest.ts +176 -0
- package/src/tooling/package.ts +166 -0
- package/src/tooling/read.ts +65 -0
- package/src/tooling/scan.ts +147 -0
- package/src/tooling/stamp.ts +44 -0
- package/src/transcripts/fetch.ts +156 -0
- package/src/transcripts/metadata.ts +54 -0
- package/src/transcripts/vtt.ts +114 -0
- package/src/ui.ts +266 -0
- package/src/version/compare.ts +53 -0
- package/src/version/installed.ts +40 -0
- package/src/version/manager.ts +67 -0
- package/src/version/skew.ts +192 -0
- package/src/wiki/init.ts +85 -0
- package/src/worktree.ts +143 -0
- package/src/worktrees/reclaim.ts +306 -0
- package/standards/architecture.md +72 -0
- package/standards/branch.md +59 -0
- package/standards/commit.md +72 -0
- package/standards/context.md +151 -0
- package/standards/design.md +93 -0
- package/standards/diagrams.md +152 -0
- package/standards/glossary.md +75 -0
- package/standards/groundwork.md +211 -0
- package/standards/index.md +36 -0
- package/standards/intake.md +192 -0
- package/standards/issue.md +94 -0
- package/standards/markdown.md +137 -0
- package/standards/memory.md +144 -0
- package/standards/plan.md +172 -0
- package/standards/pr.md +139 -0
- package/standards/publish.md +51 -0
- package/standards/readme.md +208 -0
- package/standards/requirements.md +70 -0
- package/standards/rule.md +118 -0
- package/standards/session.md +109 -0
- package/standards/skill.md +300 -0
- package/standards/slug.md +39 -0
- package/standards/snippets.md +76 -0
- package/standards/standard.md +170 -0
- package/standards/tasks.md +254 -0
- package/standards/teach.md +153 -0
- package/standards/versioning.md +71 -0
- package/standards/wireframes.md +113 -0
- package/tooling/astro/configs/astro.config.mjs +31 -0
- package/tooling/astro/configs/eslint.config.js +79 -0
- package/tooling/astro/configs/playwright.config.ts +26 -0
- package/tooling/astro/configs/tsconfig.json +12 -0
- package/tooling/astro/configs/vitest.config.ts +22 -0
- package/tooling/astro/manifest.toml +34 -0
- package/tooling/astro/reference.md +60 -0
- package/tooling/base/configs/.editorconfig +5 -0
- package/tooling/base/configs/.github/pull_request_template.md +18 -0
- package/tooling/base/configs/.github/workflows/verify.yml +35 -0
- package/tooling/base/configs/.husky/commit-msg +1 -0
- package/tooling/base/configs/.husky/post-merge +61 -0
- package/tooling/base/configs/.husky/post-rewrite +21 -0
- package/tooling/base/configs/.husky/pre-commit +1 -0
- package/tooling/base/configs/.husky/pre-push +1 -0
- package/tooling/base/configs/.prettierrc +12 -0
- package/tooling/base/configs/.shellcheckrc +1 -0
- package/tooling/base/configs/.vscode/extensions.json +9 -0
- package/tooling/base/configs/.vscode/settings.json +3 -0
- package/tooling/base/configs/commitlint.config.js +11 -0
- package/tooling/base/configs/scripts/verify.sh +64 -0
- package/tooling/base/manifest.toml +30 -0
- package/tooling/base/reference.md +98 -0
- package/tooling/base/seeds/.claude/context/ci.md +33 -0
- package/tooling/base/seeds/.claude/context/development.md +37 -0
- package/tooling/base/seeds/.claude/context/index.md +11 -0
- package/tooling/base/seeds/.cspell/project-terms.txt +0 -0
- package/tooling/base/seeds/.cspell/tech-stack.txt +19 -0
- package/tooling/base/seeds/.lintstagedrc +8 -0
- package/tooling/base/seeds/.prettierignore +0 -0
- package/tooling/base/seeds/cspell.json +20 -0
- package/tooling/claude/manifest.toml +14 -0
- package/tooling/claude/reference.md +79 -0
- package/tooling/claude/seeds/.claude/ARCHITECTURE.md +13 -0
- package/tooling/claude/seeds/.claude/DESIGN.md +62 -0
- package/tooling/claude/seeds/.claude/REQUIREMENTS.md +18 -0
- package/tooling/claude/seeds/.claude/diagrams/index.md +8 -0
- package/tooling/claude/seeds/.claude/hooks/index-reminder.sh +50 -0
- package/tooling/claude/seeds/.claude/hooks/memory-index.sh +68 -0
- package/tooling/claude/seeds/.claude/hooks/path-form.sh +57 -0
- package/tooling/claude/seeds/.claude/hooks/scratch-guard.sh +52 -0
- package/tooling/claude/seeds/.claude/hooks/standards-audit.sh +86 -0
- package/tooling/claude/seeds/.claude/hooks/tasks-index.sh +71 -0
- package/tooling/claude/seeds/.claude/memory/index.md +8 -0
- package/tooling/claude/seeds/.claude/settings.json +47 -0
- package/tooling/claude/seeds/.claude/tasks/index.md +8 -0
- package/tooling/claude/seeds/.claude/wireframes/index.md +8 -0
- package/tooling/claude/seeds/CLAUDE.md +29 -0
- package/tooling/claude/user/settings.template.json +10 -0
- package/tooling/claude/user/statusline-command.sh +53 -0
- package/tooling/python/configs/.coveragerc +14 -0
- package/tooling/python/configs/.python-version +1 -0
- package/tooling/python/configs/mypy.ini +6 -0
- package/tooling/python/configs/pytest.ini +4 -0
- package/tooling/python/configs/ruff.toml +15 -0
- package/tooling/python/configs/scripts/verify.sh +77 -0
- package/tooling/python/manifest.toml +16 -0
- package/tooling/python/reference.md +66 -0
- package/tooling/python/seeds/.cspell/tech-stack.txt +19 -0
- package/tooling/python/seeds/tests/test_smoke.py +2 -0
- package/tooling/vite-react/configs/playwright.config.ts +26 -0
- package/tooling/vite-react/configs/tsconfig.json +35 -0
- package/tooling/vite-react/configs/vite.config.ts +24 -0
- package/tooling/vite-react/configs/vitest.config.ts +26 -0
- package/tooling/vite-react/manifest.toml +23 -0
- package/tooling/vite-react/reference.md +55 -0
- package/tooling/vite-react/seeds/.cspell/project-terms.txt +1 -0
- package/tooling/vite-react/seeds/.cspell/tech-stack.txt +1 -0
- package/tooling/web/configs/.github/workflows/verify.yml +134 -0
- package/tooling/web/configs/.vscode/extensions.json +13 -0
- package/tooling/web/configs/.vscode/settings.json +10 -0
- package/tooling/web/configs/e2e/home.spec.ts +6 -0
- package/tooling/web/configs/e2e/screenshot.ts +53 -0
- package/tooling/web/configs/eslint.config.js +82 -0
- package/tooling/web/configs/scripts/screenshot.sh +28 -0
- package/tooling/web/configs/scripts/verify.sh +80 -0
- package/tooling/web/configs/scripts/worktree-port.sh +74 -0
- package/tooling/web/configs/src/test/setup.ts +8 -0
- package/tooling/web/manifest.toml +58 -0
- package/tooling/web/reference.md +115 -0
- package/tooling/web/seeds/.cspell/tech-stack.txt +18 -0
- package/tsconfig.json +14 -0
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Keep comments terse in dotfiles, config, and workflow files
|
|
3
|
+
paths:
|
|
4
|
+
- '**/.env*'
|
|
5
|
+
- '**/.gitignore'
|
|
6
|
+
- '**/.dockerignore'
|
|
7
|
+
- '**/.editorconfig'
|
|
8
|
+
- '**/Dockerfile*'
|
|
9
|
+
- '**/*.config.*'
|
|
10
|
+
- '**/*.json'
|
|
11
|
+
- '**/*.yml'
|
|
12
|
+
- '**/*.yaml'
|
|
13
|
+
---
|
|
14
|
+
|
|
15
|
+
# Config comment standards
|
|
16
|
+
|
|
17
|
+
## Comments
|
|
18
|
+
|
|
19
|
+
- Keep each comment to one short line. Do not wrap a single key in a multi-line explanation.
|
|
20
|
+
- Prefer a one-word category label over a sentence for a group header.
|
|
21
|
+
- Match the comment density of the surrounding file. Do not add a verbose comment next to terse ones.
|
|
22
|
+
- Comment what a key does or its allowed values. Do not restate the key name.
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Route tracked-file writes and shared session scratch correctly from a linked worktree
|
|
3
|
+
---
|
|
4
|
+
|
|
5
|
+
# Worktrees standards
|
|
6
|
+
|
|
7
|
+
## Entering a worktree
|
|
8
|
+
|
|
9
|
+
- Implementation work runs in a linked worktree. From the main worktree, enter one with `/claude-worktree` before editing tracked files for a feature.
|
|
10
|
+
|
|
11
|
+
## Shared session scratch
|
|
12
|
+
|
|
13
|
+
- Shared session scratch (`.claude/plans/`, `.claude/review/`, `.claude/memory/`, `.claude/tasks/`) lives at the main worktree root, not inside a linked worktree. From a linked worktree, resolve these paths against the main root via `git worktree list --porcelain | grep -m 1 '^worktree ' | cut -d' ' -f2-`. Fall back to `pwd` if not a git repo.
|
|
14
|
+
- From a linked worktree, every `Edit` or `Write` to a tracked file (source, docs) must use a path starting with `pwd`.
|
|
15
|
+
- From a linked worktree, `Edit` and `Write` are refused for every main-root path, session scratch included. The refusal names session isolation and points at the worktree copy, which is a second gitignored file no later session reads, so never take that redirect.
|
|
16
|
+
- `Read` resolves against the main root normally from a linked worktree. A main-root write reaches it only through `Bash`, as one plain command rather than a compound one, which is refused for complexity.
|
|
17
|
+
- Route a main-root write by what it does to the file. Creating a whole file goes out as one plain `Bash` command carrying a heredoc. Changing a line inside a file that already exists goes through a command that resolves the main root in-process, because the shell route for that case is the stream editor this file bans.
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Route every git operation through the canon git skills rather than built-in commit and pull request behavior
|
|
3
|
+
---
|
|
4
|
+
|
|
5
|
+
# Git standards
|
|
6
|
+
|
|
7
|
+
## Skill precedence
|
|
8
|
+
|
|
9
|
+
- Route every git operation through the `canon:git-*` skills.
|
|
10
|
+
- Do not follow built-in commit, pull request, or branch instructions for an operation a `git-*` skill covers.
|
|
11
|
+
- Report it rather than proceeding silently when no `git-*` skill resolves. They ship with the plugin and this rule ships with the CLI, so a project that installed governance alone does not have them.
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Decide when a code comment should exist and what it may claim
|
|
3
|
+
paths:
|
|
4
|
+
- '**/*.ts'
|
|
5
|
+
- '**/*.tsx'
|
|
6
|
+
- '**/*.js'
|
|
7
|
+
- '**/*.jsx'
|
|
8
|
+
- '**/*.sh'
|
|
9
|
+
- '**/*.py'
|
|
10
|
+
---
|
|
11
|
+
|
|
12
|
+
# Code comment standards
|
|
13
|
+
|
|
14
|
+
## When a comment should exist
|
|
15
|
+
|
|
16
|
+
- Write a comment only when it records a fact the reader cannot recover from the code: an external contract, a rejected alternative, or the reason a surprising line is correct.
|
|
17
|
+
- Do not restate in prose what the line beside it already says.
|
|
18
|
+
- Do not comment a self-contained function whose signature and body already carry its behavior.
|
|
19
|
+
- Let comment density follow how much of a file's behavior is decided outside that file. Treat density as an outcome, never as a target.
|
|
20
|
+
- Do not add or delete a comment to move a file toward a density figure.
|
|
21
|
+
|
|
22
|
+
## What a comment may claim
|
|
23
|
+
|
|
24
|
+
- State only what is true of the code as written.
|
|
25
|
+
- Describe a function's contract and its constraints, never its steps line by line.
|
|
26
|
+
- Update or delete an invalidated comment in the same change that invalidates it.
|
|
27
|
+
- Do not name a person, a ticket, or a date in place of the fact itself.
|
|
28
|
+
|
|
29
|
+
## What never goes in a comment
|
|
30
|
+
|
|
31
|
+
- Delete commented-out code. Do not park it beside the live path.
|
|
32
|
+
- Do not record the edit that produced the code. Version control holds the change history.
|
|
33
|
+
- Do not defer work into a comment. Deferred work belongs in the tracker.
|
|
34
|
+
|
|
35
|
+
## Degradation vocabulary
|
|
36
|
+
|
|
37
|
+
Do not write a comment carrying any of these terms.
|
|
38
|
+
|
|
39
|
+
- `FIXED`, `BUGFIX`, `HACK`, `XXX`, `NOTE:`, `TODO`, `FIXME`, `don't remove`, `previously`, `used to`, `workaround`
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Enforce opinionated React architecture and component patterns
|
|
3
|
+
paths:
|
|
4
|
+
- '**/*.tsx'
|
|
5
|
+
- '**/*.ts'
|
|
6
|
+
---
|
|
7
|
+
|
|
8
|
+
# React architecture standards
|
|
9
|
+
|
|
10
|
+
## Export conventions
|
|
11
|
+
|
|
12
|
+
- Use named exports exclusively for components and hooks.
|
|
13
|
+
- Do not use default exports.
|
|
14
|
+
|
|
15
|
+
## Project structure
|
|
16
|
+
|
|
17
|
+
- Place domain logic in `src/features/` and restrict `src/components/` to shared UI.
|
|
18
|
+
- Do not place feature-specific components in the global components folder.
|
|
19
|
+
- Import environment variables only from the validated configuration module.
|
|
20
|
+
|
|
21
|
+
## Component patterns
|
|
22
|
+
|
|
23
|
+
- Use function declarations for components over arrow functions.
|
|
24
|
+
- Define TypeScript interfaces for props immediately above the component.
|
|
25
|
+
- Use `<>` shorthand for fragments unless key prop is required.
|
|
26
|
+
- Use stable, unique keys for list items over array index.
|
|
27
|
+
- Extract components when JSX exceeds a single responsibility.
|
|
28
|
+
|
|
29
|
+
## State and effects
|
|
30
|
+
|
|
31
|
+
- Encapsulate data fetching and complex effects in custom hooks.
|
|
32
|
+
- Use `useMemo` for derived state over `useEffect`.
|
|
33
|
+
- Do not call `setState` inside `useEffect` to sync derived state. The `react-hooks/set-state-in-effect` lint enforces this.
|
|
34
|
+
- Compare the previous value during render and call `setState` from the render body when it changes, over syncing in an effect.
|
|
35
|
+
- Lift the state to a parent and reset the child with a `key` prop, over running a reset effect in the child.
|
|
36
|
+
- Return a sentinel (`undefined` or a `useSyncExternalStore` placeholder) from hooks that hydrate asynchronously and gate consumers on it, over running a hydration effect.
|
|
37
|
+
|
|
38
|
+
## Memoization
|
|
39
|
+
|
|
40
|
+
- Memoize components receiving non-primitive props with `React.memo`.
|
|
41
|
+
- Use `useCallback` for handler props passed to children.
|
|
42
|
+
|
|
43
|
+
## Composition and props
|
|
44
|
+
|
|
45
|
+
- Avoid prop drilling beyond 2 levels. Use context or composition.
|
|
46
|
+
|
|
47
|
+
## Error boundaries and Suspense
|
|
48
|
+
|
|
49
|
+
- Place error boundaries at route level.
|
|
50
|
+
- Place Suspense at data-fetching boundaries.
|
|
51
|
+
- Do not use a single root-level error boundary as the only safety net.
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Enforce astro static-first architecture with explicit island opt-in
|
|
3
|
+
paths:
|
|
4
|
+
- '**/*.astro'
|
|
5
|
+
- 'src/pages/**'
|
|
6
|
+
- 'src/layouts/**'
|
|
7
|
+
- 'src/content/**'
|
|
8
|
+
---
|
|
9
|
+
|
|
10
|
+
# Astro standards
|
|
11
|
+
|
|
12
|
+
## Static first
|
|
13
|
+
|
|
14
|
+
- Write pages and components as `.astro` unless interactivity requires a framework island.
|
|
15
|
+
- Do not add a framework integration until the first island needs it.
|
|
16
|
+
- Prefer server-rendered content over client-fetched data.
|
|
17
|
+
|
|
18
|
+
## Islands
|
|
19
|
+
|
|
20
|
+
- Apply `client:*` directives on the component boundary, not on parents.
|
|
21
|
+
- Prefer `client:visible` or `client:idle` over `client:load`. Use `client:load` only for above-the-fold interactivity.
|
|
22
|
+
- Keep islands leaf-level. Do not wrap layout chrome in a framework component to enable nested islands.
|
|
23
|
+
|
|
24
|
+
## Routing and layouts
|
|
25
|
+
|
|
26
|
+
- Place routes in `src/pages/`. Use `[param].astro` for dynamic segments and `[...rest].astro` for catch-alls.
|
|
27
|
+
- Extract shared chrome into `src/layouts/` and compose pages with a `<Layout>` wrapper.
|
|
28
|
+
|
|
29
|
+
## Content
|
|
30
|
+
|
|
31
|
+
- Use content collections in `src/content/` with a `config.ts` schema for any repeated structured content.
|
|
32
|
+
- Access collection entries via `getCollection` and `getEntry` over direct file imports.
|
|
33
|
+
|
|
34
|
+
## Styles and assets
|
|
35
|
+
|
|
36
|
+
- Component styles are scoped by default. Use `is:global` only in layouts for reset or base styles.
|
|
37
|
+
- Import images from `src/assets/` to get optimization. Use `public/` only for untouched static files.
|
|
38
|
+
|
|
39
|
+
## Environment
|
|
40
|
+
|
|
41
|
+
- Read environment variables via `import.meta.env`. Prefix client-exposed variables with `PUBLIC_`.
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Enforce FastAPI router, dependency injection, and async handler patterns
|
|
3
|
+
paths:
|
|
4
|
+
- '**/*.py'
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
# FastAPI standards
|
|
8
|
+
|
|
9
|
+
## Project structure
|
|
10
|
+
|
|
11
|
+
- Mount routes through `APIRouter` modules. Do not register handlers directly on `FastAPI()`.
|
|
12
|
+
- Group routers by feature under `src/<pkg>/api/` and include them from the root app factory.
|
|
13
|
+
- Use an `app_factory()` callable over a module-level `app = FastAPI()` for testability.
|
|
14
|
+
|
|
15
|
+
## Handlers
|
|
16
|
+
|
|
17
|
+
- Define path operations as `async def` unless the handler is purely CPU-bound.
|
|
18
|
+
- Do not perform blocking I/O inside `async def`. Use async clients or `run_in_threadpool`.
|
|
19
|
+
- Annotate path, query, and body parameters explicitly. Do not rely on `**kwargs`.
|
|
20
|
+
- Return pydantic models and set `response_model=` on the decorator for serialization control.
|
|
21
|
+
|
|
22
|
+
## Dependency injection
|
|
23
|
+
|
|
24
|
+
- Express shared logic (auth, db sessions, settings) as `Depends(...)` over decorators or globals.
|
|
25
|
+
- Use `Annotated[T, Depends(...)]` over default-value `Depends()` for reusable dependencies.
|
|
26
|
+
- Scope db sessions per request via a generator dependency that yields then closes.
|
|
27
|
+
|
|
28
|
+
## Lifespan and configuration
|
|
29
|
+
|
|
30
|
+
- Use the `lifespan` context manager for startup and shutdown over deprecated `@app.on_event`.
|
|
31
|
+
- Load settings via `pydantic_settings.BaseSettings`, injected through a cached dependency.
|
|
32
|
+
|
|
33
|
+
## Errors
|
|
34
|
+
|
|
35
|
+
- Raise `HTTPException` for client-facing errors with explicit status codes.
|
|
36
|
+
- Register `@app.exception_handler` mappings for domain exceptions over per-route try/except.
|
|
37
|
+
- Do not leak internal exception messages. Map to safe summaries at the boundary.
|
|
38
|
+
|
|
39
|
+
## Validation and security
|
|
40
|
+
|
|
41
|
+
- Validate request bodies through pydantic models. Do not parse `Request.json()` manually.
|
|
42
|
+
- Apply `dependencies=[Depends(auth)]` at the router or app level for cross-cutting auth.
|
|
43
|
+
- Configure CORS, trusted hosts, and HTTPS redirects through middleware, not per-route checks.
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Enforce Next.js App Router structure, server/client boundaries, and built-in primitives
|
|
3
|
+
paths:
|
|
4
|
+
- '**/*.tsx'
|
|
5
|
+
- '**/*.ts'
|
|
6
|
+
---
|
|
7
|
+
|
|
8
|
+
# Next.js standards
|
|
9
|
+
|
|
10
|
+
## App Router structure
|
|
11
|
+
|
|
12
|
+
- Use the App Router under `app/`. Do not introduce `pages/` in new code.
|
|
13
|
+
- Use route segment files for their documented purpose: `page.tsx` for routes, `layout.tsx` for shared shells, `loading.tsx` for Suspense fallbacks, `error.tsx` for error boundaries, `route.ts` for HTTP handlers.
|
|
14
|
+
|
|
15
|
+
## Server and client components
|
|
16
|
+
|
|
17
|
+
- Default to Server Components. Add `"use client"` only when the file needs state, effects, browser APIs, or event handlers.
|
|
18
|
+
- Place `"use client"` at the leaf, not at the layout. Push the boundary as deep as possible.
|
|
19
|
+
- Do not import server-only modules (`fs`, db clients, secrets) from a client component. Mark server-only modules with `import "server-only"`.
|
|
20
|
+
- Pass serializable props across the server/client boundary. Do not pass functions or class instances.
|
|
21
|
+
|
|
22
|
+
## Data fetching
|
|
23
|
+
|
|
24
|
+
- Fetch data in Server Components or Route Handlers. Do not fetch in client components when a server alternative exists.
|
|
25
|
+
- Set explicit caching on `fetch`: `cache: "force-cache"`, `cache: "no-store"`, or `next: { revalidate: <seconds> }`. Do not rely on defaults.
|
|
26
|
+
- Use `revalidatePath` or `revalidateTag` for invalidation over manual refetch loops.
|
|
27
|
+
|
|
28
|
+
## Server Actions
|
|
29
|
+
|
|
30
|
+
- Mark Server Actions with `"use server"` at the top of the file or function.
|
|
31
|
+
- Validate Server Action inputs with a Zod schema before use. The client/server boundary is implicit and easy to miss.
|
|
32
|
+
- Return serializable values. Do not return Response or stream objects from a Server Action.
|
|
33
|
+
|
|
34
|
+
## Route handlers
|
|
35
|
+
|
|
36
|
+
- Place HTTP endpoints in `app/**/route.ts`. Do not add `pages/api/`.
|
|
37
|
+
- Export named methods (`GET`, `POST`, ...). Return `NextResponse` over raw `Response` for typed helpers.
|
|
38
|
+
- Read params from the function signature (`{ params }`), not from the request URL.
|
|
39
|
+
|
|
40
|
+
## Built-in primitives
|
|
41
|
+
|
|
42
|
+
- Use `next/link` over `<a>` for internal navigation. Use `next/image` over `<img>` for raster images. Use `next/font` over manual `<link>` tags for fonts.
|
|
43
|
+
- Set explicit `width` and `height` (or `fill`) on `next/image`. Do not omit dimensions.
|
|
44
|
+
|
|
45
|
+
## Metadata and environment
|
|
46
|
+
|
|
47
|
+
- Export `metadata` or `generateMetadata` from `layout.tsx` or `page.tsx` over manual `<head>` injection.
|
|
48
|
+
- Prefix browser-exposed env vars with `NEXT_PUBLIC_`. Never read unprefixed server-only env vars from a client component.
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Enforce Tailwind CSS v4 utility patterns, theme tokens, dark mode, and custom styles
|
|
3
|
+
paths:
|
|
4
|
+
- '**/*.tsx'
|
|
5
|
+
- '**/*.jsx'
|
|
6
|
+
- '**/*.html'
|
|
7
|
+
- '**/*.css'
|
|
8
|
+
---
|
|
9
|
+
|
|
10
|
+
# Tailwind CSS v4 standards
|
|
11
|
+
|
|
12
|
+
## Theme variables
|
|
13
|
+
|
|
14
|
+
- Use `@theme` for design tokens that generate utility classes.
|
|
15
|
+
- Use `:root` for plain CSS variables with no utility counterpart.
|
|
16
|
+
- Define dark mode color overrides in `.dark { }` at root level over `@layer base`.
|
|
17
|
+
- Always pair light and dark utilities explicitly: `bg-white dark:bg-gray-900`.
|
|
18
|
+
|
|
19
|
+
## Layout and spacing
|
|
20
|
+
|
|
21
|
+
- Use `flex` and `grid` for all layouts.
|
|
22
|
+
- Never use floats or absolute positioning for flow.
|
|
23
|
+
- Use `gap-*` for sibling spacing over margins.
|
|
24
|
+
- Use `size-*` over `w-* h-*` for equal dimensions.
|
|
25
|
+
- Mobile-first: default styles apply to mobile. Use `sm:` and up to override.
|
|
26
|
+
|
|
27
|
+
## Class application
|
|
28
|
+
|
|
29
|
+
- Use `cn()` from `@/lib/utils` for all conditional class application.
|
|
30
|
+
- Do not use the `!` important modifier.
|
|
31
|
+
- Do not use inline `style` props for static styling. Use arbitrary values (`bg-[#316ff6]`) instead.
|
|
32
|
+
- Use inline styles only for dynamic values from JS/API or to set CSS variables for utility consumption.
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Enforce shadcn/ui v4 component patterns, semantic tokens, and composition rules
|
|
3
|
+
paths:
|
|
4
|
+
- '**/*.tsx'
|
|
5
|
+
- '**/*.jsx'
|
|
6
|
+
---
|
|
7
|
+
|
|
8
|
+
# shadcn/ui standards
|
|
9
|
+
|
|
10
|
+
## Source files
|
|
11
|
+
|
|
12
|
+
- Do not edit component files installed by the shadcn CLI. Treat them as vendored.
|
|
13
|
+
- Check `components.json` for the install path.
|
|
14
|
+
- Extend behavior via wrapper components over modifying installed files.
|
|
15
|
+
|
|
16
|
+
## Component authoring
|
|
17
|
+
|
|
18
|
+
- Use `React.ComponentProps<typeof Primitive>` over `React.forwardRef`.
|
|
19
|
+
- Add `data-slot="component-name"` to every primitive root for Tailwind targeting.
|
|
20
|
+
|
|
21
|
+
## Tokens and styling
|
|
22
|
+
|
|
23
|
+
- Use semantic color tokens (`bg-background`, `text-foreground`, `border-border`) over hardcoded colors.
|
|
24
|
+
- Use `cn()` from `@/lib/utils` for all className merging and conditional classes.
|
|
25
|
+
- Do not override shadcn component internals with arbitrary classes.
|
|
26
|
+
- Extend via `className` prop only.
|
|
27
|
+
|
|
28
|
+
## Composition
|
|
29
|
+
|
|
30
|
+
- Compose shadcn primitives as documented.
|
|
31
|
+
- Do not destructure or restructure internal component trees.
|
|
32
|
+
- Use `asChild` prop with `<Slot>` for polymorphic rendering.
|
|
33
|
+
- Do not wrap primitives in extra DOM elements.
|
|
34
|
+
- Use `sonner` for toasts over the deprecated `toast` component.
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Enforce strict TypeScript type safety and patterns
|
|
3
|
+
paths:
|
|
4
|
+
- '**/*.ts'
|
|
5
|
+
- '**/*.tsx'
|
|
6
|
+
---
|
|
7
|
+
|
|
8
|
+
# TypeScript standards
|
|
9
|
+
|
|
10
|
+
## Casing conventions
|
|
11
|
+
|
|
12
|
+
- Use `kebab-case` for filenames and directories.
|
|
13
|
+
- Use `camelCase` for variables, functions, and methods.
|
|
14
|
+
- Use `PascalCase` for types, interfaces, classes, and components.
|
|
15
|
+
- Use `UPPER_SNAKE_CASE` for constants and environment variables.
|
|
16
|
+
|
|
17
|
+
## Type declarations
|
|
18
|
+
|
|
19
|
+
- Enforce explicit types or strict inference.
|
|
20
|
+
- Use `unknown` over `any`.
|
|
21
|
+
- Use `interface` for object shapes and component props.
|
|
22
|
+
- Use `type` for unions, intersections, and utility types.
|
|
23
|
+
- Do not prefix interfaces with `I`.
|
|
24
|
+
- Use constant objects or union types instead of `enum`.
|
|
25
|
+
|
|
26
|
+
## Type safety
|
|
27
|
+
|
|
28
|
+
- Use type guards and narrowing over type assertions.
|
|
29
|
+
- Use discriminated unions for error handling over throwing exceptions.
|
|
30
|
+
- Use built-in utility types (`Partial`, `Pick`, `Omit`) over manual type manipulation.
|
|
31
|
+
- Prefer `readonly` properties for data objects.
|
|
32
|
+
- Do not use non-null assertions.
|
|
33
|
+
- Use `Promise.all()` for independent async operations.
|
|
34
|
+
|
|
35
|
+
## Imports and configuration
|
|
36
|
+
|
|
37
|
+
- Use absolute imports mapping `@/` to `src/`.
|
|
38
|
+
- Import from the module's source file directly over barrel `index` re-exports.
|
|
39
|
+
- Use `import type` for type-only imports.
|
|
40
|
+
- Enable `strict: true` in tsconfig.json with no exceptions.
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Enforce strict Python type hints, casing, and import patterns
|
|
3
|
+
paths:
|
|
4
|
+
- '**/*.py'
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
# Python standards
|
|
8
|
+
|
|
9
|
+
## Casing conventions
|
|
10
|
+
|
|
11
|
+
- Use `snake_case` for modules, functions, variables, and methods.
|
|
12
|
+
- Use `PascalCase` for classes, type aliases, `TypeVar`, and `ParamSpec`.
|
|
13
|
+
- Use `UPPER_SNAKE_CASE` for module-level constants and environment variables.
|
|
14
|
+
- Use `_leading_underscore` for module-private names. Reserve `__dunder__` for the standard protocol.
|
|
15
|
+
|
|
16
|
+
## Type hints
|
|
17
|
+
|
|
18
|
+
- Annotate all public functions, methods, and class attributes.
|
|
19
|
+
- Use `X | None` over `Optional[X]` and `X | Y` over `Union[X, Y]`.
|
|
20
|
+
- Use built-in generics (`list[str]`, `dict[str, int]`) over `typing.List` and `typing.Dict`.
|
|
21
|
+
- Avoid `from __future__ import annotations` in modules that pydantic, FastAPI, or other libraries introspect at runtime.
|
|
22
|
+
- Use `typing.Protocol` for structural typing over abstract base classes for interfaces.
|
|
23
|
+
- Do not use `Any`. Reach for `object` or `typing.cast` at boundaries instead.
|
|
24
|
+
|
|
25
|
+
## Errors
|
|
26
|
+
|
|
27
|
+
- Raise specific built-in exceptions over bare `Exception`.
|
|
28
|
+
- Define a project-rooted exception hierarchy for domain errors.
|
|
29
|
+
- Catch the narrowest exception class. Never use bare `except:`.
|
|
30
|
+
- Re-raise with `raise ... from err` to preserve the cause chain.
|
|
31
|
+
|
|
32
|
+
## Data shapes
|
|
33
|
+
|
|
34
|
+
- Use `dataclasses.dataclass(frozen=True, slots=True)` for internal value objects.
|
|
35
|
+
- Use `enum.Enum` or `enum.StrEnum` for closed sets over module-level constants.
|
|
36
|
+
- Prefer `pathlib.Path` over `os.path` for filesystem paths.
|
|
37
|
+
|
|
38
|
+
## Imports and modules
|
|
39
|
+
|
|
40
|
+
- Use absolute imports rooted at the package. Do not use parent-relative (`from ..pkg`) imports.
|
|
41
|
+
- Do not alias imports to shorten internal names. Ecosystem conventions (`numpy as np`, `pandas as pd`) are exceptions.
|
|
42
|
+
- Do not place executable code at module scope. Guard with `if __name__ == "__main__":`.
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Route bash script authoring to the interactive or non-interactive skill, and name the lint gate
|
|
3
|
+
paths:
|
|
4
|
+
- '**/*.sh'
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
# Bash standards
|
|
8
|
+
|
|
9
|
+
## Skill routing
|
|
10
|
+
|
|
11
|
+
- Use `canon:bash-script` for an interactive or human-facing script: prompts, a visual timeline UI, framed terminal output.
|
|
12
|
+
- Use `canon:bash-cli-script` for a non-interactive script: automation, CI, cron, a pipeline helper, or anything run by an agent rather than watched by a person.
|
|
13
|
+
- Load the matched skill's own reference templates rather than hand-rolling interactivity or logging patterns outside them.
|
|
14
|
+
- Report it rather than proceeding silently when the matched skill does not resolve. Both ship with the plugin and this rule ships with the CLI, so a project that installed governance alone does not have them.
|
|
15
|
+
|
|
16
|
+
## Lint gate
|
|
17
|
+
|
|
18
|
+
- Format with `shfmt --write --indent 2` and lint with `shellcheck --severity=warning` before committing a script.
|
|
19
|
+
- Fix a shellcheck finding at the source. Suppress one with a directive comment only for a genuine false positive, and state why beside the suppression.
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Enforce Vitest, Playwright, and Testing Library patterns for TypeScript test files
|
|
3
|
+
paths:
|
|
4
|
+
- '**/*.test.ts'
|
|
5
|
+
- '**/*.test.tsx'
|
|
6
|
+
- '**/*.spec.ts'
|
|
7
|
+
- '**/*.spec.tsx'
|
|
8
|
+
---
|
|
9
|
+
|
|
10
|
+
# TypeScript/JavaScript testing tooling
|
|
11
|
+
|
|
12
|
+
## Unit and integration
|
|
13
|
+
|
|
14
|
+
- Use Vitest for unit and integration tests.
|
|
15
|
+
- Co-locate unit tests with their respective components.
|
|
16
|
+
- Use `userEvent` over synthetic events for interaction simulation.
|
|
17
|
+
- Use MSW for network mocking. Do not mock fetch or axios manually.
|
|
18
|
+
- Select elements by accessibility attributes first (`getByRole`, `getByLabelText`).
|
|
19
|
+
|
|
20
|
+
## End-to-end
|
|
21
|
+
|
|
22
|
+
- Use Playwright for end-to-end tests.
|
|
23
|
+
- Place all Playwright tests within the `e2e/` directory.
|
|
24
|
+
- Never place Playwright tests inside `src/`.
|
|
25
|
+
- Scope the three rules above to tests the Playwright runner executes. A Vitest test importing a browser driver to exercise project code stays beside its module, where Vitest looks for it.
|
|
26
|
+
|
|
27
|
+
## Timers and async
|
|
28
|
+
|
|
29
|
+
- Never use `vi.useFakeTimers()` in `beforeEach` when tests use `waitFor`, `act`, or `userEvent`.
|
|
30
|
+
- Scope fake timers to the individual test that needs them.
|
|
31
|
+
- Restore real timers with `vi.useRealTimers()` in a matching `afterEach`.
|
|
32
|
+
|
|
33
|
+
## Conventions
|
|
34
|
+
|
|
35
|
+
- Use `.test.ts` / `.test.tsx` for unit tests.
|
|
36
|
+
- Use `.spec.ts` / `.spec.tsx` for integration tests and for Playwright tests under `e2e/`.
|
|
37
|
+
- Do not make real network calls in unit tests.
|
|
38
|
+
- `describe()` labels use the exact identifier of the subject under test in its natural casing.
|
|
39
|
+
- `it()` descriptions use "should" + sentence case.
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Enforce settled waits and falsifiable guards in end-to-end tests
|
|
3
|
+
paths:
|
|
4
|
+
- 'e2e/*.ts'
|
|
5
|
+
- 'e2e/**/*.ts'
|
|
6
|
+
---
|
|
7
|
+
|
|
8
|
+
# End-to-end reliability standards
|
|
9
|
+
|
|
10
|
+
## Waiting
|
|
11
|
+
|
|
12
|
+
- Settle on the condition a step waits for. Use `expect.poll` or a web-first assertion ahead of any read.
|
|
13
|
+
- Reserve a fixed duration for an assertion that nothing happened across a window.
|
|
14
|
+
- Bound every settle with an explicit timeout.
|
|
15
|
+
- Do not raise a timeout to clear a failure that reproduces under load. Replace the wait with a settle.
|
|
16
|
+
- Do not read a value once after a pause. Poll it.
|
|
17
|
+
|
|
18
|
+
## Falsifiable guards
|
|
19
|
+
|
|
20
|
+
- Assert the set under test is non-empty before asserting a property over its members.
|
|
21
|
+
- Raise from an instrument that was refused rather than returning a value a passing assertion accepts.
|
|
22
|
+
- Run a new guard against the defect it was written for, and see it fail, before trusting it.
|
|
23
|
+
- Do not weaken an assertion to clear a failure. Narrow the wait instead.
|
|
24
|
+
|
|
25
|
+
## Reproducing a failure that only appears in CI
|
|
26
|
+
|
|
27
|
+
- Reproduce under `Emulation.setCPUThrottlingRate` rather than by rerunning the gate.
|
|
28
|
+
- Read the state the assertion does not: which markers were set, which listeners fired, how far a transition ran.
|
|
29
|
+
- Vary the condition under suspicion deliberately. Do not compare counts across runs that differed in something uncontrolled.
|
|
30
|
+
- Read the check conclusion as its own act. A green diff review reports nothing about the gate.
|
|
31
|
+
|
|
32
|
+
## Authority
|
|
33
|
+
|
|
34
|
+
- Follow `.claude/rules/lib/300-testing-ts.md` for framework choice, file placement, and test naming.
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Enforce which specs and which engines an end-to-end run covers at each point in the loop
|
|
3
|
+
paths:
|
|
4
|
+
- 'e2e/*.ts'
|
|
5
|
+
- 'e2e/**/*.ts'
|
|
6
|
+
---
|
|
7
|
+
|
|
8
|
+
# Test scope standards
|
|
9
|
+
|
|
10
|
+
## Selecting a run
|
|
11
|
+
|
|
12
|
+
- Narrow an end-to-end run by spec path or by test name. Never narrow it by engine.
|
|
13
|
+
- Run one named test while iterating on a behavior: `bun run test:e2e -- -g '<name>'`.
|
|
14
|
+
- Run one surface while iterating on that surface: `bun run test:e2e -- e2e/<area>.spec.ts`.
|
|
15
|
+
- Run `bun run test:e2e:changed` to select specs from the import graph.
|
|
16
|
+
- Run the whole suite before pushing.
|
|
17
|
+
- Pass `--project` in a local run only to reproduce a failure that engine has already reported. The CI matrix passes it on every job, one engine per leg, which is the gate rather than a narrowed run.
|
|
18
|
+
- Do not add a script that pins a default run to one engine.
|
|
19
|
+
|
|
20
|
+
## Instruments
|
|
21
|
+
|
|
22
|
+
- Answer a question about the running page with a script against the dev server rather than with the suite.
|
|
23
|
+
- Do not enable `fullyParallel` in `playwright.config.ts`.
|
|
24
|
+
- Follow `.claude/rules/ui/440-surface-capture.md` for capture scope.
|
|
25
|
+
- Follow `.claude/rules/lib/305-e2e-reliability.md` for waits and guards.
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Enforce zod schema validation and type inference
|
|
3
|
+
paths:
|
|
4
|
+
- '**/*.ts'
|
|
5
|
+
- '**/*.tsx'
|
|
6
|
+
---
|
|
7
|
+
|
|
8
|
+
# Zod validation standards
|
|
9
|
+
|
|
10
|
+
## Type inference
|
|
11
|
+
|
|
12
|
+
- Use `z.infer<typeof Schema>` to generate TypeScript types (Single Source of Truth).
|
|
13
|
+
- Do not manually declare interfaces that duplicate Zod schemas.
|
|
14
|
+
- Do not export the runtime Schema if only the inferred Type is required by consumers.
|
|
15
|
+
|
|
16
|
+
## Boundary validation
|
|
17
|
+
|
|
18
|
+
- Use `.strict()` for untrusted external API boundaries to prevent data pollution.
|
|
19
|
+
- Use `.parse()` for blocking validation (env vars) and `.safeParse()` for recoverable flows (forms).
|
|
20
|
+
- Restrict `z.coerce` to I/O boundaries (e.g., URL params). Never use it for internal data flow.
|
|
21
|
+
|
|
22
|
+
## Schema safety
|
|
23
|
+
|
|
24
|
+
- Use `z.unknown()` for truly ambiguous inputs instead of `z.any()`.
|
|
25
|
+
- Prefer `.strict()` at boundaries or explicit `.pick()`/`.omit()` over `.passthrough()`.
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Enforce tanstack query data fetching and cache patterns
|
|
3
|
+
paths:
|
|
4
|
+
- '**/*.ts'
|
|
5
|
+
- '**/*.tsx'
|
|
6
|
+
---
|
|
7
|
+
|
|
8
|
+
# TanStack Query standards
|
|
9
|
+
|
|
10
|
+
## Query conventions
|
|
11
|
+
|
|
12
|
+
- Define query keys as `readonly` tuple constants.
|
|
13
|
+
- Co-locate query keys with their query functions.
|
|
14
|
+
- Encapsulate each query in a custom `use*Query` hook over calling `useQuery` inline in components.
|
|
15
|
+
- Set explicit `staleTime` per query based on data volatility over relying on the default.
|
|
16
|
+
|
|
17
|
+
## Mutations
|
|
18
|
+
|
|
19
|
+
- Use `useMutation` for all write operations.
|
|
20
|
+
- Never mutate data outside the mutation lifecycle.
|
|
21
|
+
- Invalidate related query keys in `onSuccess` over manual cache updates unless optimistic UI is required.
|
|
22
|
+
- Handle `onError` at the mutation site with user-facing feedback.
|
|
23
|
+
|
|
24
|
+
## Cache management
|
|
25
|
+
|
|
26
|
+
- Use `queryClient.invalidateQueries` over `queryClient.setQueryData` unless implementing optimistic updates.
|
|
27
|
+
- Prefetch predictable navigations with `queryClient.prefetchQuery` at route boundaries.
|
|
28
|
+
|
|
29
|
+
## Separation of concerns
|
|
30
|
+
|
|
31
|
+
- Keep query functions as pure async data fetchers with no UI logic or side effects.
|
|
32
|
+
- Use the query `enabled` option for conditional fetching over `useEffect`.
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Enforce pytest fixtures, parametrize, and async patterns for Python tests
|
|
3
|
+
paths:
|
|
4
|
+
- 'tests/**/*.py'
|
|
5
|
+
- '**/test_*.py'
|
|
6
|
+
- '**/*_test.py'
|
|
7
|
+
---
|
|
8
|
+
|
|
9
|
+
# Python testing tooling
|
|
10
|
+
|
|
11
|
+
## Framework
|
|
12
|
+
|
|
13
|
+
- Use `pytest` for all tests. Do not use `unittest.TestCase`.
|
|
14
|
+
- Place tests under `tests/`, mirroring the `src/` package layout.
|
|
15
|
+
- Name files `test_*.py` and test functions `test_*`.
|
|
16
|
+
|
|
17
|
+
## Fixtures
|
|
18
|
+
|
|
19
|
+
- Use `@pytest.fixture` over setup and teardown methods.
|
|
20
|
+
- Place shared fixtures in `conftest.py` at the narrowest scope that needs them.
|
|
21
|
+
- Set `scope=` (`"session"`, `"module"`, `"function"`) explicitly when reuse matters.
|
|
22
|
+
- Use `tmp_path` and `monkeypatch` over hand-rolled temp directories or env stashes.
|
|
23
|
+
|
|
24
|
+
## Parametrize
|
|
25
|
+
|
|
26
|
+
- Use `@pytest.mark.parametrize` for table-driven cases over per-case test functions.
|
|
27
|
+
- Use `ids=` to label parametrized cases when their repr is unclear.
|
|
28
|
+
|
|
29
|
+
## Async
|
|
30
|
+
|
|
31
|
+
- Mark async tests with `@pytest.mark.asyncio` or configure `asyncio_mode = "auto"`.
|
|
32
|
+
- Do not start a fresh event loop inside tests.
|
|
33
|
+
|
|
34
|
+
## Assertions and mocks
|
|
35
|
+
|
|
36
|
+
- Use plain `assert` over `self.assertEqual`. Pytest rewrites assertions for readable diffs.
|
|
37
|
+
- Use `pytest.raises(...)` over `try/except` for expected exceptions.
|
|
38
|
+
- Use `monkeypatch.setattr` or `unittest.mock.patch` over ad hoc module rewrites.
|
|
39
|
+
- Do not make real network calls. Use `responses`, `httpx_mock`, or fakes.
|
|
40
|
+
|
|
41
|
+
## Conventions
|
|
42
|
+
|
|
43
|
+
- Arrange, act, assert per test, with one logical assertion group.
|
|
44
|
+
- Use descriptive `test_*` names that read as the assertion. Do not prefix with `should_`.
|