aw-spec-cli 0.1.3 → 0.1.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +291 -0
- package/assets/.agents/agent.json +28 -0
- package/assets/.agents/skills/aw-spec-orch/SKILL.md +56 -0
- package/assets/.agents/skills/aw-spec-orch-demo/SKILL.md +59 -0
- package/assets/.aw-spec/DESIGN-FORMAT.md +151 -0
- package/assets/.aw-spec/ORCH-DIALECT.md +156 -0
- package/assets/.aw-spec/RULE-PARTITION.md +126 -0
- package/assets/.aw-spec/extensions/agent-context/extension.yml +12 -9
- package/assets/.aw-spec/extensions.yml +12 -19
- package/assets/.aw-spec/integrations/aw-spec.manifest.json +1 -9
- package/assets/.aw-spec/interpreter/run-skill.py +1158 -0
- package/assets/.aw-spec/orchestrator/AGENT-PROFILE.md +94 -0
- package/assets/.aw-spec/orchestrator/README.md +300 -0
- package/assets/.aw-spec/orchestrator/adapters/claude_agent_sdk.py +74 -0
- package/assets/.aw-spec/orchestrator/adapters/google_antigravity.py +74 -0
- package/assets/.aw-spec/orchestrator/modules/delta-design.orch.yaml +105 -0
- package/assets/.aw-spec/orchestrator/modules/delta-spec.orch.yaml +79 -0
- package/assets/.aw-spec/orchestrator/modules/domain-select.orch.yaml +81 -0
- package/assets/.aw-spec/orchestrator/modules/tech-select.orch.yaml +75 -0
- package/assets/.aw-spec/orchestrator/orchestrator.py +1721 -0
- package/assets/.aw-spec/orchestrator/rev-templates/ai-rules.reference.md +40 -0
- package/assets/.aw-spec/orchestrator/rev-templates/comandrulemap.skeleton.md +59 -0
- package/assets/.aw-spec/orchestrator/rev-templates/commandtechrulemap.skeleton.md +97 -0
- package/assets/.aw-spec/orchestrator/rev-templates/domain-constitution.skeleton.md +61 -0
- package/assets/.aw-spec/orchestrator/rev-templates/domain-requirements.skeleton.md +48 -0
- package/assets/.aw-spec/orchestrator/rev-templates/domain-rule-file.skeleton.md +39 -0
- package/assets/.aw-spec/orchestrator/rev-templates/technical-constitution.skeleton.md +106 -0
- package/assets/.aw-spec/orchestrator/rev-templates/technical-rule-file.skeleton.md +54 -0
- package/assets/.aw-spec/orchestrator/workflows/_smoke.orch.yaml +160 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-add-component.orch.yaml +244 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-adopt.orch.yaml +775 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-analyze-delta-design.orch.yaml +248 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-analyze-design.orch.yaml +261 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-analyze-slice.orch.yaml +425 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-build.orch.yaml +188 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-characterize.orch.yaml +474 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-close-delta.orch.yaml +181 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-constitution.orch.yaml +284 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-demo.orch.yaml +103 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-dependency-tree.orch.yaml +69 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-deploy.orch.yaml +85 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-design.orch.yaml +382 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-finalize-delta.orch.yaml +382 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-foundation.orch.yaml +246 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-implement-delta.orch.yaml +231 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-implement.orch.yaml +258 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-inventory.orch.yaml +236 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-onboard.orch.yaml +949 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-parity.orch.yaml +293 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-run.orch.yaml +177 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-select-domain.orch.yaml +79 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-select-feature.orch.yaml +128 -0
- package/assets/.aw-spec/orchestrator/workflows/aw-spec-specify.orch.yaml +412 -0
- package/assets/.aw-spec/scripts/bash/aw-inventory.sh +14 -0
- package/assets/.aw-spec/scripts/bash/aw-parity.sh +13 -0
- package/assets/.aw-spec/scripts/bash/aw-rev-constitution.sh +13 -0
- package/assets/.aw-spec/scripts/bash/aw-spec-actions.sh +1899 -0
- package/assets/.aw-spec/scripts/bash/aw-xref.sh +15 -0
- package/assets/.aw-spec/scripts/bash/common.sh +11 -60
- package/assets/.aw-spec/scripts/powershell/aw-inventory.ps1 +14 -0
- package/assets/.aw-spec/scripts/powershell/aw-parity.ps1 +13 -0
- package/assets/.aw-spec/scripts/powershell/aw-rev-constitution.ps1 +13 -0
- package/assets/.aw-spec/scripts/powershell/aw-spec-actions.ps1 +1563 -0
- package/assets/.aw-spec/scripts/powershell/aw-xref.ps1 +15 -0
- package/assets/.aw-spec/scripts/python/aw-inventory.py +683 -0
- package/assets/.aw-spec/scripts/python/aw-parity.py +380 -0
- package/assets/.aw-spec/scripts/python/aw-rev-constitution.py +312 -0
- package/assets/.aw-spec/scripts/python/aw-xref.py +1330 -0
- package/assets/.aw-spec/scripts/python/validate_okf.py +349 -0
- package/assets/.aw-spec/templates/constitution-domain-template.md +75 -0
- package/assets/.aw-spec/templates/constitution-technical-template.md +70 -0
- package/assets/.aw-spec/templates/delta-design-template.md +69 -0
- package/assets/.aw-spec/templates/delta-spec-template.md +60 -0
- package/assets/.aw-spec/templates/design-template.md +383 -0
- package/assets/.aw-spec/templates/okf-concept-template.md +103 -0
- package/assets/.aw-spec/templates/parity-manifest-template.json +49 -0
- package/assets/.aw-spec/templates/source-map-template.md +85 -0
- package/assets/.aw-spec/templates/spec-template.md +192 -71
- package/assets/.claude/agent.json +27 -0
- package/assets/.claude/skills/aw-spec-orch/SKILL.md +55 -0
- package/assets/.claude/skills/aw-spec-orch-demo/SKILL.md +59 -0
- package/assets/.kilocode/agent.json +28 -0
- package/assets/.kilocode/workflows/aw-spec-orch-demo.md +59 -0
- package/assets/.kilocode/workflows/aw-spec-orch.md +55 -0
- package/assets/docs/architecture/clean-architecture.md +1 -1
- package/assets/docs/architecture/cqrs.md +1 -1
- package/assets/docs/architecture/eventing.md +1 -1
- package/assets/docs/architecture/folder-structure.md +1 -1
- package/assets/docs/architecture/modular-monolith.md +1 -1
- package/assets/docs/architecture/persistence.md +1 -1
- package/assets/docs/architecture/testing.md +1 -1
- package/assets/docs/architecture/vertical-slices.md +1 -1
- package/assets/docs/components/Email/README.md +1 -1
- package/assets/docs/components/Jobs/README.md +1 -1
- package/assets/docs/components/QrGenerator/README.md +1 -1
- package/assets/docs/components/README.md +1 -1
- package/assets/docs/domain/domain-driven-design.md +1 -1
- package/assets/docs/domainspecs/healthcare/api-versioning.domain.md +1 -1
- package/assets/docs/domainspecs/healthcare/auditing.domain.md +86 -18
- package/assets/docs/domainspecs/healthcare/authorization.domain.md +1 -1
- package/assets/docs/domainspecs/healthcare/clinical-terms.md +1 -1
- package/assets/docs/domainspecs/healthcare/coding-standards.domain.md +1 -1
- package/assets/docs/domainspecs/healthcare/comandrulemap.md +58 -124
- package/assets/docs/domainspecs/healthcare/commandtechrulemap.md +119 -0
- package/assets/docs/domainspecs/healthcare/consent.md +1 -1
- package/assets/docs/domainspecs/healthcare/cqrs.domain.md +1 -1
- package/assets/docs/domainspecs/healthcare/data-classification.domain.md +1 -1
- package/assets/docs/domainspecs/healthcare/dependency-policy.domain.md +1 -1
- package/assets/docs/domainspecs/healthcare/dicom.md +1 -1
- package/assets/docs/domainspecs/healthcare/domain-driven-design.domain.md +1 -1
- package/assets/docs/domainspecs/healthcare/eventing.domain.md +1 -1
- package/assets/docs/domainspecs/healthcare/fhir.md +1 -1
- package/assets/docs/domainspecs/healthcare/folder-structure.domain.md +1 -1
- package/assets/docs/domainspecs/healthcare/hipaa.md +1 -1
- package/assets/docs/domainspecs/healthcare/hl7.md +1 -1
- package/assets/docs/domainspecs/healthcare/integration-terms.md +1 -1
- package/assets/docs/domainspecs/healthcare/persistence.domain.md +1 -1
- package/assets/docs/domainspecs/healthcare/terminology.md +1 -1
- package/assets/docs/domainspecs/healthcare/testing.domain.md +1 -1
- package/assets/docs/domainspecs/healthcare/vertical-slices.domain.md +1 -1
- package/assets/docs/domainspecs/healthcare/zero-trust.domain.md +1 -1
- package/assets/docs/domainspecs/pharma/api-versioning.domain.md +1 -1
- package/assets/docs/domainspecs/pharma/atc.md +1 -1
- package/assets/docs/domainspecs/pharma/auditing.domain.md +80 -16
- package/assets/docs/domainspecs/pharma/authorization.domain.md +1 -1
- package/assets/docs/domainspecs/pharma/coding-standards.domain.md +1 -1
- package/assets/docs/domainspecs/pharma/comandrulemap.md +64 -142
- package/assets/docs/domainspecs/pharma/commandtechrulemap.md +119 -0
- package/assets/docs/domainspecs/pharma/cqrs.domain.md +1 -1
- package/assets/docs/domainspecs/pharma/data-classification.domain.md +1 -1
- package/assets/docs/domainspecs/pharma/data-provenance.md +1 -1
- package/assets/docs/domainspecs/pharma/dependency-policy.domain.md +1 -1
- package/assets/docs/domainspecs/pharma/domain-driven-design.domain.md +1 -1
- package/assets/docs/domainspecs/pharma/eventing.domain.md +1 -1
- package/assets/docs/domainspecs/pharma/fhir.md +1 -1
- package/assets/docs/domainspecs/pharma/folder-structure.domain.md +1 -1
- package/assets/docs/domainspecs/pharma/hl7.md +1 -1
- package/assets/docs/domainspecs/pharma/idmp.md +1 -1
- package/assets/docs/domainspecs/pharma/integration-terms.md +1 -1
- package/assets/docs/domainspecs/pharma/ndc.md +1 -1
- package/assets/docs/domainspecs/pharma/persistence.domain.md +1 -1
- package/assets/docs/domainspecs/pharma/pharma-terms.md +1 -1
- package/assets/docs/domainspecs/pharma/product-lifecycle.domain.md +1 -1
- package/assets/docs/domainspecs/pharma/regulatory-compliance.md +1 -1
- package/assets/docs/domainspecs/pharma/terminology.md +1 -1
- package/assets/docs/domainspecs/pharma/testing.domain.md +1 -1
- package/assets/docs/domainspecs/pharma/vertical-slices.domain.md +1 -1
- package/assets/docs/domainspecs/pharma/zero-trust.domain.md +1 -1
- package/assets/docs/governance/api-versioning.md +1 -1
- package/assets/docs/governance/coding-standards.md +1 -1
- package/assets/docs/governance/dependency-policy.md +1 -1
- package/assets/docs/requirement-spec.txt +13 -1
- package/assets/docs/security/auditing.md +54 -11
- package/assets/docs/security/authorization.md +1 -1
- package/assets/docs/security/data-classification.md +1 -1
- package/assets/docs/security/zero-trust.md +1 -1
- package/dist/commands/update.d.ts +3 -0
- package/dist/commands/update.d.ts.map +1 -0
- package/dist/commands/update.js +142 -0
- package/dist/commands/update.js.map +1 -0
- package/dist/utils/manifest.d.ts +31 -0
- package/dist/utils/manifest.d.ts.map +1 -0
- package/dist/utils/manifest.js +91 -0
- package/dist/utils/manifest.js.map +1 -0
- package/dist/utils/paths.js +2 -2
- package/dist/utils/paths.js.map +1 -1
- package/dist/utils/update-engine.d.ts +52 -0
- package/dist/utils/update-engine.d.ts.map +1 -0
- package/dist/utils/update-engine.js +203 -0
- package/dist/utils/update-engine.js.map +1 -0
- package/package.json +1 -1
- package/assets/.agents/skills/aw-spec-addcomponent/SKILL.md +0 -129
- package/assets/.agents/skills/aw-spec-agent-context-update/SKILL.md +0 -31
- package/assets/.agents/skills/aw-spec-analyze/SKILL.md +0 -296
- package/assets/.agents/skills/aw-spec-checklist/SKILL.md +0 -374
- package/assets/.agents/skills/aw-spec-clarify/SKILL.md +0 -320
- package/assets/.agents/skills/aw-spec-constitution/SKILL.md +0 -194
- package/assets/.agents/skills/aw-spec-fast-implement/SKILL.md +0 -268
- package/assets/.agents/skills/aw-spec-foundation/SKILL.md +0 -358
- package/assets/.agents/skills/aw-spec-implement/SKILL.md +0 -279
- package/assets/.agents/skills/aw-spec-minimal-implementation/SKILL.md +0 -209
- package/assets/.agents/skills/aw-spec-plan/SKILL.md +0 -221
- package/assets/.agents/skills/aw-spec-select-domain/SKILL.md +0 -73
- package/assets/.agents/skills/aw-spec-specify/SKILL.md +0 -382
- package/assets/.agents/skills/aw-spec-tasks/SKILL.md +0 -259
- package/assets/.agents/skills/aw-spec-taskstoissues/SKILL.md +0 -107
- package/assets/.aw-spec/integrations/claude.manifest.json +0 -17
- package/assets/.aw-spec/scripts/bash/check-prerequisites.sh +0 -189
- package/assets/.aw-spec/scripts/bash/create-new-feature.sh +0 -299
- package/assets/.aw-spec/scripts/bash/setup-plan.sh +0 -84
- package/assets/.aw-spec/scripts/bash/setup-tasks.sh +0 -91
- package/assets/.aw-spec/templates/checklist-template.md +0 -40
- package/assets/.aw-spec/templates/constitution-template.md +0 -57
- package/assets/.aw-spec/templates/plan-template.md +0 -113
- package/assets/.aw-spec/templates/tasks-template.md +0 -252
- package/assets/.aw-spec/workflows/aw-spec/workflow.yml +0 -77
- package/assets/.aw-spec/workflows/workflow-registry.json +0 -13
- package/assets/.claude/skills/aw-spec-addcomponent/SKILL.md +0 -129
- package/assets/.claude/skills/aw-spec-agent-context-update/SKILL.md +0 -31
- package/assets/.claude/skills/aw-spec-analyze/SKILL.md +0 -296
- package/assets/.claude/skills/aw-spec-checklist/SKILL.md +0 -374
- package/assets/.claude/skills/aw-spec-clarify/SKILL.md +0 -320
- package/assets/.claude/skills/aw-spec-constitution/SKILL.md +0 -194
- package/assets/.claude/skills/aw-spec-fast-implement/SKILL.md +0 -268
- package/assets/.claude/skills/aw-spec-foundation/SKILL.md +0 -358
- package/assets/.claude/skills/aw-spec-implement/SKILL.md +0 -279
- package/assets/.claude/skills/aw-spec-minimal-implementation/SKILL.md +0 -209
- package/assets/.claude/skills/aw-spec-plan/SKILL.md +0 -221
- package/assets/.claude/skills/aw-spec-select-domain/SKILL.md +0 -73
- package/assets/.claude/skills/aw-spec-specify/SKILL.md +0 -382
- package/assets/.claude/skills/aw-spec-tasks/SKILL.md +0 -259
- package/assets/.claude/skills/aw-spec-taskstoissues/SKILL.md +0 -107
- package/assets/.kilocode/rules/specify-rules.md +0 -4
- package/assets/.kilocode/workflows/aw-spec-addcomponent.md +0 -129
- package/assets/.kilocode/workflows/aw-spec-agent-context.update.md +0 -31
- package/assets/.kilocode/workflows/aw-spec-analyze.md +0 -296
- package/assets/.kilocode/workflows/aw-spec-checklist.md +0 -374
- package/assets/.kilocode/workflows/aw-spec-clarify.md +0 -320
- package/assets/.kilocode/workflows/aw-spec-constitution.md +0 -194
- package/assets/.kilocode/workflows/aw-spec-fast-implement.md +0 -263
- package/assets/.kilocode/workflows/aw-spec-foundation.md +0 -358
- package/assets/.kilocode/workflows/aw-spec-implement.md +0 -279
- package/assets/.kilocode/workflows/aw-spec-minimal-implementation.md +0 -204
- package/assets/.kilocode/workflows/aw-spec-plan.md +0 -221
- package/assets/.kilocode/workflows/aw-spec-select-domain.md +0 -73
- package/assets/.kilocode/workflows/aw-spec-specify.md +0 -382
- package/assets/.kilocode/workflows/aw-spec-tasks.md +0 -259
- package/assets/.kilocode/workflows/aw-spec-taskstoissues.md +0 -107
- package/assets/docs/command.txt +0 -295
- package/assets/docs/pharma-constitution.my-ref.md +0 -86
|
@@ -1,107 +0,0 @@
|
|
|
1
|
-
---
|
|
2
|
-
name: "aw-spec-taskstoissues"
|
|
3
|
-
description: "Convert existing tasks into actionable, dependency-ordered GitHub issues for the feature based on available design artifacts."
|
|
4
|
-
argument-hint: "Optional filter or label for GitHub issues"
|
|
5
|
-
compatibility: "Requires aw-spec project structure with .aw-spec/ directory"
|
|
6
|
-
metadata:
|
|
7
|
-
author: "github-aw-spec"
|
|
8
|
-
source: "templates/commands/taskstoissues.md"
|
|
9
|
-
user-invocable: true
|
|
10
|
-
disable-model-invocation: false
|
|
11
|
-
---
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
## User Input
|
|
15
|
-
|
|
16
|
-
```text
|
|
17
|
-
$ARGUMENTS
|
|
18
|
-
```
|
|
19
|
-
|
|
20
|
-
You **MUST** consider the user input before proceeding (if not empty).
|
|
21
|
-
|
|
22
|
-
## Pre-Execution Checks
|
|
23
|
-
|
|
24
|
-
**Check for extension hooks (before tasks-to-issues conversion)**:
|
|
25
|
-
- Check if `.aw-spec/extensions.yml` exists in the project root.
|
|
26
|
-
- If it exists, read it and look for entries under the `hooks.before_taskstoissues` key
|
|
27
|
-
- If the YAML cannot be parsed or is invalid, skip hook checking silently and continue normally
|
|
28
|
-
- Filter out hooks where `enabled` is explicitly `false`. Treat hooks without an `enabled` field as enabled by default.
|
|
29
|
-
- For each remaining hook, do **not** attempt to interpret or evaluate hook `condition` expressions:
|
|
30
|
-
- If the hook has no `condition` field, or it is null/empty, treat the hook as executable
|
|
31
|
-
- If the hook defines a non-empty `condition`, skip the hook and leave condition evaluation to the HookExecutor implementation
|
|
32
|
-
- When constructing slash commands from hook command names, replace dots (`.`) with hyphens (`-`). For example, `aw-spec.git.commit` → `/aw-spec-git-commit`.
|
|
33
|
-
- For each executable hook, output the following based on its `optional` flag:
|
|
34
|
-
- **Optional hook** (`optional: true`):
|
|
35
|
-
```
|
|
36
|
-
## Extension Hooks
|
|
37
|
-
|
|
38
|
-
**Optional Pre-Hook**: {extension}
|
|
39
|
-
Command: `/{command}`
|
|
40
|
-
Description: {description}
|
|
41
|
-
|
|
42
|
-
Prompt: {prompt}
|
|
43
|
-
To execute: `/{command}`
|
|
44
|
-
```
|
|
45
|
-
- **Mandatory hook** (`optional: false`):
|
|
46
|
-
```
|
|
47
|
-
## Extension Hooks
|
|
48
|
-
|
|
49
|
-
**Automatic Pre-Hook**: {extension}
|
|
50
|
-
Executing: `/{command}`
|
|
51
|
-
EXECUTE_COMMAND: {command}
|
|
52
|
-
|
|
53
|
-
Wait for the result of the hook command before proceeding to the Outline.
|
|
54
|
-
```
|
|
55
|
-
- If no hooks are registered or `.aw-spec/extensions.yml` does not exist, skip silently
|
|
56
|
-
|
|
57
|
-
## Outline
|
|
58
|
-
|
|
59
|
-
1. Run `.aw-spec/scripts/bash/check-prerequisites.sh --json --require-tasks --include-tasks` from repo root and parse FEATURE_DIR and AVAILABLE_DOCS list. All paths must be absolute. For single quotes in args like "I'm Groot", use escape syntax: e.g 'I'\''m Groot' (or double-quote if possible: "I'm Groot").
|
|
60
|
-
1. **IF EXISTS**: Load `.aw-spec/memory/constitution.md` for project principles and governance constraints.
|
|
61
|
-
1. From the executed script, extract the path to **tasks**.
|
|
62
|
-
1. Get the Git remote by running:
|
|
63
|
-
|
|
64
|
-
```bash
|
|
65
|
-
git config --get remote.origin.url
|
|
66
|
-
```
|
|
67
|
-
|
|
68
|
-
> [!CAUTION]
|
|
69
|
-
> ONLY PROCEED TO NEXT STEPS IF THE REMOTE IS A GITHUB URL
|
|
70
|
-
|
|
71
|
-
1. For each task in the list, use the GitHub MCP server to create a new issue in the repository that is representative of the Git remote.
|
|
72
|
-
|
|
73
|
-
> [!CAUTION]
|
|
74
|
-
> UNDER NO CIRCUMSTANCES EVER CREATE ISSUES IN REPOSITORIES THAT DO NOT MATCH THE REMOTE URL
|
|
75
|
-
|
|
76
|
-
## Post-Execution Checks
|
|
77
|
-
|
|
78
|
-
**Check for extension hooks (after tasks-to-issues conversion)**:
|
|
79
|
-
Check if `.aw-spec/extensions.yml` exists in the project root.
|
|
80
|
-
- If it exists, read it and look for entries under the `hooks.after_taskstoissues` key
|
|
81
|
-
- If the YAML cannot be parsed or is invalid, skip hook checking silently and continue normally
|
|
82
|
-
- Filter out hooks where `enabled` is explicitly `false`. Treat hooks without an `enabled` field as enabled by default.
|
|
83
|
-
- For each remaining hook, do **not** attempt to interpret or evaluate hook `condition` expressions:
|
|
84
|
-
- If the hook has no `condition` field, or it is null/empty, treat the hook as executable
|
|
85
|
-
- If the hook defines a non-empty `condition`, skip the hook and leave condition evaluation to the HookExecutor implementation
|
|
86
|
-
- When constructing slash commands from hook command names, replace dots (`.`) with hyphens (`-`). For example, `aw-spec.git.commit` → `/aw-spec-git-commit`.
|
|
87
|
-
- For each executable hook, output the following based on its `optional` flag:
|
|
88
|
-
- **Optional hook** (`optional: true`):
|
|
89
|
-
```
|
|
90
|
-
## Extension Hooks
|
|
91
|
-
|
|
92
|
-
**Optional Hook**: {extension}
|
|
93
|
-
Command: `/{command}`
|
|
94
|
-
Description: {description}
|
|
95
|
-
|
|
96
|
-
Prompt: {prompt}
|
|
97
|
-
To execute: `/{command}`
|
|
98
|
-
```
|
|
99
|
-
- **Mandatory hook** (`optional: false`):
|
|
100
|
-
```
|
|
101
|
-
## Extension Hooks
|
|
102
|
-
|
|
103
|
-
**Automatic Hook**: {extension}
|
|
104
|
-
Executing: `/{command}`
|
|
105
|
-
EXECUTE_COMMAND: {command}
|
|
106
|
-
```
|
|
107
|
-
- If no hooks are registered or `.aw-spec/extensions.yml` does not exist, skip silently
|
|
@@ -1,17 +0,0 @@
|
|
|
1
|
-
{
|
|
2
|
-
"integration": "claude",
|
|
3
|
-
"version": "0.10.1",
|
|
4
|
-
"installed_at": "2026-06-10T07:39:01.929414+00:00",
|
|
5
|
-
"files": {
|
|
6
|
-
".claude/skills/aw-spec-analyze/SKILL.md": "9b8caa25a53ba97ddcfc993b5f304990468e29aa0bf1e397f534c7a0a54678ab",
|
|
7
|
-
".claude/skills/aw-spec-clarify/SKILL.md": "fc52a87c6a851c5cdb1451c766c6c71619554b35d219071c74214a4f4cc33d8a",
|
|
8
|
-
".claude/skills/aw-spec-constitution/SKILL.md": "cbe4e06a11cbf92bdb39bcf2a3000717f33556c751ad5666bfefcc2811851bf6",
|
|
9
|
-
".claude/skills/aw-spec-implement/SKILL.md": "6018e531dd7d366318d107fba44ad36881e0ce3649a93365292eedb713203710",
|
|
10
|
-
".claude/skills/aw-spec-plan/SKILL.md": "93b68cc5219333a9588813830ed6a61904f8f470bd0c5b01419b5b31b923b433",
|
|
11
|
-
".claude/skills/aw-spec-checklist/SKILL.md": "7e223721a3c43e1083a018af3ced3297b3c1486468a158b29f09a85b4f2a6e2b",
|
|
12
|
-
".claude/skills/aw-spec-specify/SKILL.md": "823f6ebe99d1f7b7f5e29754a16c0fa6e8be36087aa97344ddb61a22e54dac79",
|
|
13
|
-
".claude/skills/aw-spec-tasks/SKILL.md": "8c2ff9da9e93603484ac4ef077dd0c67b7b51253315e71fbdc334924e145a03e",
|
|
14
|
-
".claude/skills/aw-spec-taskstoissues/SKILL.md": "41e708e04a8449a2ee27cdbffb19b0fbb8596ef0862611e827afb1372056c23f",
|
|
15
|
-
".claude/skills/aw-spec-select-domain/SKILL.md": "07cbbc12dcbad9c2d0342fde853c4338eb91c9c818586f75aa291f6ebcf59eca"
|
|
16
|
-
}
|
|
17
|
-
}
|
|
@@ -1,189 +0,0 @@
|
|
|
1
|
-
#!/usr/bin/env bash
|
|
2
|
-
|
|
3
|
-
# Consolidated prerequisite checking script
|
|
4
|
-
#
|
|
5
|
-
# This script provides unified prerequisite checking for Spec-Driven Development workflow.
|
|
6
|
-
# It replaces the functionality previously spread across multiple scripts.
|
|
7
|
-
#
|
|
8
|
-
# Usage: ./check-prerequisites.sh [OPTIONS]
|
|
9
|
-
#
|
|
10
|
-
# OPTIONS:
|
|
11
|
-
# --json Output in JSON format
|
|
12
|
-
# --require-tasks Require tasks.md to exist (for implementation phase)
|
|
13
|
-
# --include-tasks Include tasks.md in AVAILABLE_DOCS list
|
|
14
|
-
# --paths-only Only output path variables (no validation)
|
|
15
|
-
# --help, -h Show help message
|
|
16
|
-
#
|
|
17
|
-
# OUTPUTS:
|
|
18
|
-
# JSON mode: {"FEATURE_DIR":"...", "AVAILABLE_DOCS":["..."]}
|
|
19
|
-
# Text mode: FEATURE_DIR:... \n AVAILABLE_DOCS: \n ✓/✗ file.md
|
|
20
|
-
# Paths only: REPO_ROOT: ... \n BRANCH: ... \n FEATURE_DIR: ... etc.
|
|
21
|
-
|
|
22
|
-
set -e
|
|
23
|
-
|
|
24
|
-
# Parse command line arguments
|
|
25
|
-
JSON_MODE=false
|
|
26
|
-
REQUIRE_TASKS=false
|
|
27
|
-
INCLUDE_TASKS=false
|
|
28
|
-
PATHS_ONLY=false
|
|
29
|
-
|
|
30
|
-
for arg in "$@"; do
|
|
31
|
-
case "$arg" in
|
|
32
|
-
--json)
|
|
33
|
-
JSON_MODE=true
|
|
34
|
-
;;
|
|
35
|
-
--require-tasks)
|
|
36
|
-
REQUIRE_TASKS=true
|
|
37
|
-
;;
|
|
38
|
-
--include-tasks)
|
|
39
|
-
INCLUDE_TASKS=true
|
|
40
|
-
;;
|
|
41
|
-
--paths-only)
|
|
42
|
-
PATHS_ONLY=true
|
|
43
|
-
;;
|
|
44
|
-
--help|-h)
|
|
45
|
-
cat << 'EOF'
|
|
46
|
-
Usage: check-prerequisites.sh [OPTIONS]
|
|
47
|
-
|
|
48
|
-
Consolidated prerequisite checking for Spec-Driven Development workflow.
|
|
49
|
-
|
|
50
|
-
OPTIONS:
|
|
51
|
-
--json Output in JSON format
|
|
52
|
-
--require-tasks Require tasks.md to exist (for implementation phase)
|
|
53
|
-
--include-tasks Include tasks.md in AVAILABLE_DOCS list
|
|
54
|
-
--paths-only Only output path variables (no prerequisite validation)
|
|
55
|
-
--help, -h Show this help message
|
|
56
|
-
|
|
57
|
-
EXAMPLES:
|
|
58
|
-
# Check task prerequisites (plan.md required)
|
|
59
|
-
./check-prerequisites.sh --json
|
|
60
|
-
|
|
61
|
-
# Check implementation prerequisites (plan.md + tasks.md required)
|
|
62
|
-
./check-prerequisites.sh --json --require-tasks --include-tasks
|
|
63
|
-
|
|
64
|
-
# Get feature paths only (no validation)
|
|
65
|
-
./check-prerequisites.sh --paths-only
|
|
66
|
-
|
|
67
|
-
EOF
|
|
68
|
-
exit 0
|
|
69
|
-
;;
|
|
70
|
-
*)
|
|
71
|
-
echo "ERROR: Unknown option '$arg'. Use --help for usage information." >&2
|
|
72
|
-
exit 1
|
|
73
|
-
;;
|
|
74
|
-
esac
|
|
75
|
-
done
|
|
76
|
-
|
|
77
|
-
# Source common functions
|
|
78
|
-
SCRIPT_DIR="$(CDPATH="" cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
|
79
|
-
source "$SCRIPT_DIR/common.sh"
|
|
80
|
-
|
|
81
|
-
# Get feature paths
|
|
82
|
-
_paths_output=$(get_feature_paths) || { echo "ERROR: Failed to resolve feature paths" >&2; exit 1; }
|
|
83
|
-
eval "$_paths_output"
|
|
84
|
-
unset _paths_output
|
|
85
|
-
|
|
86
|
-
# If paths-only mode, output paths and exit (no validation)
|
|
87
|
-
if $PATHS_ONLY; then
|
|
88
|
-
if $JSON_MODE; then
|
|
89
|
-
# Minimal JSON paths payload (no validation performed)
|
|
90
|
-
if has_jq; then
|
|
91
|
-
jq -cn \
|
|
92
|
-
--arg repo_root "$REPO_ROOT" \
|
|
93
|
-
--arg branch "$CURRENT_BRANCH" \
|
|
94
|
-
--arg feature_dir "$FEATURE_DIR" \
|
|
95
|
-
--arg feature_spec "$FEATURE_SPEC" \
|
|
96
|
-
--arg impl_plan "$IMPL_PLAN" \
|
|
97
|
-
--arg tasks "$TASKS" \
|
|
98
|
-
'{REPO_ROOT:$repo_root,BRANCH:$branch,FEATURE_DIR:$feature_dir,FEATURE_SPEC:$feature_spec,IMPL_PLAN:$impl_plan,TASKS:$tasks}'
|
|
99
|
-
else
|
|
100
|
-
printf '{"REPO_ROOT":"%s","BRANCH":"%s","FEATURE_DIR":"%s","FEATURE_SPEC":"%s","IMPL_PLAN":"%s","TASKS":"%s"}\n' \
|
|
101
|
-
"$(json_escape "$REPO_ROOT")" "$(json_escape "$CURRENT_BRANCH")" "$(json_escape "$FEATURE_DIR")" "$(json_escape "$FEATURE_SPEC")" "$(json_escape "$IMPL_PLAN")" "$(json_escape "$TASKS")"
|
|
102
|
-
fi
|
|
103
|
-
else
|
|
104
|
-
echo "REPO_ROOT: $REPO_ROOT"
|
|
105
|
-
echo "BRANCH: $CURRENT_BRANCH"
|
|
106
|
-
echo "FEATURE_DIR: $FEATURE_DIR"
|
|
107
|
-
echo "FEATURE_SPEC: $FEATURE_SPEC"
|
|
108
|
-
echo "IMPL_PLAN: $IMPL_PLAN"
|
|
109
|
-
echo "TASKS: $TASKS"
|
|
110
|
-
fi
|
|
111
|
-
exit 0
|
|
112
|
-
fi
|
|
113
|
-
|
|
114
|
-
# Validate required directories and files
|
|
115
|
-
if [[ ! -d "$FEATURE_DIR" ]]; then
|
|
116
|
-
echo "ERROR: Feature directory not found: $FEATURE_DIR" >&2
|
|
117
|
-
echo "Run /aw-spec-specify first to create the feature structure." >&2
|
|
118
|
-
exit 1
|
|
119
|
-
fi
|
|
120
|
-
|
|
121
|
-
if [[ ! -f "$IMPL_PLAN" ]]; then
|
|
122
|
-
echo "ERROR: plan.md not found in $FEATURE_DIR" >&2
|
|
123
|
-
echo "Run /aw-spec-plan first to create the implementation plan." >&2
|
|
124
|
-
exit 1
|
|
125
|
-
fi
|
|
126
|
-
|
|
127
|
-
# Check for tasks.md if required
|
|
128
|
-
if $REQUIRE_TASKS && [[ ! -f "$TASKS" ]]; then
|
|
129
|
-
echo "ERROR: tasks.md not found in $FEATURE_DIR" >&2
|
|
130
|
-
echo "Run /aw-spec-tasks first to create the task list." >&2
|
|
131
|
-
exit 1
|
|
132
|
-
fi
|
|
133
|
-
|
|
134
|
-
# Build list of available documents
|
|
135
|
-
docs=()
|
|
136
|
-
|
|
137
|
-
# Always check these optional docs
|
|
138
|
-
[[ -f "$RESEARCH" ]] && docs+=("research.md")
|
|
139
|
-
[[ -f "$DATA_MODEL" ]] && docs+=("data-model.md")
|
|
140
|
-
|
|
141
|
-
# Check contracts directory (only if it exists and has files)
|
|
142
|
-
if [[ -d "$CONTRACTS_DIR" ]] && [[ -n "$(ls -A "$CONTRACTS_DIR" 2>/dev/null)" ]]; then
|
|
143
|
-
docs+=("contracts/")
|
|
144
|
-
fi
|
|
145
|
-
|
|
146
|
-
[[ -f "$QUICKSTART" ]] && docs+=("quickstart.md")
|
|
147
|
-
|
|
148
|
-
# Include tasks.md if requested and it exists
|
|
149
|
-
if $INCLUDE_TASKS && [[ -f "$TASKS" ]]; then
|
|
150
|
-
docs+=("tasks.md")
|
|
151
|
-
fi
|
|
152
|
-
|
|
153
|
-
# Output results
|
|
154
|
-
if $JSON_MODE; then
|
|
155
|
-
# Build JSON array of documents
|
|
156
|
-
if has_jq; then
|
|
157
|
-
if [[ ${#docs[@]} -eq 0 ]]; then
|
|
158
|
-
json_docs="[]"
|
|
159
|
-
else
|
|
160
|
-
json_docs=$(printf '%s\n' "${docs[@]}" | jq -R . | jq -s .)
|
|
161
|
-
fi
|
|
162
|
-
jq -cn \
|
|
163
|
-
--arg feature_dir "$FEATURE_DIR" \
|
|
164
|
-
--argjson docs "$json_docs" \
|
|
165
|
-
'{FEATURE_DIR:$feature_dir,AVAILABLE_DOCS:$docs}'
|
|
166
|
-
else
|
|
167
|
-
if [[ ${#docs[@]} -eq 0 ]]; then
|
|
168
|
-
json_docs="[]"
|
|
169
|
-
else
|
|
170
|
-
json_docs=$(for d in "${docs[@]}"; do printf '"%s",' "$(json_escape "$d")"; done)
|
|
171
|
-
json_docs="[${json_docs%,}]"
|
|
172
|
-
fi
|
|
173
|
-
printf '{"FEATURE_DIR":"%s","AVAILABLE_DOCS":%s}\n' "$(json_escape "$FEATURE_DIR")" "$json_docs"
|
|
174
|
-
fi
|
|
175
|
-
else
|
|
176
|
-
# Text output
|
|
177
|
-
echo "FEATURE_DIR:$FEATURE_DIR"
|
|
178
|
-
echo "AVAILABLE_DOCS:"
|
|
179
|
-
|
|
180
|
-
# Show status of each potential document
|
|
181
|
-
check_file "$RESEARCH" "research.md"
|
|
182
|
-
check_file "$DATA_MODEL" "data-model.md"
|
|
183
|
-
check_dir "$CONTRACTS_DIR" "contracts/"
|
|
184
|
-
check_file "$QUICKSTART" "quickstart.md"
|
|
185
|
-
|
|
186
|
-
if $INCLUDE_TASKS; then
|
|
187
|
-
check_file "$TASKS" "tasks.md"
|
|
188
|
-
fi
|
|
189
|
-
fi
|
|
@@ -1,299 +0,0 @@
|
|
|
1
|
-
#!/usr/bin/env bash
|
|
2
|
-
|
|
3
|
-
set -e
|
|
4
|
-
|
|
5
|
-
JSON_MODE=false
|
|
6
|
-
DRY_RUN=false
|
|
7
|
-
ALLOW_EXISTING=false
|
|
8
|
-
SHORT_NAME=""
|
|
9
|
-
BRANCH_NUMBER=""
|
|
10
|
-
USE_TIMESTAMP=false
|
|
11
|
-
ARGS=()
|
|
12
|
-
i=1
|
|
13
|
-
while [ $i -le $# ]; do
|
|
14
|
-
arg="${!i}"
|
|
15
|
-
case "$arg" in
|
|
16
|
-
--json)
|
|
17
|
-
JSON_MODE=true
|
|
18
|
-
;;
|
|
19
|
-
--dry-run)
|
|
20
|
-
DRY_RUN=true
|
|
21
|
-
;;
|
|
22
|
-
--allow-existing-branch)
|
|
23
|
-
ALLOW_EXISTING=true
|
|
24
|
-
;;
|
|
25
|
-
--short-name)
|
|
26
|
-
if [ $((i + 1)) -gt $# ]; then
|
|
27
|
-
echo 'Error: --short-name requires a value' >&2
|
|
28
|
-
exit 1
|
|
29
|
-
fi
|
|
30
|
-
i=$((i + 1))
|
|
31
|
-
next_arg="${!i}"
|
|
32
|
-
# Check if the next argument is another option (starts with --)
|
|
33
|
-
if [[ "$next_arg" == --* ]]; then
|
|
34
|
-
echo 'Error: --short-name requires a value' >&2
|
|
35
|
-
exit 1
|
|
36
|
-
fi
|
|
37
|
-
SHORT_NAME="$next_arg"
|
|
38
|
-
;;
|
|
39
|
-
--number)
|
|
40
|
-
if [ $((i + 1)) -gt $# ]; then
|
|
41
|
-
echo 'Error: --number requires a value' >&2
|
|
42
|
-
exit 1
|
|
43
|
-
fi
|
|
44
|
-
i=$((i + 1))
|
|
45
|
-
next_arg="${!i}"
|
|
46
|
-
if [[ "$next_arg" == --* ]]; then
|
|
47
|
-
echo 'Error: --number requires a value' >&2
|
|
48
|
-
exit 1
|
|
49
|
-
fi
|
|
50
|
-
BRANCH_NUMBER="$next_arg"
|
|
51
|
-
;;
|
|
52
|
-
--timestamp)
|
|
53
|
-
USE_TIMESTAMP=true
|
|
54
|
-
;;
|
|
55
|
-
--help|-h)
|
|
56
|
-
echo "Usage: $0 [--json] [--dry-run] [--allow-existing-branch] [--short-name <name>] [--number N] [--timestamp] <feature_description>"
|
|
57
|
-
echo ""
|
|
58
|
-
echo "Options:"
|
|
59
|
-
echo " --json Output in JSON format"
|
|
60
|
-
echo " --dry-run Compute feature name and paths without creating directories or files"
|
|
61
|
-
echo " --allow-existing-branch Reuse an existing feature directory if it already exists"
|
|
62
|
-
echo " --short-name <name> Provide a custom short name (2-4 words) for the feature"
|
|
63
|
-
echo " --number N Specify branch number manually (overrides auto-detection)"
|
|
64
|
-
echo " --timestamp Use timestamp prefix (YYYYMMDD-HHMMSS) instead of sequential numbering"
|
|
65
|
-
echo " --help, -h Show this help message"
|
|
66
|
-
echo ""
|
|
67
|
-
echo "Examples:"
|
|
68
|
-
echo " $0 'Add user authentication system' --short-name 'user-auth'"
|
|
69
|
-
echo " $0 'Implement OAuth2 integration for API' --number 5"
|
|
70
|
-
echo " $0 --timestamp --short-name 'user-auth' 'Add user authentication'"
|
|
71
|
-
exit 0
|
|
72
|
-
;;
|
|
73
|
-
*)
|
|
74
|
-
ARGS+=("$arg")
|
|
75
|
-
;;
|
|
76
|
-
esac
|
|
77
|
-
i=$((i + 1))
|
|
78
|
-
done
|
|
79
|
-
|
|
80
|
-
FEATURE_DESCRIPTION="${ARGS[*]}"
|
|
81
|
-
if [ -z "$FEATURE_DESCRIPTION" ]; then
|
|
82
|
-
echo "Usage: $0 [--json] [--dry-run] [--allow-existing-branch] [--short-name <name>] [--number N] [--timestamp] <feature_description>" >&2
|
|
83
|
-
exit 1
|
|
84
|
-
fi
|
|
85
|
-
|
|
86
|
-
# Trim whitespace and validate description is not empty (e.g., user passed only whitespace)
|
|
87
|
-
FEATURE_DESCRIPTION=$(echo "$FEATURE_DESCRIPTION" | sed -E 's/^[[:space:]]+|[[:space:]]+$//g')
|
|
88
|
-
if [ -z "$FEATURE_DESCRIPTION" ]; then
|
|
89
|
-
echo "Error: Feature description cannot be empty or contain only whitespace" >&2
|
|
90
|
-
exit 1
|
|
91
|
-
fi
|
|
92
|
-
|
|
93
|
-
# Function to get highest number from specs directory
|
|
94
|
-
get_highest_from_specs() {
|
|
95
|
-
local specs_dir="$1"
|
|
96
|
-
local highest=0
|
|
97
|
-
|
|
98
|
-
if [ -d "$specs_dir" ]; then
|
|
99
|
-
for dir in "$specs_dir"/*; do
|
|
100
|
-
[ -d "$dir" ] || continue
|
|
101
|
-
dirname=$(basename "$dir")
|
|
102
|
-
# Match sequential prefixes (>=3 digits), but skip timestamp dirs.
|
|
103
|
-
if echo "$dirname" | grep -Eq '^[0-9]{3,}-' && ! echo "$dirname" | grep -Eq '^[0-9]{8}-[0-9]{6}-'; then
|
|
104
|
-
number=$(echo "$dirname" | grep -Eo '^[0-9]+')
|
|
105
|
-
number=$((10#$number))
|
|
106
|
-
if [ "$number" -gt "$highest" ]; then
|
|
107
|
-
highest=$number
|
|
108
|
-
fi
|
|
109
|
-
fi
|
|
110
|
-
done
|
|
111
|
-
fi
|
|
112
|
-
|
|
113
|
-
echo "$highest"
|
|
114
|
-
}
|
|
115
|
-
|
|
116
|
-
# Function to clean and format a branch name
|
|
117
|
-
clean_branch_name() {
|
|
118
|
-
local name="$1"
|
|
119
|
-
echo "$name" | tr '[:upper:]' '[:lower:]' | sed 's/[^a-z0-9]/-/g' | sed 's/-\+/-/g' | sed 's/^-//' | sed 's/-$//'
|
|
120
|
-
}
|
|
121
|
-
|
|
122
|
-
# Resolve repository root using common.sh functions which prioritize .aw-spec
|
|
123
|
-
SCRIPT_DIR="$(CDPATH="" cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
|
124
|
-
source "$SCRIPT_DIR/common.sh"
|
|
125
|
-
|
|
126
|
-
REPO_ROOT=$(get_repo_root)
|
|
127
|
-
|
|
128
|
-
cd "$REPO_ROOT"
|
|
129
|
-
|
|
130
|
-
SPECS_DIR="$REPO_ROOT/specs"
|
|
131
|
-
if [ "$DRY_RUN" != true ]; then
|
|
132
|
-
mkdir -p "$SPECS_DIR"
|
|
133
|
-
fi
|
|
134
|
-
|
|
135
|
-
# Function to generate branch name with stop word filtering and length filtering
|
|
136
|
-
generate_branch_name() {
|
|
137
|
-
local description="$1"
|
|
138
|
-
|
|
139
|
-
# Common stop words to filter out
|
|
140
|
-
local stop_words="^(i|a|an|the|to|for|of|in|on|at|by|with|from|is|are|was|were|be|been|being|have|has|had|do|does|did|will|would|should|could|can|may|might|must|shall|this|that|these|those|my|your|our|their|want|need|add|get|set)$"
|
|
141
|
-
|
|
142
|
-
# Convert to lowercase and split into words
|
|
143
|
-
local clean_name=$(echo "$description" | tr '[:upper:]' '[:lower:]' | sed 's/[^a-z0-9]/ /g')
|
|
144
|
-
|
|
145
|
-
# Filter words: remove stop words and words shorter than 3 chars (unless they're uppercase acronyms in original)
|
|
146
|
-
local meaningful_words=()
|
|
147
|
-
for word in $clean_name; do
|
|
148
|
-
# Skip empty words
|
|
149
|
-
[ -z "$word" ] && continue
|
|
150
|
-
|
|
151
|
-
# Keep words that are NOT stop words AND (length >= 3 OR are potential acronyms)
|
|
152
|
-
if ! echo "$word" | grep -qiE "$stop_words"; then
|
|
153
|
-
if [ ${#word} -ge 3 ]; then
|
|
154
|
-
meaningful_words+=("$word")
|
|
155
|
-
elif echo "$description" | grep -q "\b${word^^}\b"; then
|
|
156
|
-
# Keep short words if they appear as uppercase in original (likely acronyms)
|
|
157
|
-
meaningful_words+=("$word")
|
|
158
|
-
fi
|
|
159
|
-
fi
|
|
160
|
-
done
|
|
161
|
-
|
|
162
|
-
# If we have meaningful words, use first 3-4 of them
|
|
163
|
-
if [ ${#meaningful_words[@]} -gt 0 ]; then
|
|
164
|
-
local max_words=3
|
|
165
|
-
if [ ${#meaningful_words[@]} -eq 4 ]; then max_words=4; fi
|
|
166
|
-
|
|
167
|
-
local result=""
|
|
168
|
-
local count=0
|
|
169
|
-
for word in "${meaningful_words[@]}"; do
|
|
170
|
-
if [ $count -ge $max_words ]; then break; fi
|
|
171
|
-
if [ -n "$result" ]; then result="$result-"; fi
|
|
172
|
-
result="$result$word"
|
|
173
|
-
count=$((count + 1))
|
|
174
|
-
done
|
|
175
|
-
echo "$result"
|
|
176
|
-
else
|
|
177
|
-
# Fallback to original logic if no meaningful words found
|
|
178
|
-
local cleaned=$(clean_branch_name "$description")
|
|
179
|
-
echo "$cleaned" | tr '-' '\n' | grep -v '^$' | head -3 | tr '\n' '-' | sed 's/-$//'
|
|
180
|
-
fi
|
|
181
|
-
}
|
|
182
|
-
|
|
183
|
-
# Generate branch name
|
|
184
|
-
if [ -n "$SHORT_NAME" ]; then
|
|
185
|
-
# Use provided short name, just clean it up
|
|
186
|
-
BRANCH_SUFFIX=$(clean_branch_name "$SHORT_NAME")
|
|
187
|
-
else
|
|
188
|
-
# Generate from description with smart filtering
|
|
189
|
-
BRANCH_SUFFIX=$(generate_branch_name "$FEATURE_DESCRIPTION")
|
|
190
|
-
fi
|
|
191
|
-
|
|
192
|
-
# Warn if --number and --timestamp are both specified
|
|
193
|
-
if [ "$USE_TIMESTAMP" = true ] && [ -n "$BRANCH_NUMBER" ]; then
|
|
194
|
-
>&2 echo "[specify] Warning: --number is ignored when --timestamp is used"
|
|
195
|
-
BRANCH_NUMBER=""
|
|
196
|
-
fi
|
|
197
|
-
|
|
198
|
-
# Determine branch prefix
|
|
199
|
-
if [ "$USE_TIMESTAMP" = true ]; then
|
|
200
|
-
FEATURE_NUM=$(date +%Y%m%d-%H%M%S)
|
|
201
|
-
BRANCH_NAME="${FEATURE_NUM}-${BRANCH_SUFFIX}"
|
|
202
|
-
else
|
|
203
|
-
# Determine branch number from existing feature directories
|
|
204
|
-
if [ -z "$BRANCH_NUMBER" ]; then
|
|
205
|
-
HIGHEST=$(get_highest_from_specs "$SPECS_DIR")
|
|
206
|
-
BRANCH_NUMBER=$((HIGHEST + 1))
|
|
207
|
-
fi
|
|
208
|
-
|
|
209
|
-
# Force base-10 interpretation to prevent octal conversion (e.g., 010 → 8 in octal, but should be 10 in decimal)
|
|
210
|
-
FEATURE_NUM=$(printf "%03d" "$((10#$BRANCH_NUMBER))")
|
|
211
|
-
BRANCH_NAME="${FEATURE_NUM}-${BRANCH_SUFFIX}"
|
|
212
|
-
fi
|
|
213
|
-
|
|
214
|
-
# GitHub enforces a 244-byte limit on branch names
|
|
215
|
-
# Validate and truncate if necessary
|
|
216
|
-
MAX_BRANCH_LENGTH=244
|
|
217
|
-
if [ ${#BRANCH_NAME} -gt $MAX_BRANCH_LENGTH ]; then
|
|
218
|
-
# Calculate how much we need to trim from suffix
|
|
219
|
-
# Account for prefix length: timestamp (15) + hyphen (1) = 16, or sequential (3) + hyphen (1) = 4
|
|
220
|
-
PREFIX_LENGTH=$(( ${#FEATURE_NUM} + 1 ))
|
|
221
|
-
MAX_SUFFIX_LENGTH=$((MAX_BRANCH_LENGTH - PREFIX_LENGTH))
|
|
222
|
-
|
|
223
|
-
# Truncate suffix at word boundary if possible
|
|
224
|
-
TRUNCATED_SUFFIX=$(echo "$BRANCH_SUFFIX" | cut -c1-$MAX_SUFFIX_LENGTH)
|
|
225
|
-
# Remove trailing hyphen if truncation created one
|
|
226
|
-
TRUNCATED_SUFFIX=$(echo "$TRUNCATED_SUFFIX" | sed 's/-$//')
|
|
227
|
-
|
|
228
|
-
ORIGINAL_BRANCH_NAME="$BRANCH_NAME"
|
|
229
|
-
BRANCH_NAME="${FEATURE_NUM}-${TRUNCATED_SUFFIX}"
|
|
230
|
-
|
|
231
|
-
>&2 echo "[specify] Warning: Branch name exceeded GitHub's 244-byte limit"
|
|
232
|
-
>&2 echo "[specify] Original: $ORIGINAL_BRANCH_NAME (${#ORIGINAL_BRANCH_NAME} bytes)"
|
|
233
|
-
>&2 echo "[specify] Truncated to: $BRANCH_NAME (${#BRANCH_NAME} bytes)"
|
|
234
|
-
fi
|
|
235
|
-
|
|
236
|
-
FEATURE_DIR="$SPECS_DIR/$BRANCH_NAME"
|
|
237
|
-
SPEC_FILE="$FEATURE_DIR/spec.md"
|
|
238
|
-
|
|
239
|
-
if [ "$DRY_RUN" != true ]; then
|
|
240
|
-
if [ -d "$FEATURE_DIR" ] && [ "$ALLOW_EXISTING" != true ]; then
|
|
241
|
-
if [ "$USE_TIMESTAMP" = true ]; then
|
|
242
|
-
>&2 echo "Error: Feature directory '$FEATURE_DIR' already exists. Rerun to get a new timestamp or use a different --short-name."
|
|
243
|
-
else
|
|
244
|
-
>&2 echo "Error: Feature directory '$FEATURE_DIR' already exists. Please use a different feature name or specify a different number with --number."
|
|
245
|
-
fi
|
|
246
|
-
exit 1
|
|
247
|
-
fi
|
|
248
|
-
|
|
249
|
-
mkdir -p "$FEATURE_DIR"
|
|
250
|
-
|
|
251
|
-
if [ ! -f "$SPEC_FILE" ]; then
|
|
252
|
-
TEMPLATE=$(resolve_template "spec-template" "$REPO_ROOT") || true
|
|
253
|
-
if [ -n "$TEMPLATE" ] && [ -f "$TEMPLATE" ]; then
|
|
254
|
-
cp "$TEMPLATE" "$SPEC_FILE"
|
|
255
|
-
else
|
|
256
|
-
echo "Warning: Spec template not found; created empty spec file" >&2
|
|
257
|
-
touch "$SPEC_FILE"
|
|
258
|
-
fi
|
|
259
|
-
fi
|
|
260
|
-
|
|
261
|
-
# Persist to .aw-spec/feature.json so downstream commands can find the feature
|
|
262
|
-
_persist_feature_json "$REPO_ROOT" "$FEATURE_DIR"
|
|
263
|
-
|
|
264
|
-
# Inform the user how to set feature state in their own shell
|
|
265
|
-
printf '# To persist: export SPECIFY_FEATURE=%q\n' "$BRANCH_NAME" >&2
|
|
266
|
-
printf '# export SPECIFY_FEATURE_DIRECTORY=%q\n' "$FEATURE_DIR" >&2
|
|
267
|
-
fi
|
|
268
|
-
|
|
269
|
-
if $JSON_MODE; then
|
|
270
|
-
if command -v jq >/dev/null 2>&1; then
|
|
271
|
-
if [ "$DRY_RUN" = true ]; then
|
|
272
|
-
jq -cn \
|
|
273
|
-
--arg branch_name "$BRANCH_NAME" \
|
|
274
|
-
--arg spec_file "$SPEC_FILE" \
|
|
275
|
-
--arg feature_num "$FEATURE_NUM" \
|
|
276
|
-
'{BRANCH_NAME:$branch_name,SPEC_FILE:$spec_file,FEATURE_NUM:$feature_num,DRY_RUN:true}'
|
|
277
|
-
else
|
|
278
|
-
jq -cn \
|
|
279
|
-
--arg branch_name "$BRANCH_NAME" \
|
|
280
|
-
--arg spec_file "$SPEC_FILE" \
|
|
281
|
-
--arg feature_num "$FEATURE_NUM" \
|
|
282
|
-
'{BRANCH_NAME:$branch_name,SPEC_FILE:$spec_file,FEATURE_NUM:$feature_num}'
|
|
283
|
-
fi
|
|
284
|
-
else
|
|
285
|
-
if [ "$DRY_RUN" = true ]; then
|
|
286
|
-
printf '{"BRANCH_NAME":"%s","SPEC_FILE":"%s","FEATURE_NUM":"%s","DRY_RUN":true}\n' "$(json_escape "$BRANCH_NAME")" "$(json_escape "$SPEC_FILE")" "$(json_escape "$FEATURE_NUM")"
|
|
287
|
-
else
|
|
288
|
-
printf '{"BRANCH_NAME":"%s","SPEC_FILE":"%s","FEATURE_NUM":"%s"}\n' "$(json_escape "$BRANCH_NAME")" "$(json_escape "$SPEC_FILE")" "$(json_escape "$FEATURE_NUM")"
|
|
289
|
-
fi
|
|
290
|
-
fi
|
|
291
|
-
else
|
|
292
|
-
echo "BRANCH_NAME: $BRANCH_NAME"
|
|
293
|
-
echo "SPEC_FILE: $SPEC_FILE"
|
|
294
|
-
echo "FEATURE_NUM: $FEATURE_NUM"
|
|
295
|
-
if [ "$DRY_RUN" != true ]; then
|
|
296
|
-
printf '# To persist in your shell: export SPECIFY_FEATURE=%q\n' "$BRANCH_NAME"
|
|
297
|
-
printf '# export SPECIFY_FEATURE_DIRECTORY=%q\n' "$FEATURE_DIR"
|
|
298
|
-
fi
|
|
299
|
-
fi
|