bmad-elsabro 1.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/.auto-claude-security.json +209 -0
- package/.claude_settings.json +34 -0
- package/.coderabbit.yaml +40 -0
- package/.nvmrc +1 -0
- package/.prettierignore +9 -0
- package/AI_TEST_GENERATOR_VERIFICATION.md +260 -0
- package/BUDGET_ALERT_TESTING.md +325 -0
- package/CHANGELOG.md +1488 -0
- package/CNAME +1 -0
- package/CONTRIBUTING.md +167 -0
- package/CONTRIBUTORS.md +32 -0
- package/LEGACY_MIGRATION_TESTING.md +428 -0
- package/LICENSE +30 -0
- package/PARTY_MODE_VERIFICATION.md +274 -0
- package/PROJECT_DETECTOR_TESTING.md +288 -0
- package/README.md +236 -0
- package/SECURITY.md +85 -0
- package/TRADEMARK.md +55 -0
- package/WORKFLOW_ROUTER_IMPLEMENTATION.md +379 -0
- package/Wordmark.png +0 -0
- package/banner-bmad-method.png +0 -0
- package/build/icons/512x512.png +0 -0
- package/build-mac.sh +3 -0
- package/docs/404.md +9 -0
- package/docs/_STYLE_GUIDE.md +367 -0
- package/docs/developer/api-reference.md +945 -0
- package/docs/developer/architecture.md +563 -0
- package/docs/developer/contributing.md +831 -0
- package/docs/downloads.md +74 -0
- package/docs/explanation/advanced-elicitation.md +24 -0
- package/docs/explanation/adversarial-review.md +57 -0
- package/docs/explanation/brainstorming.md +31 -0
- package/docs/explanation/brownfield-faq.md +55 -0
- package/docs/explanation/party-mode.md +57 -0
- package/docs/explanation/preventing-agent-conflicts.md +110 -0
- package/docs/explanation/quick-flow.md +27 -0
- package/docs/explanation/why-solutioning-matters.md +75 -0
- package/docs/how-to/brownfield/index.md +84 -0
- package/docs/how-to/brownfield/quick-fix-in-brownfield.md +76 -0
- package/docs/how-to/customize-bmad.md +158 -0
- package/docs/how-to/get-answers-about-bmad.md +102 -0
- package/docs/how-to/install-bmad.md +82 -0
- package/docs/how-to/shard-large-documents.md +101 -0
- package/docs/how-to/upgrade-to-v6.md +131 -0
- package/docs/index.md +56 -0
- package/docs/reference/workflow-map.md +83 -0
- package/docs/tea/explanation/engagement-models.md +710 -0
- package/docs/tea/explanation/fixture-architecture.md +457 -0
- package/docs/tea/explanation/knowledge-base-system.md +554 -0
- package/docs/tea/explanation/network-first-patterns.md +853 -0
- package/docs/tea/explanation/risk-based-testing.md +586 -0
- package/docs/tea/explanation/tea-overview.md +410 -0
- package/docs/tea/explanation/test-quality-standards.md +907 -0
- package/docs/tea/explanation/testing-as-engineering.md +112 -0
- package/docs/tea/glossary/index.md +159 -0
- package/docs/tea/how-to/brownfield/use-tea-for-enterprise.md +525 -0
- package/docs/tea/how-to/brownfield/use-tea-with-existing-tests.md +577 -0
- package/docs/tea/how-to/customization/enable-tea-mcp-enhancements.md +424 -0
- package/docs/tea/how-to/customization/integrate-playwright-utils.md +813 -0
- package/docs/tea/how-to/workflows/run-atdd.md +436 -0
- package/docs/tea/how-to/workflows/run-automate.md +653 -0
- package/docs/tea/how-to/workflows/run-nfr-assess.md +679 -0
- package/docs/tea/how-to/workflows/run-test-design.md +135 -0
- package/docs/tea/how-to/workflows/run-test-review.md +605 -0
- package/docs/tea/how-to/workflows/run-trace.md +883 -0
- package/docs/tea/how-to/workflows/setup-ci.md +712 -0
- package/docs/tea/how-to/workflows/setup-test-framework.md +98 -0
- package/docs/tea/reference/commands.md +276 -0
- package/docs/tea/reference/configuration.md +678 -0
- package/docs/tea/reference/knowledge-base.md +340 -0
- package/docs/tea/tutorials/tea-lite-quickstart.md +444 -0
- package/docs/tutorials/getting-started.md +205 -0
- package/docs/user-guide/getting-started.md +348 -0
- package/docs/user-guide/token-economy.md +601 -0
- package/docs/user-guide/workflows.md +546 -0
- package/electron-builder.yml +75 -0
- package/eslint.config.mjs +152 -0
- package/package.json +162 -0
- package/prettier.config.mjs +32 -0
- package/public/monaco-workers/index.js +21 -0
- package/renderer/App.tsx +311 -0
- package/renderer/components/ChatPanel.tsx +285 -0
- package/renderer/components/CodeEditor.tsx +327 -0
- package/renderer/components/CodeEditor.types.ts +245 -0
- package/renderer/components/FlowSelector.tsx +534 -0
- package/renderer/components/MessageInput.tsx +252 -0
- package/renderer/components/MessageList.tsx +204 -0
- package/renderer/components/MigrationWizard.tsx +896 -0
- package/renderer/components/NotificationCenter.tsx +291 -0
- package/renderer/components/OnboardingWizard.tsx +112 -0
- package/renderer/components/PartyMode.tsx +555 -0
- package/renderer/components/Sidebar.module.css +258 -0
- package/renderer/components/Sidebar.tsx +157 -0
- package/renderer/components/TemplateSelector.tsx +553 -0
- package/renderer/components/Terminal.tsx +523 -0
- package/renderer/components/TestCenter.tsx +364 -0
- package/renderer/components/TokenAnalytics.tsx +607 -0
- package/renderer/components/TokenMonitor.tsx +331 -0
- package/renderer/components/TutorialOverlay.tsx +483 -0
- package/renderer/components/WorkflowEditor.tsx +470 -0
- package/renderer/components/onboarding/Step1Welcome.tsx +72 -0
- package/renderer/components/onboarding/Step2Setup.tsx +193 -0
- package/renderer/components/onboarding/Step3CreateProject.tsx +209 -0
- package/renderer/components/test-center/CoverageDashboard.tsx +588 -0
- package/renderer/components/test-center/ELI5Guide.tsx +521 -0
- package/renderer/components/test-center/TestList.tsx +381 -0
- package/renderer/components/test-center/TestRunner.tsx +431 -0
- package/renderer/components/test-center/TestStepWizard.tsx +1000 -0
- package/renderer/components/test-center/VisualTestBuilder.tsx +460 -0
- package/renderer/components/workflow/DependencyEdge.tsx +200 -0
- package/renderer/components/workflow/StepNode.tsx +234 -0
- package/renderer/components/workflow/StepPalette.tsx +412 -0
- package/renderer/context/ThemeContext.tsx +97 -0
- package/renderer/data/shortcuts.json +94 -0
- package/renderer/data/testing-guides.json +261 -0
- package/renderer/data/tutorials.json +546 -0
- package/renderer/hooks/useKeyboardShortcuts.ts +249 -0
- package/renderer/hooks/useNotifications.ts +267 -0
- package/renderer/hooks/useTheme.ts +149 -0
- package/renderer/hooks/useTokenTracking.ts +464 -0
- package/renderer/hooks/useWorkflowState.ts +309 -0
- package/renderer/index.html +16 -0
- package/renderer/index.tsx +17 -0
- package/renderer/lib/MONACO_OFFLINE_CONFIG.md +153 -0
- package/renderer/lib/chart-utils.ts +472 -0
- package/renderer/lib/file-system-provider.ts +295 -0
- package/renderer/lib/monaco-loader.ts +247 -0
- package/renderer/renderer/components/NOTIFICATION_SYSTEM.md +192 -0
- package/renderer/styles.css +55 -0
- package/renderer/types/css-modules.d.ts +21 -0
- package/renderer/types/electron.d.ts +316 -0
- package/src/bmm/_module-installer/installer.js +48 -0
- package/src/bmm/agents/analyst.agent.yaml +36 -0
- package/src/bmm/agents/architect.agent.yaml +28 -0
- package/src/bmm/agents/dev.agent.yaml +38 -0
- package/src/bmm/agents/parallel-orchestrator.agent.yaml +50 -0
- package/src/bmm/agents/pm.agent.yaml +46 -0
- package/src/bmm/agents/quick-flow-solo-dev.agent.yaml +32 -0
- package/src/bmm/agents/sm.agent.yaml +36 -0
- package/src/bmm/agents/tea.agent.yaml +63 -0
- package/src/bmm/agents/tech-writer/tech-writer-sidecar/documentation-standards.md +224 -0
- package/src/bmm/agents/tech-writer/tech-writer.agent.yaml +45 -0
- package/src/bmm/agents/ux-designer.agent.yaml +26 -0
- package/src/bmm/agents/yolo-dev.agent.yaml +41 -0
- package/src/bmm/data/auto-testing-config.yaml +84 -0
- package/src/bmm/data/guided-mode-instructions.yaml +112 -0
- package/src/bmm/data/parallelization-config.yaml +136 -0
- package/src/bmm/data/project-context-template.md +26 -0
- package/src/bmm/data/speed-profiles.yaml +127 -0
- package/src/bmm/module-help.csv +32 -0
- package/src/bmm/module.yaml +60 -0
- package/src/bmm/teams/default-party.csv +21 -0
- package/src/bmm/teams/team-fullstack.yaml +12 -0
- package/src/bmm/testarch/knowledge/adr-quality-readiness-checklist.md +350 -0
- package/src/bmm/testarch/knowledge/api-request.md +442 -0
- package/src/bmm/testarch/knowledge/api-testing-patterns.md +843 -0
- package/src/bmm/testarch/knowledge/auth-session.md +552 -0
- package/src/bmm/testarch/knowledge/burn-in.md +273 -0
- package/src/bmm/testarch/knowledge/ci-burn-in.md +675 -0
- package/src/bmm/testarch/knowledge/component-tdd.md +486 -0
- package/src/bmm/testarch/knowledge/contract-testing.md +957 -0
- package/src/bmm/testarch/knowledge/data-factories.md +500 -0
- package/src/bmm/testarch/knowledge/email-auth.md +721 -0
- package/src/bmm/testarch/knowledge/error-handling.md +725 -0
- package/src/bmm/testarch/knowledge/feature-flags.md +750 -0
- package/src/bmm/testarch/knowledge/file-utils.md +463 -0
- package/src/bmm/testarch/knowledge/fixture-architecture.md +401 -0
- package/src/bmm/testarch/knowledge/fixtures-composition.md +382 -0
- package/src/bmm/testarch/knowledge/intercept-network-call.md +430 -0
- package/src/bmm/testarch/knowledge/log.md +429 -0
- package/src/bmm/testarch/knowledge/network-error-monitor.md +405 -0
- package/src/bmm/testarch/knowledge/network-first.md +486 -0
- package/src/bmm/testarch/knowledge/network-recorder.md +527 -0
- package/src/bmm/testarch/knowledge/nfr-criteria.md +670 -0
- package/src/bmm/testarch/knowledge/overview.md +286 -0
- package/src/bmm/testarch/knowledge/playwright-config.md +730 -0
- package/src/bmm/testarch/knowledge/probability-impact.md +601 -0
- package/src/bmm/testarch/knowledge/recurse.md +421 -0
- package/src/bmm/testarch/knowledge/risk-governance.md +615 -0
- package/src/bmm/testarch/knowledge/selective-testing.md +732 -0
- package/src/bmm/testarch/knowledge/selector-resilience.md +527 -0
- package/src/bmm/testarch/knowledge/test-healing-patterns.md +644 -0
- package/src/bmm/testarch/knowledge/test-levels-framework.md +473 -0
- package/src/bmm/testarch/knowledge/test-priorities-matrix.md +373 -0
- package/src/bmm/testarch/knowledge/test-quality.md +664 -0
- package/src/bmm/testarch/knowledge/timing-debugging.md +372 -0
- package/src/bmm/testarch/knowledge/visual-debugging.md +524 -0
- package/src/bmm/testarch/tea-index.csv +35 -0
- package/src/bmm/workflows/1-analysis/create-product-brief/product-brief.template.md +10 -0
- package/src/bmm/workflows/1-analysis/create-product-brief/steps/step-01-init.md +177 -0
- package/src/bmm/workflows/1-analysis/create-product-brief/steps/step-01b-continue.md +161 -0
- package/src/bmm/workflows/1-analysis/create-product-brief/steps/step-02-vision.md +199 -0
- package/src/bmm/workflows/1-analysis/create-product-brief/steps/step-03-users.md +202 -0
- package/src/bmm/workflows/1-analysis/create-product-brief/steps/step-04-metrics.md +205 -0
- package/src/bmm/workflows/1-analysis/create-product-brief/steps/step-05-scope.md +219 -0
- package/src/bmm/workflows/1-analysis/create-product-brief/steps/step-06-complete.md +162 -0
- package/src/bmm/workflows/1-analysis/create-product-brief/workflow.md +58 -0
- package/src/bmm/workflows/1-analysis/research/domain-steps/step-01-init.md +137 -0
- package/src/bmm/workflows/1-analysis/research/domain-steps/step-02-domain-analysis.md +229 -0
- package/src/bmm/workflows/1-analysis/research/domain-steps/step-03-competitive-landscape.md +238 -0
- package/src/bmm/workflows/1-analysis/research/domain-steps/step-04-regulatory-focus.md +206 -0
- package/src/bmm/workflows/1-analysis/research/domain-steps/step-05-technical-trends.md +234 -0
- package/src/bmm/workflows/1-analysis/research/domain-steps/step-06-research-synthesis.md +443 -0
- package/src/bmm/workflows/1-analysis/research/market-steps/step-01-init.md +182 -0
- package/src/bmm/workflows/1-analysis/research/market-steps/step-02-customer-behavior.md +237 -0
- package/src/bmm/workflows/1-analysis/research/market-steps/step-02-customer-insights.md +200 -0
- package/src/bmm/workflows/1-analysis/research/market-steps/step-03-customer-pain-points.md +249 -0
- package/src/bmm/workflows/1-analysis/research/market-steps/step-04-customer-decisions.md +259 -0
- package/src/bmm/workflows/1-analysis/research/market-steps/step-05-competitive-analysis.md +177 -0
- package/src/bmm/workflows/1-analysis/research/market-steps/step-06-research-completion.md +475 -0
- package/src/bmm/workflows/1-analysis/research/research.template.md +29 -0
- package/src/bmm/workflows/1-analysis/research/technical-steps/step-01-init.md +137 -0
- package/src/bmm/workflows/1-analysis/research/technical-steps/step-02-technical-overview.md +239 -0
- package/src/bmm/workflows/1-analysis/research/technical-steps/step-03-integration-patterns.md +248 -0
- package/src/bmm/workflows/1-analysis/research/technical-steps/step-04-architectural-patterns.md +202 -0
- package/src/bmm/workflows/1-analysis/research/technical-steps/step-05-implementation-research.md +239 -0
- package/src/bmm/workflows/1-analysis/research/technical-steps/step-06-research-synthesis.md +486 -0
- package/src/bmm/workflows/1-analysis/research/workflow.md +173 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/data/domain-complexity.csv +13 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/data/prd-purpose.md +197 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/data/project-types.csv +11 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-c/step-01-init.md +191 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-c/step-01b-continue.md +153 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-c/step-02-discovery.md +224 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-c/step-03-success.md +226 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-c/step-04-journeys.md +213 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-c/step-05-domain.md +207 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-c/step-06-innovation.md +226 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-c/step-07-project-type.md +237 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-c/step-08-scoping.md +228 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-c/step-09-functional.md +231 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-c/step-10-nonfunctional.md +242 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-c/step-11-polish.md +217 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-c/step-12-complete.md +124 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-e/step-e-01-discovery.md +247 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-e/step-e-01b-legacy-conversion.md +208 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-e/step-e-02-review.md +249 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-e/step-e-03-edit.md +253 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-e/step-e-04-complete.md +168 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-v/step-v-01-discovery.md +218 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-v/step-v-02-format-detection.md +191 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-v/step-v-02b-parity-check.md +209 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-v/step-v-03-density-validation.md +174 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-v/step-v-04-brief-coverage-validation.md +214 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-v/step-v-05-measurability-validation.md +228 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-v/step-v-06-traceability-validation.md +217 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-v/step-v-07-implementation-leakage-validation.md +205 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-v/step-v-08-domain-compliance-validation.md +243 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-v/step-v-09-project-type-validation.md +263 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-v/step-v-10-smart-validation.md +209 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-v/step-v-11-holistic-quality-validation.md +264 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-v/step-v-12-completeness-validation.md +242 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/steps-v/step-v-13-report-complete.md +231 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/templates/prd-template.md +10 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/validation-report-prd-workflow.md +433 -0
- package/src/bmm/workflows/2-plan-workflows/create-prd/workflow.md +150 -0
- package/src/bmm/workflows/2-plan-workflows/create-ux-design/steps/step-01-init.md +135 -0
- package/src/bmm/workflows/2-plan-workflows/create-ux-design/steps/step-01b-continue.md +127 -0
- package/src/bmm/workflows/2-plan-workflows/create-ux-design/steps/step-02-discovery.md +190 -0
- package/src/bmm/workflows/2-plan-workflows/create-ux-design/steps/step-03-core-experience.md +216 -0
- package/src/bmm/workflows/2-plan-workflows/create-ux-design/steps/step-04-emotional-response.md +219 -0
- package/src/bmm/workflows/2-plan-workflows/create-ux-design/steps/step-05-inspiration.md +234 -0
- package/src/bmm/workflows/2-plan-workflows/create-ux-design/steps/step-06-design-system.md +252 -0
- package/src/bmm/workflows/2-plan-workflows/create-ux-design/steps/step-07-defining-experience.md +254 -0
- package/src/bmm/workflows/2-plan-workflows/create-ux-design/steps/step-08-visual-foundation.md +224 -0
- package/src/bmm/workflows/2-plan-workflows/create-ux-design/steps/step-09-design-directions.md +224 -0
- package/src/bmm/workflows/2-plan-workflows/create-ux-design/steps/step-10-user-journeys.md +241 -0
- package/src/bmm/workflows/2-plan-workflows/create-ux-design/steps/step-11-component-strategy.md +248 -0
- package/src/bmm/workflows/2-plan-workflows/create-ux-design/steps/step-12-ux-patterns.md +237 -0
- package/src/bmm/workflows/2-plan-workflows/create-ux-design/steps/step-13-responsive-accessibility.md +264 -0
- package/src/bmm/workflows/2-plan-workflows/create-ux-design/steps/step-14-complete.md +171 -0
- package/src/bmm/workflows/2-plan-workflows/create-ux-design/ux-design-template.md +13 -0
- package/src/bmm/workflows/2-plan-workflows/create-ux-design/workflow.md +43 -0
- package/src/bmm/workflows/3-solutioning/check-implementation-readiness/steps/step-01-document-discovery.md +190 -0
- package/src/bmm/workflows/3-solutioning/check-implementation-readiness/steps/step-02-prd-analysis.md +178 -0
- package/src/bmm/workflows/3-solutioning/check-implementation-readiness/steps/step-03-epic-coverage-validation.md +179 -0
- package/src/bmm/workflows/3-solutioning/check-implementation-readiness/steps/step-04-ux-alignment.md +139 -0
- package/src/bmm/workflows/3-solutioning/check-implementation-readiness/steps/step-05-epic-quality-review.md +252 -0
- package/src/bmm/workflows/3-solutioning/check-implementation-readiness/steps/step-06-final-assessment.md +135 -0
- package/src/bmm/workflows/3-solutioning/check-implementation-readiness/templates/readiness-report-template.md +4 -0
- package/src/bmm/workflows/3-solutioning/check-implementation-readiness/workflow.md +55 -0
- package/src/bmm/workflows/3-solutioning/create-architecture/architecture-decision-template.md +12 -0
- package/src/bmm/workflows/3-solutioning/create-architecture/data/domain-complexity.csv +11 -0
- package/src/bmm/workflows/3-solutioning/create-architecture/data/project-types.csv +7 -0
- package/src/bmm/workflows/3-solutioning/create-architecture/steps/step-01-init.md +153 -0
- package/src/bmm/workflows/3-solutioning/create-architecture/steps/step-01b-continue.md +164 -0
- package/src/bmm/workflows/3-solutioning/create-architecture/steps/step-02-context.md +224 -0
- package/src/bmm/workflows/3-solutioning/create-architecture/steps/step-03-starter.md +331 -0
- package/src/bmm/workflows/3-solutioning/create-architecture/steps/step-04-decisions.md +318 -0
- package/src/bmm/workflows/3-solutioning/create-architecture/steps/step-05-patterns.md +359 -0
- package/src/bmm/workflows/3-solutioning/create-architecture/steps/step-06-structure.md +379 -0
- package/src/bmm/workflows/3-solutioning/create-architecture/steps/step-07-validation.md +359 -0
- package/src/bmm/workflows/3-solutioning/create-architecture/steps/step-08-complete.md +76 -0
- package/src/bmm/workflows/3-solutioning/create-architecture/workflow.md +50 -0
- package/src/bmm/workflows/3-solutioning/create-epics-and-stories/steps/step-01-validate-prerequisites.md +259 -0
- package/src/bmm/workflows/3-solutioning/create-epics-and-stories/steps/step-02-design-epics.md +233 -0
- package/src/bmm/workflows/3-solutioning/create-epics-and-stories/steps/step-03-create-stories.md +272 -0
- package/src/bmm/workflows/3-solutioning/create-epics-and-stories/steps/step-04-final-validation.md +149 -0
- package/src/bmm/workflows/3-solutioning/create-epics-and-stories/templates/epics-template.md +57 -0
- package/src/bmm/workflows/3-solutioning/create-epics-and-stories/workflow.md +59 -0
- package/src/bmm/workflows/4-implementation/code-review/checklist.md +23 -0
- package/src/bmm/workflows/4-implementation/code-review/instructions.xml +227 -0
- package/src/bmm/workflows/4-implementation/code-review/workflow.yaml +51 -0
- package/src/bmm/workflows/4-implementation/correct-course/checklist.md +288 -0
- package/src/bmm/workflows/4-implementation/correct-course/instructions.md +206 -0
- package/src/bmm/workflows/4-implementation/correct-course/workflow.yaml +60 -0
- package/src/bmm/workflows/4-implementation/create-story/checklist.md +358 -0
- package/src/bmm/workflows/4-implementation/create-story/instructions.xml +345 -0
- package/src/bmm/workflows/4-implementation/create-story/template.md +49 -0
- package/src/bmm/workflows/4-implementation/create-story/workflow.yaml +61 -0
- package/src/bmm/workflows/4-implementation/dev-story/checklist.md +80 -0
- package/src/bmm/workflows/4-implementation/dev-story/instructions.xml +410 -0
- package/src/bmm/workflows/4-implementation/dev-story/workflow.yaml +32 -0
- package/src/bmm/workflows/4-implementation/fix-and-test/workflow.md +197 -0
- package/src/bmm/workflows/4-implementation/retrospective/instructions.md +1443 -0
- package/src/bmm/workflows/4-implementation/retrospective/workflow.yaml +58 -0
- package/src/bmm/workflows/4-implementation/sprint-planning/checklist.md +33 -0
- package/src/bmm/workflows/4-implementation/sprint-planning/instructions.md +225 -0
- package/src/bmm/workflows/4-implementation/sprint-planning/sprint-status-template.yaml +55 -0
- package/src/bmm/workflows/4-implementation/sprint-planning/workflow.yaml +54 -0
- package/src/bmm/workflows/4-implementation/sprint-status/instructions.md +229 -0
- package/src/bmm/workflows/4-implementation/sprint-status/workflow.yaml +36 -0
- package/src/bmm/workflows/bmad-quick-flow/brownfield-fast-track/steps/step-01-detect.md +55 -0
- package/src/bmm/workflows/bmad-quick-flow/brownfield-fast-track/steps/step-02-confirm.md +48 -0
- package/src/bmm/workflows/bmad-quick-flow/brownfield-fast-track/steps/step-03-implement.md +61 -0
- package/src/bmm/workflows/bmad-quick-flow/brownfield-fast-track/workflow.md +41 -0
- package/src/bmm/workflows/bmad-quick-flow/quick-dev/steps/step-01-mode-detection.md +176 -0
- package/src/bmm/workflows/bmad-quick-flow/quick-dev/steps/step-02-context-gathering.md +120 -0
- package/src/bmm/workflows/bmad-quick-flow/quick-dev/steps/step-03-execute.md +153 -0
- package/src/bmm/workflows/bmad-quick-flow/quick-dev/steps/step-04-self-check.md +113 -0
- package/src/bmm/workflows/bmad-quick-flow/quick-dev/steps/step-05-adversarial-review.md +106 -0
- package/src/bmm/workflows/bmad-quick-flow/quick-dev/steps/step-06-resolve-findings.md +149 -0
- package/src/bmm/workflows/bmad-quick-flow/quick-dev/workflow.md +73 -0
- package/src/bmm/workflows/bmad-quick-flow/quick-spec/steps/step-01-understand.md +192 -0
- package/src/bmm/workflows/bmad-quick-flow/quick-spec/steps/step-02-investigate.md +145 -0
- package/src/bmm/workflows/bmad-quick-flow/quick-spec/steps/step-03-generate.md +128 -0
- package/src/bmm/workflows/bmad-quick-flow/quick-spec/steps/step-04-review.md +201 -0
- package/src/bmm/workflows/bmad-quick-flow/quick-spec/tech-spec-template.md +74 -0
- package/src/bmm/workflows/bmad-quick-flow/quick-spec/workflow.md +93 -0
- package/src/bmm/workflows/bmad-quick-flow/yolo-mode/steps/step-01-rapid-spec.md +54 -0
- package/src/bmm/workflows/bmad-quick-flow/yolo-mode/steps/step-02-ship-it.md +65 -0
- package/src/bmm/workflows/bmad-quick-flow/yolo-mode/workflow.md +54 -0
- package/src/bmm/workflows/document-project/checklist.md +245 -0
- package/src/bmm/workflows/document-project/documentation-requirements.csv +12 -0
- package/src/bmm/workflows/document-project/instructions.md +221 -0
- package/src/bmm/workflows/document-project/templates/deep-dive-template.md +345 -0
- package/src/bmm/workflows/document-project/templates/index-template.md +169 -0
- package/src/bmm/workflows/document-project/templates/project-overview-template.md +103 -0
- package/src/bmm/workflows/document-project/templates/project-scan-report-schema.json +160 -0
- package/src/bmm/workflows/document-project/templates/source-tree-template.md +135 -0
- package/src/bmm/workflows/document-project/workflow.yaml +30 -0
- package/src/bmm/workflows/document-project/workflows/deep-dive-instructions.md +298 -0
- package/src/bmm/workflows/document-project/workflows/deep-dive.yaml +31 -0
- package/src/bmm/workflows/document-project/workflows/full-scan-instructions.md +1106 -0
- package/src/bmm/workflows/document-project/workflows/full-scan.yaml +31 -0
- package/src/bmm/workflows/excalidraw-diagrams/_shared/excalidraw-library.json +90 -0
- package/src/bmm/workflows/excalidraw-diagrams/_shared/excalidraw-templates.yaml +127 -0
- package/src/bmm/workflows/excalidraw-diagrams/create-dataflow/checklist.md +39 -0
- package/src/bmm/workflows/excalidraw-diagrams/create-dataflow/instructions.md +130 -0
- package/src/bmm/workflows/excalidraw-diagrams/create-dataflow/workflow.yaml +27 -0
- package/src/bmm/workflows/excalidraw-diagrams/create-diagram/checklist.md +43 -0
- package/src/bmm/workflows/excalidraw-diagrams/create-diagram/instructions.md +141 -0
- package/src/bmm/workflows/excalidraw-diagrams/create-diagram/workflow.yaml +27 -0
- package/src/bmm/workflows/excalidraw-diagrams/create-flowchart/checklist.md +49 -0
- package/src/bmm/workflows/excalidraw-diagrams/create-flowchart/instructions.md +241 -0
- package/src/bmm/workflows/excalidraw-diagrams/create-flowchart/workflow.yaml +27 -0
- package/src/bmm/workflows/excalidraw-diagrams/create-wireframe/checklist.md +38 -0
- package/src/bmm/workflows/excalidraw-diagrams/create-wireframe/instructions.md +133 -0
- package/src/bmm/workflows/excalidraw-diagrams/create-wireframe/workflow.yaml +27 -0
- package/src/bmm/workflows/parallel-work/parallel-analysis/steps/step-01-parse-target.md +49 -0
- package/src/bmm/workflows/parallel-work/parallel-analysis/steps/step-02-launch-streams.md +135 -0
- package/src/bmm/workflows/parallel-work/parallel-analysis/steps/step-03-sync-point.md +74 -0
- package/src/bmm/workflows/parallel-work/parallel-analysis/steps/step-04-merge-insights.md +179 -0
- package/src/bmm/workflows/parallel-work/parallel-analysis/workflow.md +55 -0
- package/src/bmm/workflows/parallel-work/parallel-generation/workflow.md +109 -0
- package/src/bmm/workflows/parallel-work/parallel-reviews/workflow.md +111 -0
- package/src/bmm/workflows/parallel-work/parallel-stories/workflow.md +112 -0
- package/src/bmm/workflows/parallel-work/sprint-mode/steps/step-01-load-sprint.md +54 -0
- package/src/bmm/workflows/parallel-work/sprint-mode/steps/step-02-plan-execution.md +63 -0
- package/src/bmm/workflows/parallel-work/sprint-mode/steps/step-03-execute-stories.md +112 -0
- package/src/bmm/workflows/parallel-work/sprint-mode/steps/step-04-code-review.md +148 -0
- package/src/bmm/workflows/parallel-work/sprint-mode/steps/step-05-integration-testing.md +200 -0
- package/src/bmm/workflows/parallel-work/sprint-mode/steps/step-06-sprint-report.md +290 -0
- package/src/bmm/workflows/parallel-work/sprint-mode/workflow.md +58 -0
- package/src/bmm/workflows/testarch/atdd/atdd-checklist-template.md +363 -0
- package/src/bmm/workflows/testarch/atdd/checklist.md +374 -0
- package/src/bmm/workflows/testarch/atdd/instructions.md +806 -0
- package/src/bmm/workflows/testarch/atdd/workflow.yaml +47 -0
- package/src/bmm/workflows/testarch/automate/checklist.md +582 -0
- package/src/bmm/workflows/testarch/automate/instructions.md +1324 -0
- package/src/bmm/workflows/testarch/automate/workflow.yaml +54 -0
- package/src/bmm/workflows/testarch/ci/checklist.md +247 -0
- package/src/bmm/workflows/testarch/ci/github-actions-template.yaml +198 -0
- package/src/bmm/workflows/testarch/ci/gitlab-ci-template.yaml +149 -0
- package/src/bmm/workflows/testarch/ci/instructions.md +536 -0
- package/src/bmm/workflows/testarch/ci/workflow.yaml +47 -0
- package/src/bmm/workflows/testarch/framework/checklist.md +320 -0
- package/src/bmm/workflows/testarch/framework/instructions.md +481 -0
- package/src/bmm/workflows/testarch/framework/workflow.yaml +49 -0
- package/src/bmm/workflows/testarch/nfr-assess/checklist.md +407 -0
- package/src/bmm/workflows/testarch/nfr-assess/instructions.md +726 -0
- package/src/bmm/workflows/testarch/nfr-assess/nfr-report-template.md +461 -0
- package/src/bmm/workflows/testarch/nfr-assess/workflow.yaml +49 -0
- package/src/bmm/workflows/testarch/test-design/checklist.md +407 -0
- package/src/bmm/workflows/testarch/test-design/instructions.md +1158 -0
- package/src/bmm/workflows/testarch/test-design/test-design-architecture-template.md +213 -0
- package/src/bmm/workflows/testarch/test-design/test-design-qa-template.md +286 -0
- package/src/bmm/workflows/testarch/test-design/test-design-template.md +294 -0
- package/src/bmm/workflows/testarch/test-design/workflow.yaml +71 -0
- package/src/bmm/workflows/testarch/test-review/checklist.md +472 -0
- package/src/bmm/workflows/testarch/test-review/instructions.md +628 -0
- package/src/bmm/workflows/testarch/test-review/test-review-template.md +390 -0
- package/src/bmm/workflows/testarch/test-review/workflow.yaml +48 -0
- package/src/bmm/workflows/testarch/trace/checklist.md +642 -0
- package/src/bmm/workflows/testarch/trace/instructions.md +1030 -0
- package/src/bmm/workflows/testarch/trace/trace-template.md +675 -0
- package/src/bmm/workflows/testarch/trace/workflow.yaml +57 -0
- package/src/core/_module-installer/installer.js +60 -0
- package/src/core/agents/bmad-master.agent.yaml +29 -0
- package/src/core/module-help.csv +9 -0
- package/src/core/module.yaml +25 -0
- package/src/core/resources/excalidraw/README.md +160 -0
- package/src/core/resources/excalidraw/excalidraw-helpers.md +127 -0
- package/src/core/resources/excalidraw/library-loader.md +50 -0
- package/src/core/resources/excalidraw/validate-json-instructions.md +79 -0
- package/src/core/tasks/editorial-review-prose.xml +100 -0
- package/src/core/tasks/editorial-review-structure.xml +209 -0
- package/src/core/tasks/help.md +62 -0
- package/src/core/tasks/index-docs.xml +65 -0
- package/src/core/tasks/review-adversarial-general.xml +48 -0
- package/src/core/tasks/shard-doc.xml +109 -0
- package/src/core/tasks/workflow.xml +235 -0
- package/src/core/workflows/advanced-elicitation/methods.csv +51 -0
- package/src/core/workflows/advanced-elicitation/workflow.xml +117 -0
- package/src/core/workflows/brainstorming/brain-methods.csv +62 -0
- package/src/core/workflows/brainstorming/steps/step-01-session-setup.md +197 -0
- package/src/core/workflows/brainstorming/steps/step-01b-continue.md +122 -0
- package/src/core/workflows/brainstorming/steps/step-02a-user-selected.md +225 -0
- package/src/core/workflows/brainstorming/steps/step-02b-ai-recommended.md +237 -0
- package/src/core/workflows/brainstorming/steps/step-02c-random-selection.md +209 -0
- package/src/core/workflows/brainstorming/steps/step-02d-progressive-flow.md +264 -0
- package/src/core/workflows/brainstorming/steps/step-03-technique-execution.md +399 -0
- package/src/core/workflows/brainstorming/steps/step-04-idea-organization.md +303 -0
- package/src/core/workflows/brainstorming/template.md +15 -0
- package/src/core/workflows/brainstorming/workflow.md +58 -0
- package/src/core/workflows/party-mode/steps/step-01-agent-loading.md +138 -0
- package/src/core/workflows/party-mode/steps/step-02-discussion-orchestration.md +187 -0
- package/src/core/workflows/party-mode/steps/step-03-graceful-exit.md +157 -0
- package/src/core/workflows/party-mode/workflow.md +194 -0
- package/src/utility/agent-components/activation-rules.txt +6 -0
- package/src/utility/agent-components/activation-steps.txt +14 -0
- package/src/utility/agent-components/agent-command-header.md +1 -0
- package/src/utility/agent-components/agent.customize.template.yaml +41 -0
- package/src/utility/agent-components/handler-action.txt +4 -0
- package/src/utility/agent-components/handler-data.txt +5 -0
- package/src/utility/agent-components/handler-exec.txt +6 -0
- package/src/utility/agent-components/handler-multi.txt +14 -0
- package/src/utility/agent-components/handler-tmpl.txt +5 -0
- package/src/utility/agent-components/handler-validate-workflow.txt +7 -0
- package/src/utility/agent-components/handler-workflow.txt +10 -0
- package/src/utility/agent-components/menu-handlers.txt +6 -0
- package/tools/bmad-npx-wrapper.js +69 -0
- package/tools/build-docs.js +577 -0
- package/tools/cli/README.md +7 -0
- package/tools/cli/bmad-cli.js +65 -0
- package/tools/cli/commands/diagnostics.js +303 -0
- package/tools/cli/commands/install.js +87 -0
- package/tools/cli/commands/module.js +210 -0
- package/tools/cli/commands/status.js +65 -0
- package/tools/cli/commands/uninstall.js +86 -0
- package/tools/cli/external-official-modules.yaml +54 -0
- package/tools/cli/installers/install-messages.yaml +59 -0
- package/tools/cli/installers/lib/core/config-collector.js +1079 -0
- package/tools/cli/installers/lib/core/custom-module-cache.js +259 -0
- package/tools/cli/installers/lib/core/dependency-resolver.js +739 -0
- package/tools/cli/installers/lib/core/detector.js +223 -0
- package/tools/cli/installers/lib/core/ide-config-manager.js +156 -0
- package/tools/cli/installers/lib/core/installer.js +2812 -0
- package/tools/cli/installers/lib/core/manifest-generator.js +1054 -0
- package/tools/cli/installers/lib/core/manifest.js +1036 -0
- package/tools/cli/installers/lib/custom/handler.js +363 -0
- package/tools/cli/installers/lib/ide/_base-ide.js +655 -0
- package/tools/cli/installers/lib/ide/_config-driven.js +450 -0
- package/tools/cli/installers/lib/ide/codex.js +440 -0
- package/tools/cli/installers/lib/ide/kilo.js +250 -0
- package/tools/cli/installers/lib/ide/kiro-cli.js +326 -0
- package/tools/cli/installers/lib/ide/manager.js +271 -0
- package/tools/cli/installers/lib/ide/platform-codes.js +100 -0
- package/tools/cli/installers/lib/ide/platform-codes.yaml +227 -0
- package/tools/cli/installers/lib/ide/shared/agent-command-generator.js +181 -0
- package/tools/cli/installers/lib/ide/shared/bmad-artifacts.js +163 -0
- package/tools/cli/installers/lib/ide/shared/module-injections.js +136 -0
- package/tools/cli/installers/lib/ide/shared/path-utils.js +292 -0
- package/tools/cli/installers/lib/ide/shared/task-tool-command-generator.js +270 -0
- package/tools/cli/installers/lib/ide/shared/workflow-command-generator.js +319 -0
- package/tools/cli/installers/lib/ide/templates/agent-command-template.md +14 -0
- package/tools/cli/installers/lib/ide/templates/combined/antigravity.md +8 -0
- package/tools/cli/installers/lib/ide/templates/combined/default-agent.md +15 -0
- package/tools/cli/installers/lib/ide/templates/combined/default-workflow-yaml.md +14 -0
- package/tools/cli/installers/lib/ide/templates/combined/default-workflow.md +6 -0
- package/tools/cli/installers/lib/ide/templates/combined/gemini-agent.toml +14 -0
- package/tools/cli/installers/lib/ide/templates/combined/gemini-workflow-yaml.toml +16 -0
- package/tools/cli/installers/lib/ide/templates/combined/gemini-workflow.toml +14 -0
- package/tools/cli/installers/lib/ide/templates/combined/rovodev.md +9 -0
- package/tools/cli/installers/lib/ide/templates/combined/trae.md +9 -0
- package/tools/cli/installers/lib/ide/templates/combined/windsurf-workflow.md +10 -0
- package/tools/cli/installers/lib/ide/templates/split/opencode/body.md +10 -0
- package/tools/cli/installers/lib/ide/templates/split/opencode/header.md +4 -0
- package/tools/cli/installers/lib/ide/templates/workflow-command-template.md +13 -0
- package/tools/cli/installers/lib/ide/templates/workflow-commander.md +5 -0
- package/tools/cli/installers/lib/message-loader.js +85 -0
- package/tools/cli/installers/lib/modules/external-manager.js +135 -0
- package/tools/cli/installers/lib/modules/manager.js +1375 -0
- package/tools/cli/lib/activation-builder.js +163 -0
- package/tools/cli/lib/agent/compiler.js +522 -0
- package/tools/cli/lib/agent/compiler.ts +572 -0
- package/tools/cli/lib/agent/installer.js +716 -0
- package/tools/cli/lib/agent/template-engine.js +152 -0
- package/tools/cli/lib/agent/types.ts +155 -0
- package/tools/cli/lib/agent-analyzer.js +109 -0
- package/tools/cli/lib/agent-party-generator.js +194 -0
- package/tools/cli/lib/cli-utils.js +227 -0
- package/tools/cli/lib/config.js +213 -0
- package/tools/cli/lib/config.ts +227 -0
- package/tools/cli/lib/file-ops.js +204 -0
- package/tools/cli/lib/file-ops.ts +215 -0
- package/tools/cli/lib/platform-codes.js +116 -0
- package/tools/cli/lib/project-root.js +77 -0
- package/tools/cli/lib/prompts.js +433 -0
- package/tools/cli/lib/prompts.ts +541 -0
- package/tools/cli/lib/types/config.types.ts +43 -0
- package/tools/cli/lib/types/xml-handler.types.ts +50 -0
- package/tools/cli/lib/ui.js +1660 -0
- package/tools/cli/lib/xml-handler.js +177 -0
- package/tools/cli/lib/xml-handler.ts +188 -0
- package/tools/cli/lib/xml-to-markdown.js +82 -0
- package/tools/cli/lib/yaml-format.js +245 -0
- package/tools/cli/lib/yaml-xml-builder.js +587 -0
- package/tools/docs/BUNDLE_DISTRIBUTION_SETUP.md +95 -0
- package/tools/docs/fix-refs.md +91 -0
- package/tools/docs/index.md +2 -0
- package/tools/fix-doc-links.js +288 -0
- package/tools/flattener/aggregate.js +76 -0
- package/tools/flattener/aggregate.ts +78 -0
- package/tools/flattener/binary.js +80 -0
- package/tools/flattener/discovery.js +71 -0
- package/tools/flattener/files.js +35 -0
- package/tools/flattener/files.ts +31 -0
- package/tools/flattener/ignoreRules.js +172 -0
- package/tools/flattener/main.js +483 -0
- package/tools/flattener/main.ts +262 -0
- package/tools/flattener/projectRoot.js +201 -0
- package/tools/flattener/prompts.js +44 -0
- package/tools/flattener/stats.helpers.js +368 -0
- package/tools/flattener/stats.js +75 -0
- package/tools/flattener/test-matrix.js +409 -0
- package/tools/flattener/types.ts +53 -0
- package/tools/flattener/xml.js +82 -0
- package/tools/format-workflow-md.js +263 -0
- package/tools/lib/xml-utils.js +13 -0
- package/tools/maintainer/review-pr-README.md +55 -0
- package/tools/maintainer/review-pr.md +242 -0
- package/tools/migrate-custom-module-paths.js +124 -0
- package/tools/platform-codes.yaml +157 -0
- package/tools/schema/agent.js +491 -0
- package/tools/schema/agent.ts +489 -0
- package/tools/schema/agent.types.ts +31 -0
- package/tools/update-bmad.sh +24 -0
- package/tools/validate-agent-schema.js +110 -0
- package/tools/validate-doc-links.js +371 -0
- package/tools/validate-svg-changes.sh +356 -0
- package/vite-plugin-monaco-editor.ts +108 -0
|
@@ -0,0 +1,489 @@
|
|
|
1
|
+
// Zod schema definition for *.agent.yaml files
|
|
2
|
+
import assert from 'node:assert';
|
|
3
|
+
import { z } from 'zod';
|
|
4
|
+
import type { CompoundTriggerResult, AgentSchemaOptions } from './agent.types';
|
|
5
|
+
|
|
6
|
+
const COMMAND_TARGET_KEYS = ['workflow', 'validate-workflow', 'exec', 'action', 'tmpl', 'data'] as const;
|
|
7
|
+
const TRIGGER_PATTERN = /^[a-z0-9]+(?:-[a-z0-9]+)*$/;
|
|
8
|
+
const COMPOUND_TRIGGER_PATTERN = /^([A-Z]{1,3}) or fuzzy match on ([a-z0-9]+(?:-[a-z0-9]+)*)$/;
|
|
9
|
+
|
|
10
|
+
/**
|
|
11
|
+
* Derive the expected shortcut from a kebab-case trigger.
|
|
12
|
+
* - Single word: first letter (e.g., "help" ā "H")
|
|
13
|
+
* - Multi-word: first letter of first two words (e.g., "tech-spec" ā "TS")
|
|
14
|
+
* @param kebabTrigger The kebab-case trigger name.
|
|
15
|
+
* @returns The expected uppercase shortcut.
|
|
16
|
+
*/
|
|
17
|
+
function deriveShortcutFromKebab(kebabTrigger: string): string {
|
|
18
|
+
const words = kebabTrigger.split('-');
|
|
19
|
+
if (words.length === 1) {
|
|
20
|
+
return words[0][0].toUpperCase();
|
|
21
|
+
}
|
|
22
|
+
return (words[0][0] + words[1][0]).toUpperCase();
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
/**
|
|
26
|
+
* Parse and validate a compound trigger string.
|
|
27
|
+
* Format: "<SHORTCUT> or fuzzy match on <kebab-case>"
|
|
28
|
+
* @param triggerValue The trigger string to parse.
|
|
29
|
+
* @returns Parsed compound trigger result.
|
|
30
|
+
*/
|
|
31
|
+
function parseCompoundTrigger(triggerValue: string): CompoundTriggerResult {
|
|
32
|
+
const match = COMPOUND_TRIGGER_PATTERN.exec(triggerValue);
|
|
33
|
+
if (!match) {
|
|
34
|
+
return { valid: false, error: 'invalid compound trigger format' };
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
const [, shortcut, kebabTrigger] = match;
|
|
38
|
+
|
|
39
|
+
return { valid: true, shortcut, kebabTrigger };
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
// Public API ---------------------------------------------------------------
|
|
43
|
+
|
|
44
|
+
/**
|
|
45
|
+
* Validate an agent YAML payload against the schema derived from its file location.
|
|
46
|
+
* Exposed as the single public entry point, so callers do not reach into schema internals.
|
|
47
|
+
*
|
|
48
|
+
* @param filePath Path to the agent file (used to infer module scope).
|
|
49
|
+
* @param agentYaml Parsed YAML content.
|
|
50
|
+
* @returns SafeParse result.
|
|
51
|
+
*/
|
|
52
|
+
export function validateAgentFile(filePath: string, agentYaml: unknown): z.SafeParseReturnType<unknown, unknown> {
|
|
53
|
+
const expectedModule = deriveModuleFromPath(filePath);
|
|
54
|
+
const schema = agentSchema({ module: expectedModule });
|
|
55
|
+
return schema.safeParse(agentYaml);
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
// Internal helpers ---------------------------------------------------------
|
|
59
|
+
|
|
60
|
+
/**
|
|
61
|
+
* Build a Zod schema for validating a single agent definition.
|
|
62
|
+
* The schema is generated per call so module-scoped agents can pass their expected
|
|
63
|
+
* module slug while core agents leave it undefined.
|
|
64
|
+
*
|
|
65
|
+
* @param options Configuration options.
|
|
66
|
+
* @returns Configured Zod schema instance.
|
|
67
|
+
*/
|
|
68
|
+
function agentSchema(options: AgentSchemaOptions = {}): z.ZodSchema {
|
|
69
|
+
const expectedModule = normalizeModuleOption(options.module);
|
|
70
|
+
|
|
71
|
+
return (
|
|
72
|
+
z
|
|
73
|
+
.object({
|
|
74
|
+
agent: buildAgentSchema(expectedModule),
|
|
75
|
+
})
|
|
76
|
+
.strict()
|
|
77
|
+
// Refinement: enforce trigger format and uniqueness rules after structural checks.
|
|
78
|
+
.superRefine((value, ctx) => {
|
|
79
|
+
const seenTriggers = new Set<string>();
|
|
80
|
+
|
|
81
|
+
let index = 0;
|
|
82
|
+
for (const item of value.agent.menu) {
|
|
83
|
+
// Handle legacy format with trigger field
|
|
84
|
+
if (item.trigger) {
|
|
85
|
+
const triggerValue = item.trigger;
|
|
86
|
+
let canonicalTrigger = triggerValue;
|
|
87
|
+
|
|
88
|
+
// Check if it's a compound trigger (contains " or ")
|
|
89
|
+
if (triggerValue.includes(' or ')) {
|
|
90
|
+
const result = parseCompoundTrigger(triggerValue);
|
|
91
|
+
if (!result.valid) {
|
|
92
|
+
ctx.addIssue({
|
|
93
|
+
code: 'custom',
|
|
94
|
+
path: ['agent', 'menu', index, 'trigger'],
|
|
95
|
+
message: `agent.menu[].trigger compound format error: ${result.error}`,
|
|
96
|
+
});
|
|
97
|
+
return;
|
|
98
|
+
}
|
|
99
|
+
|
|
100
|
+
// Validate that shortcut matches description brackets
|
|
101
|
+
const descriptionMatch = item.description?.match(/^\[([A-Z]{1,3})\]/);
|
|
102
|
+
if (!descriptionMatch) {
|
|
103
|
+
ctx.addIssue({
|
|
104
|
+
code: 'custom',
|
|
105
|
+
path: ['agent', 'menu', index, 'description'],
|
|
106
|
+
message: `agent.menu[].description must start with [SHORTCUT] where SHORTCUT matches the trigger shortcut "${result.shortcut}"`,
|
|
107
|
+
});
|
|
108
|
+
return;
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
const descriptionShortcut = descriptionMatch[1];
|
|
112
|
+
if (descriptionShortcut !== result.shortcut) {
|
|
113
|
+
ctx.addIssue({
|
|
114
|
+
code: 'custom',
|
|
115
|
+
path: ['agent', 'menu', index, 'description'],
|
|
116
|
+
message: `agent.menu[].description shortcut "[${descriptionShortcut}]" must match trigger shortcut "${result.shortcut}"`,
|
|
117
|
+
});
|
|
118
|
+
return;
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
canonicalTrigger = result.kebabTrigger!;
|
|
122
|
+
} else if (!TRIGGER_PATTERN.test(triggerValue)) {
|
|
123
|
+
ctx.addIssue({
|
|
124
|
+
code: 'custom',
|
|
125
|
+
path: ['agent', 'menu', index, 'trigger'],
|
|
126
|
+
message: 'agent.menu[].trigger must be kebab-case (lowercase words separated by hyphen)',
|
|
127
|
+
});
|
|
128
|
+
return;
|
|
129
|
+
}
|
|
130
|
+
|
|
131
|
+
if (seenTriggers.has(canonicalTrigger)) {
|
|
132
|
+
ctx.addIssue({
|
|
133
|
+
code: 'custom',
|
|
134
|
+
path: ['agent', 'menu', index, 'trigger'],
|
|
135
|
+
message: `agent.menu[].trigger duplicates "${canonicalTrigger}" within the same agent`,
|
|
136
|
+
});
|
|
137
|
+
return;
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
seenTriggers.add(canonicalTrigger);
|
|
141
|
+
}
|
|
142
|
+
// Handle multi format with triggers array (new format)
|
|
143
|
+
else if (item.triggers && Array.isArray(item.triggers)) {
|
|
144
|
+
for (const [triggerIndex, triggerItem] of item.triggers.entries()) {
|
|
145
|
+
let triggerName: string | null = null;
|
|
146
|
+
|
|
147
|
+
// Extract trigger name from all three formats
|
|
148
|
+
if (triggerItem.trigger) {
|
|
149
|
+
// Format 1: Simple flat format with trigger field
|
|
150
|
+
triggerName = triggerItem.trigger;
|
|
151
|
+
} else {
|
|
152
|
+
// Format 2a or 2b: Object-key format
|
|
153
|
+
const keys = Object.keys(triggerItem);
|
|
154
|
+
if (keys.length === 1 && keys[0] !== 'trigger') {
|
|
155
|
+
triggerName = keys[0];
|
|
156
|
+
}
|
|
157
|
+
}
|
|
158
|
+
|
|
159
|
+
if (triggerName) {
|
|
160
|
+
if (!TRIGGER_PATTERN.test(triggerName)) {
|
|
161
|
+
ctx.addIssue({
|
|
162
|
+
code: 'custom',
|
|
163
|
+
path: ['agent', 'menu', index, 'triggers', triggerIndex],
|
|
164
|
+
message: `agent.menu[].triggers[] must be kebab-case (lowercase words separated by hyphen) - got "${triggerName}"`,
|
|
165
|
+
});
|
|
166
|
+
return;
|
|
167
|
+
}
|
|
168
|
+
|
|
169
|
+
if (seenTriggers.has(triggerName)) {
|
|
170
|
+
ctx.addIssue({
|
|
171
|
+
code: 'custom',
|
|
172
|
+
path: ['agent', 'menu', index, 'triggers', triggerIndex],
|
|
173
|
+
message: `agent.menu[].triggers[] duplicates "${triggerName}" within the same agent`,
|
|
174
|
+
});
|
|
175
|
+
return;
|
|
176
|
+
}
|
|
177
|
+
|
|
178
|
+
seenTriggers.add(triggerName);
|
|
179
|
+
}
|
|
180
|
+
}
|
|
181
|
+
}
|
|
182
|
+
|
|
183
|
+
index += 1;
|
|
184
|
+
}
|
|
185
|
+
})
|
|
186
|
+
// Refinement: suggest conversational_knowledge when discussion is true
|
|
187
|
+
.superRefine((value, ctx) => {
|
|
188
|
+
if (value.agent.discussion === true && !value.agent.conversational_knowledge) {
|
|
189
|
+
ctx.addIssue({
|
|
190
|
+
code: 'custom',
|
|
191
|
+
path: ['agent', 'conversational_knowledge'],
|
|
192
|
+
message: 'It is recommended to include conversational_knowledge when discussion is true',
|
|
193
|
+
});
|
|
194
|
+
}
|
|
195
|
+
})
|
|
196
|
+
);
|
|
197
|
+
}
|
|
198
|
+
|
|
199
|
+
/**
|
|
200
|
+
* Assemble the full agent schema using the module expectation provided by the caller.
|
|
201
|
+
* @param expectedModule Trimmed module slug or null for core agents.
|
|
202
|
+
*/
|
|
203
|
+
function buildAgentSchema(expectedModule: string | null): z.ZodSchema {
|
|
204
|
+
return z
|
|
205
|
+
.object({
|
|
206
|
+
metadata: buildMetadataSchema(expectedModule),
|
|
207
|
+
persona: buildPersonaSchema(),
|
|
208
|
+
critical_actions: z.array(createNonEmptyString('agent.critical_actions[]')).optional(),
|
|
209
|
+
menu: z.array(buildMenuItemSchema()).min(1, { message: 'agent.menu must include at least one entry' }),
|
|
210
|
+
prompts: z.array(buildPromptSchema()).optional(),
|
|
211
|
+
webskip: z.boolean().optional(),
|
|
212
|
+
discussion: z.boolean().optional(),
|
|
213
|
+
conversational_knowledge: z.array(z.object({}).passthrough()).min(1).optional(),
|
|
214
|
+
})
|
|
215
|
+
.strict();
|
|
216
|
+
}
|
|
217
|
+
|
|
218
|
+
/**
|
|
219
|
+
* Validate metadata shape.
|
|
220
|
+
* @param expectedModule Trimmed module slug or null when core agent metadata is expected.
|
|
221
|
+
* Note: Module field is optional and can be any value - no validation against path.
|
|
222
|
+
*/
|
|
223
|
+
function buildMetadataSchema(expectedModule: string | null): z.ZodSchema {
|
|
224
|
+
const schemaShape = {
|
|
225
|
+
id: createNonEmptyString('agent.metadata.id'),
|
|
226
|
+
name: createNonEmptyString('agent.metadata.name'),
|
|
227
|
+
title: createNonEmptyString('agent.metadata.title'),
|
|
228
|
+
icon: createNonEmptyString('agent.metadata.icon'),
|
|
229
|
+
module: createNonEmptyString('agent.metadata.module').optional(),
|
|
230
|
+
hasSidecar: z.boolean(),
|
|
231
|
+
};
|
|
232
|
+
|
|
233
|
+
return z.object(schemaShape).strict();
|
|
234
|
+
}
|
|
235
|
+
|
|
236
|
+
function buildPersonaSchema(): z.ZodSchema {
|
|
237
|
+
return z
|
|
238
|
+
.object({
|
|
239
|
+
role: createNonEmptyString('agent.persona.role'),
|
|
240
|
+
identity: createNonEmptyString('agent.persona.identity'),
|
|
241
|
+
communication_style: createNonEmptyString('agent.persona.communication_style'),
|
|
242
|
+
principles: z.union([
|
|
243
|
+
createNonEmptyString('agent.persona.principles'),
|
|
244
|
+
z
|
|
245
|
+
.array(createNonEmptyString('agent.persona.principles[]'))
|
|
246
|
+
.min(1, { message: 'agent.persona.principles must include at least one entry' }),
|
|
247
|
+
]),
|
|
248
|
+
})
|
|
249
|
+
.strict();
|
|
250
|
+
}
|
|
251
|
+
|
|
252
|
+
function buildPromptSchema(): z.ZodSchema {
|
|
253
|
+
return z
|
|
254
|
+
.object({
|
|
255
|
+
id: createNonEmptyString('agent.prompts[].id'),
|
|
256
|
+
content: z.string().refine((value) => value.trim().length > 0, {
|
|
257
|
+
message: 'agent.prompts[].content must be a non-empty string',
|
|
258
|
+
}),
|
|
259
|
+
description: createNonEmptyString('agent.prompts[].description').optional(),
|
|
260
|
+
})
|
|
261
|
+
.strict();
|
|
262
|
+
}
|
|
263
|
+
|
|
264
|
+
/**
|
|
265
|
+
* Schema for individual menu entries ensuring they are actionable.
|
|
266
|
+
* Supports both legacy format and new multi format.
|
|
267
|
+
*/
|
|
268
|
+
function buildMenuItemSchema(): z.ZodSchema {
|
|
269
|
+
// Legacy menu item format
|
|
270
|
+
const legacyMenuItemSchema = z
|
|
271
|
+
.object({
|
|
272
|
+
trigger: createNonEmptyString('agent.menu[].trigger'),
|
|
273
|
+
description: createNonEmptyString('agent.menu[].description'),
|
|
274
|
+
workflow: createNonEmptyString('agent.menu[].workflow').optional(),
|
|
275
|
+
'workflow-install': createNonEmptyString('agent.menu[].workflow-install').optional(),
|
|
276
|
+
'validate-workflow': createNonEmptyString('agent.menu[].validate-workflow').optional(),
|
|
277
|
+
exec: createNonEmptyString('agent.menu[].exec').optional(),
|
|
278
|
+
action: createNonEmptyString('agent.menu[].action').optional(),
|
|
279
|
+
tmpl: createNonEmptyString('agent.menu[].tmpl').optional(),
|
|
280
|
+
data: z.string().optional(),
|
|
281
|
+
checklist: createNonEmptyString('agent.menu[].checklist').optional(),
|
|
282
|
+
document: createNonEmptyString('agent.menu[].document').optional(),
|
|
283
|
+
'ide-only': z.boolean().optional(),
|
|
284
|
+
'web-only': z.boolean().optional(),
|
|
285
|
+
discussion: z.boolean().optional(),
|
|
286
|
+
})
|
|
287
|
+
.strict()
|
|
288
|
+
.superRefine((value, ctx) => {
|
|
289
|
+
const hasCommandTarget = COMMAND_TARGET_KEYS.some((key) => {
|
|
290
|
+
const commandValue = value[key as keyof typeof value];
|
|
291
|
+
return typeof commandValue === 'string' && commandValue.trim().length > 0;
|
|
292
|
+
});
|
|
293
|
+
|
|
294
|
+
if (!hasCommandTarget) {
|
|
295
|
+
ctx.addIssue({
|
|
296
|
+
code: 'custom',
|
|
297
|
+
message: 'agent.menu[] entries must include at least one command target field',
|
|
298
|
+
});
|
|
299
|
+
}
|
|
300
|
+
});
|
|
301
|
+
|
|
302
|
+
// Multi menu item format
|
|
303
|
+
const multiMenuItemSchema = z
|
|
304
|
+
.object({
|
|
305
|
+
multi: createNonEmptyString('agent.menu[].multi'),
|
|
306
|
+
triggers: z
|
|
307
|
+
.array(
|
|
308
|
+
z.union([
|
|
309
|
+
// Format 1: Simple flat format (has trigger field)
|
|
310
|
+
z
|
|
311
|
+
.object({
|
|
312
|
+
trigger: z.string(),
|
|
313
|
+
input: createNonEmptyString('agent.menu[].triggers[].input'),
|
|
314
|
+
route: createNonEmptyString('agent.menu[].triggers[].route').optional(),
|
|
315
|
+
action: createNonEmptyString('agent.menu[].triggers[].action').optional(),
|
|
316
|
+
data: z.string().optional(),
|
|
317
|
+
type: z.enum(['exec', 'action', 'workflow']).optional(),
|
|
318
|
+
})
|
|
319
|
+
.strict()
|
|
320
|
+
.refine((data) => data.trigger, { message: 'Must have trigger field' })
|
|
321
|
+
.superRefine((value, ctx) => {
|
|
322
|
+
// Must have either route or action (or both)
|
|
323
|
+
if (!value.route && !value.action) {
|
|
324
|
+
ctx.addIssue({
|
|
325
|
+
code: 'custom',
|
|
326
|
+
message: 'agent.menu[].triggers[] must have either route or action (or both)',
|
|
327
|
+
});
|
|
328
|
+
}
|
|
329
|
+
}),
|
|
330
|
+
// Format 2a: Object with array format (like bmad-builder.agent.yaml)
|
|
331
|
+
z
|
|
332
|
+
.object({})
|
|
333
|
+
.passthrough()
|
|
334
|
+
.refine(
|
|
335
|
+
(value) => {
|
|
336
|
+
const keys = Object.keys(value);
|
|
337
|
+
if (keys.length !== 1) return false;
|
|
338
|
+
const triggerItems = value[keys[0]];
|
|
339
|
+
return Array.isArray(triggerItems);
|
|
340
|
+
},
|
|
341
|
+
{ message: 'Must be object with single key pointing to array' },
|
|
342
|
+
)
|
|
343
|
+
.superRefine((value, ctx) => {
|
|
344
|
+
const triggerName = Object.keys(value)[0];
|
|
345
|
+
const triggerItems = value[triggerName];
|
|
346
|
+
|
|
347
|
+
if (!Array.isArray(triggerItems)) {
|
|
348
|
+
ctx.addIssue({
|
|
349
|
+
code: 'custom',
|
|
350
|
+
message: `Trigger "${triggerName}" must be an array of items`,
|
|
351
|
+
});
|
|
352
|
+
return;
|
|
353
|
+
}
|
|
354
|
+
|
|
355
|
+
// Check required fields in the array
|
|
356
|
+
const hasInput = triggerItems.some((item: any) => 'input' in item);
|
|
357
|
+
const hasRouteOrAction = triggerItems.some((item: any) => 'route' in item || 'action' in item);
|
|
358
|
+
|
|
359
|
+
if (!hasInput) {
|
|
360
|
+
ctx.addIssue({
|
|
361
|
+
code: 'custom',
|
|
362
|
+
message: `Trigger "${triggerName}" must have an input field`,
|
|
363
|
+
});
|
|
364
|
+
}
|
|
365
|
+
|
|
366
|
+
if (!hasRouteOrAction) {
|
|
367
|
+
ctx.addIssue({
|
|
368
|
+
code: 'custom',
|
|
369
|
+
message: `Trigger "${triggerName}" must have a route or action field`,
|
|
370
|
+
});
|
|
371
|
+
}
|
|
372
|
+
}),
|
|
373
|
+
// Format 2b: Object with direct fields (like analyst.agent.yaml)
|
|
374
|
+
z
|
|
375
|
+
.object({})
|
|
376
|
+
.passthrough()
|
|
377
|
+
.refine(
|
|
378
|
+
(value) => {
|
|
379
|
+
const keys = Object.keys(value);
|
|
380
|
+
if (keys.length !== 1) return false;
|
|
381
|
+
const triggerFields = value[keys[0]];
|
|
382
|
+
return !Array.isArray(triggerFields) && typeof triggerFields === 'object';
|
|
383
|
+
},
|
|
384
|
+
{ message: 'Must be object with single key pointing to object' },
|
|
385
|
+
)
|
|
386
|
+
.superRefine((value, ctx) => {
|
|
387
|
+
const triggerName = Object.keys(value)[0];
|
|
388
|
+
const triggerFields = value[triggerName];
|
|
389
|
+
|
|
390
|
+
// Check required fields
|
|
391
|
+
if (!triggerFields.input || typeof triggerFields.input !== 'string') {
|
|
392
|
+
ctx.addIssue({
|
|
393
|
+
code: 'custom',
|
|
394
|
+
message: `Trigger "${triggerName}" must have an input field`,
|
|
395
|
+
});
|
|
396
|
+
}
|
|
397
|
+
|
|
398
|
+
if (!triggerFields.route && !triggerFields.action) {
|
|
399
|
+
ctx.addIssue({
|
|
400
|
+
code: 'custom',
|
|
401
|
+
message: `Trigger "${triggerName}" must have a route or action field`,
|
|
402
|
+
});
|
|
403
|
+
}
|
|
404
|
+
}),
|
|
405
|
+
]),
|
|
406
|
+
)
|
|
407
|
+
.min(1, { message: 'agent.menu[].triggers must have at least one trigger' }),
|
|
408
|
+
discussion: z.boolean().optional(),
|
|
409
|
+
})
|
|
410
|
+
.strict()
|
|
411
|
+
.superRefine((value, ctx) => {
|
|
412
|
+
// Check for duplicate trigger names
|
|
413
|
+
const seenTriggers = new Set<string>();
|
|
414
|
+
for (const [index, triggerItem] of value.triggers.entries()) {
|
|
415
|
+
let triggerName: string | null = null;
|
|
416
|
+
|
|
417
|
+
// Extract trigger name from either format
|
|
418
|
+
if (triggerItem.trigger) {
|
|
419
|
+
// Format 1
|
|
420
|
+
triggerName = triggerItem.trigger;
|
|
421
|
+
} else {
|
|
422
|
+
// Format 2
|
|
423
|
+
const keys = Object.keys(triggerItem);
|
|
424
|
+
if (keys.length === 1) {
|
|
425
|
+
triggerName = keys[0];
|
|
426
|
+
}
|
|
427
|
+
}
|
|
428
|
+
|
|
429
|
+
if (triggerName) {
|
|
430
|
+
if (seenTriggers.has(triggerName)) {
|
|
431
|
+
ctx.addIssue({
|
|
432
|
+
code: 'custom',
|
|
433
|
+
path: ['agent', 'menu', 'triggers', index],
|
|
434
|
+
message: `Trigger name "${triggerName}" is duplicated`,
|
|
435
|
+
});
|
|
436
|
+
}
|
|
437
|
+
seenTriggers.add(triggerName);
|
|
438
|
+
|
|
439
|
+
// Validate trigger name format
|
|
440
|
+
if (!TRIGGER_PATTERN.test(triggerName)) {
|
|
441
|
+
ctx.addIssue({
|
|
442
|
+
code: 'custom',
|
|
443
|
+
path: ['agent', 'menu', 'triggers', index],
|
|
444
|
+
message: `Trigger name "${triggerName}" must be kebab-case (lowercase words separated by hyphen)`,
|
|
445
|
+
});
|
|
446
|
+
}
|
|
447
|
+
}
|
|
448
|
+
}
|
|
449
|
+
});
|
|
450
|
+
|
|
451
|
+
return z.union([legacyMenuItemSchema, multiMenuItemSchema]);
|
|
452
|
+
}
|
|
453
|
+
|
|
454
|
+
/**
|
|
455
|
+
* Derive the expected module slug from a file path residing under src/<module>/agents/.
|
|
456
|
+
* @param filePath Absolute or relative agent path.
|
|
457
|
+
* @returns Module slug if identifiable, otherwise null.
|
|
458
|
+
*/
|
|
459
|
+
function deriveModuleFromPath(filePath: string): string | null {
|
|
460
|
+
assert(filePath, 'validateAgentFile expects filePath to be provided');
|
|
461
|
+
assert(typeof filePath === 'string', 'validateAgentFile expects filePath to be a string');
|
|
462
|
+
assert(filePath.startsWith('src/'), 'validateAgentFile expects filePath to start with "src/"');
|
|
463
|
+
|
|
464
|
+
const marker = 'src/';
|
|
465
|
+
if (!filePath.startsWith(marker)) {
|
|
466
|
+
return null;
|
|
467
|
+
}
|
|
468
|
+
|
|
469
|
+
const remainder = filePath.slice(marker.length);
|
|
470
|
+
const slashIndex = remainder.indexOf('/');
|
|
471
|
+
return slashIndex === -1 ? null : remainder.slice(0, slashIndex);
|
|
472
|
+
}
|
|
473
|
+
|
|
474
|
+
function normalizeModuleOption(moduleOption: string | null | undefined): string | null {
|
|
475
|
+
if (typeof moduleOption !== 'string') {
|
|
476
|
+
return null;
|
|
477
|
+
}
|
|
478
|
+
|
|
479
|
+
const trimmed = moduleOption.trim();
|
|
480
|
+
return trimmed.length > 0 ? trimmed : null;
|
|
481
|
+
}
|
|
482
|
+
|
|
483
|
+
// Primitive validators -----------------------------------------------------
|
|
484
|
+
|
|
485
|
+
function createNonEmptyString(label: string): z.ZodEffects<z.ZodString, string, string> {
|
|
486
|
+
return z.string().refine((value) => value.trim().length > 0, {
|
|
487
|
+
message: `${label} must be a non-empty string`,
|
|
488
|
+
});
|
|
489
|
+
}
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
// Type definitions for agent schema validation
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* Result of parsing a compound trigger string.
|
|
5
|
+
*/
|
|
6
|
+
export interface CompoundTriggerResult {
|
|
7
|
+
valid: boolean;
|
|
8
|
+
shortcut?: string;
|
|
9
|
+
kebabTrigger?: string;
|
|
10
|
+
error?: string;
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
/**
|
|
14
|
+
* Options for building an agent schema.
|
|
15
|
+
*/
|
|
16
|
+
export interface AgentSchemaOptions {
|
|
17
|
+
module?: string | null | undefined;
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
/**
|
|
21
|
+
* Inferred menu item trigger formats
|
|
22
|
+
*/
|
|
23
|
+
export interface TriggerItem {
|
|
24
|
+
trigger?: string;
|
|
25
|
+
input?: string;
|
|
26
|
+
route?: string;
|
|
27
|
+
action?: string;
|
|
28
|
+
data?: string;
|
|
29
|
+
type?: 'exec' | 'action' | 'workflow';
|
|
30
|
+
[key: string]: any;
|
|
31
|
+
}
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
#!/bin/bash
|
|
2
|
+
# BMAD-ElSabro Auto-Update Script
|
|
3
|
+
|
|
4
|
+
BMAD_DIR="/Users/cubait/Desktop/CoD-Refresh/workflow-cubait/openspurce/BMAD-METHOD"
|
|
5
|
+
|
|
6
|
+
echo "š Checking for BMAD-ElSabro updates..."
|
|
7
|
+
|
|
8
|
+
cd "$BMAD_DIR"
|
|
9
|
+
|
|
10
|
+
# Fetch latest from GitHub
|
|
11
|
+
git fetch origin main --quiet
|
|
12
|
+
|
|
13
|
+
# Check if updates available
|
|
14
|
+
LOCAL=$(git rev-parse HEAD)
|
|
15
|
+
REMOTE=$(git rev-parse origin/main)
|
|
16
|
+
|
|
17
|
+
if [ "$LOCAL" != "$REMOTE" ]; then
|
|
18
|
+
echo "š¦ Updates found! Downloading..."
|
|
19
|
+
git pull origin main --quiet
|
|
20
|
+
npm install --quiet
|
|
21
|
+
echo "ā
BMAD-ElSabro updated to latest version!"
|
|
22
|
+
else
|
|
23
|
+
echo "ā
BMAD-ElSabro is up to date."
|
|
24
|
+
fi
|
|
@@ -0,0 +1,110 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Agent Schema Validator CLI
|
|
3
|
+
*
|
|
4
|
+
* Scans all *.agent.yaml files in src/{core,modules/*}/agents/
|
|
5
|
+
* and validates them against the Zod schema.
|
|
6
|
+
*
|
|
7
|
+
* Usage: node tools/validate-agent-schema.js [project_root]
|
|
8
|
+
* Exit codes: 0 = success, 1 = validation failures
|
|
9
|
+
*
|
|
10
|
+
* Optional argument:
|
|
11
|
+
* project_root - Directory to scan (defaults to BMAD repo root)
|
|
12
|
+
*/
|
|
13
|
+
|
|
14
|
+
const { glob } = require('glob');
|
|
15
|
+
const yaml = require('yaml');
|
|
16
|
+
const fs = require('node:fs');
|
|
17
|
+
const path = require('node:path');
|
|
18
|
+
const { validateAgentFile } = require('./schema/agent.js');
|
|
19
|
+
|
|
20
|
+
/**
|
|
21
|
+
* Main validation routine
|
|
22
|
+
* @param {string} [customProjectRoot] - Optional project root to scan (for testing)
|
|
23
|
+
*/
|
|
24
|
+
async function main(customProjectRoot) {
|
|
25
|
+
console.log('š Scanning for agent files...\n');
|
|
26
|
+
|
|
27
|
+
// Determine project root: use custom path if provided, otherwise default to repo root
|
|
28
|
+
const project_root = customProjectRoot || path.join(__dirname, '..');
|
|
29
|
+
|
|
30
|
+
// Find all agent files
|
|
31
|
+
const agentFiles = await glob('src/{core,modules/*}/agents/*.agent.yaml', {
|
|
32
|
+
cwd: project_root,
|
|
33
|
+
absolute: true,
|
|
34
|
+
});
|
|
35
|
+
|
|
36
|
+
if (agentFiles.length === 0) {
|
|
37
|
+
console.log('ā No agent files found. This likely indicates a configuration error.');
|
|
38
|
+
console.log(' Expected to find *.agent.yaml files in src/{core,modules/*}/agents/');
|
|
39
|
+
process.exit(1);
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
console.log(`Found ${agentFiles.length} agent file(s)\n`);
|
|
43
|
+
|
|
44
|
+
const errors = [];
|
|
45
|
+
|
|
46
|
+
// Validate each file
|
|
47
|
+
for (const filePath of agentFiles) {
|
|
48
|
+
const relativePath = path.relative(process.cwd(), filePath);
|
|
49
|
+
|
|
50
|
+
try {
|
|
51
|
+
const fileContent = fs.readFileSync(filePath, 'utf8');
|
|
52
|
+
const agentData = yaml.parse(fileContent);
|
|
53
|
+
|
|
54
|
+
// Convert absolute path to relative src/ path for module detection
|
|
55
|
+
const srcRelativePath = relativePath.startsWith('src/') ? relativePath : path.relative(project_root, filePath).replaceAll('\\', '/');
|
|
56
|
+
|
|
57
|
+
const result = validateAgentFile(srcRelativePath, agentData);
|
|
58
|
+
|
|
59
|
+
if (result.success) {
|
|
60
|
+
console.log(`ā
${relativePath}`);
|
|
61
|
+
} else {
|
|
62
|
+
errors.push({
|
|
63
|
+
file: relativePath,
|
|
64
|
+
issues: result.error.issues,
|
|
65
|
+
});
|
|
66
|
+
}
|
|
67
|
+
} catch (error) {
|
|
68
|
+
errors.push({
|
|
69
|
+
file: relativePath,
|
|
70
|
+
issues: [
|
|
71
|
+
{
|
|
72
|
+
code: 'parse_error',
|
|
73
|
+
message: `Failed to parse YAML: ${error.message}`,
|
|
74
|
+
path: [],
|
|
75
|
+
},
|
|
76
|
+
],
|
|
77
|
+
});
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
// Report errors
|
|
82
|
+
if (errors.length > 0) {
|
|
83
|
+
console.log('\nā Validation failed for the following files:\n');
|
|
84
|
+
|
|
85
|
+
for (const { file, issues } of errors) {
|
|
86
|
+
console.log(`\nš ${file}`);
|
|
87
|
+
for (const issue of issues) {
|
|
88
|
+
const pathString = issue.path.length > 0 ? issue.path.join('.') : '(root)';
|
|
89
|
+
console.log(` Path: ${pathString}`);
|
|
90
|
+
console.log(` Error: ${issue.message}`);
|
|
91
|
+
if (issue.code) {
|
|
92
|
+
console.log(` Code: ${issue.code}`);
|
|
93
|
+
}
|
|
94
|
+
}
|
|
95
|
+
}
|
|
96
|
+
|
|
97
|
+
console.log(`\n\nš„ ${errors.length} file(s) failed validation`);
|
|
98
|
+
process.exit(1);
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
console.log(`\n⨠All ${agentFiles.length} agent file(s) passed validation!\n`);
|
|
102
|
+
process.exit(0);
|
|
103
|
+
}
|
|
104
|
+
|
|
105
|
+
// Run with optional command-line argument for project root
|
|
106
|
+
const customProjectRoot = process.argv[2];
|
|
107
|
+
main(customProjectRoot).catch((error) => {
|
|
108
|
+
console.error('Fatal error:', error);
|
|
109
|
+
process.exit(1);
|
|
110
|
+
});
|