@nlaprell/shipit 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/.cursor/commands/create_intent_from_issue.md +28 -0
- package/.cursor/commands/create_pr.md +28 -0
- package/.cursor/commands/dashboard.md +39 -0
- package/.cursor/commands/deploy.md +152 -0
- package/.cursor/commands/drift_check.md +36 -0
- package/.cursor/commands/fix.md +39 -0
- package/.cursor/commands/generate_release_plan.md +31 -0
- package/.cursor/commands/generate_roadmap.md +38 -0
- package/.cursor/commands/help.md +37 -0
- package/.cursor/commands/init_project.md +26 -0
- package/.cursor/commands/kill.md +72 -0
- package/.cursor/commands/new_intent.md +68 -0
- package/.cursor/commands/pr.md +77 -0
- package/.cursor/commands/revert-plan.md +58 -0
- package/.cursor/commands/risk.md +64 -0
- package/.cursor/commands/rollback.md +43 -0
- package/.cursor/commands/scope_project.md +53 -0
- package/.cursor/commands/ship.md +345 -0
- package/.cursor/commands/status.md +71 -0
- package/.cursor/commands/suggest.md +44 -0
- package/.cursor/commands/test_shipit.md +197 -0
- package/.cursor/commands/verify.md +50 -0
- package/.cursor/rules/architect.mdc +84 -0
- package/.cursor/rules/assumption-extractor.mdc +95 -0
- package/.cursor/rules/docs.mdc +66 -0
- package/.cursor/rules/implementer.mdc +112 -0
- package/.cursor/rules/pm.mdc +136 -0
- package/.cursor/rules/qa.mdc +97 -0
- package/.cursor/rules/security.mdc +90 -0
- package/.cursor/rules/steward.mdc +99 -0
- package/.cursor/rules/test-runner.mdc +196 -0
- package/AGENTS.md +121 -0
- package/README.md +264 -0
- package/_system/architecture/CANON.md +159 -0
- package/_system/architecture/invariants.yml +87 -0
- package/_system/architecture/project-schema.json +98 -0
- package/_system/architecture/workflow-state-layout.md +68 -0
- package/_system/artifacts/SYSTEM_STATE.md +43 -0
- package/_system/artifacts/confidence-calibration.json +16 -0
- package/_system/artifacts/dependencies.md +46 -0
- package/_system/artifacts/framework-files-manifest.json +179 -0
- package/_system/artifacts/usage.json +1 -0
- package/_system/behaviors/DO_RELEASE.md +371 -0
- package/_system/behaviors/DO_RELEASE_AI.md +329 -0
- package/_system/behaviors/PREPARE_RELEASE.md +373 -0
- package/_system/behaviors/PREPARE_RELEASE_AI.md +234 -0
- package/_system/behaviors/WORK_ROOT_PLATFORM_ISSUES.md +140 -0
- package/_system/behaviors/WORK_TEST_PLAN_ISSUES.md +380 -0
- package/_system/do-not-repeat/abandoned-designs.md +18 -0
- package/_system/do-not-repeat/bad-patterns.md +19 -0
- package/_system/do-not-repeat/failed-experiments.md +18 -0
- package/_system/do-not-repeat/rejected-libraries.md +19 -0
- package/_system/drift/baselines.md +49 -0
- package/_system/drift/metrics.md +33 -0
- package/_system/golden-data/.gitkeep +0 -0
- package/_system/golden-data/README.md +47 -0
- package/_system/reports/mutation/mutation.html +492 -0
- package/_system/security/audit-allowlist.json +4 -0
- package/bin/create-shipit-app +29 -0
- package/bin/shipit +183 -0
- package/cli/src/commands/check.js +82 -0
- package/cli/src/commands/create.js +195 -0
- package/cli/src/commands/init.js +267 -0
- package/cli/src/commands/upgrade.js +196 -0
- package/cli/src/utils/config.js +27 -0
- package/cli/src/utils/file-copy.js +144 -0
- package/cli/src/utils/gitignore-merge.js +44 -0
- package/cli/src/utils/manifest.js +105 -0
- package/cli/src/utils/package-json-merge.js +163 -0
- package/cli/src/utils/project-json-merge.js +57 -0
- package/cli/src/utils/prompts.js +30 -0
- package/cli/src/utils/stack-detection.js +56 -0
- package/cli/src/utils/stack-files.js +364 -0
- package/cli/src/utils/upgrade-backup.js +159 -0
- package/cli/src/utils/version.js +64 -0
- package/dashboard-app/README.md +73 -0
- package/dashboard-app/eslint.config.js +23 -0
- package/dashboard-app/index.html +13 -0
- package/dashboard-app/package.json +30 -0
- package/dashboard-app/pnpm-lock.yaml +2721 -0
- package/dashboard-app/public/dashboard.json +66 -0
- package/dashboard-app/public/vite.svg +1 -0
- package/dashboard-app/src/App.css +141 -0
- package/dashboard-app/src/App.tsx +155 -0
- package/dashboard-app/src/assets/react.svg +1 -0
- package/dashboard-app/src/index.css +68 -0
- package/dashboard-app/src/main.tsx +10 -0
- package/dashboard-app/tsconfig.app.json +28 -0
- package/dashboard-app/tsconfig.json +4 -0
- package/dashboard-app/tsconfig.node.json +26 -0
- package/dashboard-app/vite.config.ts +7 -0
- package/package.json +116 -0
- package/scripts/README.md +70 -0
- package/scripts/audit-check.sh +125 -0
- package/scripts/calibration-report.sh +198 -0
- package/scripts/check-readiness.sh +155 -0
- package/scripts/collect-metrics.sh +116 -0
- package/scripts/command-manifest.yml +131 -0
- package/scripts/create-test-plan-issue.sh +110 -0
- package/scripts/dashboard-start.sh +16 -0
- package/scripts/deploy.sh +170 -0
- package/scripts/drift-check.sh +93 -0
- package/scripts/execute-rollback.sh +177 -0
- package/scripts/export-dashboard-json.js +208 -0
- package/scripts/fix-intents.sh +239 -0
- package/scripts/generate-dashboard.sh +136 -0
- package/scripts/generate-docs.sh +279 -0
- package/scripts/generate-project-context.sh +142 -0
- package/scripts/generate-release-plan.sh +443 -0
- package/scripts/generate-roadmap.sh +189 -0
- package/scripts/generate-system-state.sh +95 -0
- package/scripts/gh/create-intent-from-issue.sh +82 -0
- package/scripts/gh/create-issue-from-intent.sh +59 -0
- package/scripts/gh/create-pr.sh +41 -0
- package/scripts/gh/link-issue.sh +44 -0
- package/scripts/gh/on-ship-update-issue.sh +42 -0
- package/scripts/headless/README.md +8 -0
- package/scripts/headless/call-llm.js +109 -0
- package/scripts/headless/run-phase.sh +99 -0
- package/scripts/help.sh +271 -0
- package/scripts/init-project.sh +976 -0
- package/scripts/kill-intent.sh +125 -0
- package/scripts/lib/common.sh +29 -0
- package/scripts/lib/intent.sh +61 -0
- package/scripts/lib/progress.sh +57 -0
- package/scripts/lib/suggest-next.sh +131 -0
- package/scripts/lib/validate-intents.sh +240 -0
- package/scripts/lib/verify-outputs.sh +55 -0
- package/scripts/lib/workflow_state.sh +201 -0
- package/scripts/new-intent.sh +271 -0
- package/scripts/publish-npm.sh +28 -0
- package/scripts/scope-project.sh +380 -0
- package/scripts/setup-worktrees.sh +125 -0
- package/scripts/status.sh +278 -0
- package/scripts/suggest.sh +173 -0
- package/scripts/test-headless.sh +47 -0
- package/scripts/test-shipit.sh +52 -0
- package/scripts/test-workflow-state.sh +49 -0
- package/scripts/usage-report.sh +47 -0
- package/scripts/usage.sh +58 -0
- package/scripts/validate-cursor.sh +151 -0
- package/scripts/validate-project.sh +71 -0
- package/scripts/validate-vscode.sh +146 -0
- package/scripts/verify.sh +153 -0
- package/scripts/workflow-orchestrator.sh +97 -0
- package/scripts/workflow-templates/01_analysis.md.tpl +25 -0
- package/scripts/workflow-templates/02_plan.md.tpl +30 -0
- package/scripts/workflow-templates/03_implementation.md.tpl +25 -0
- package/scripts/workflow-templates/04_verification.md.tpl +29 -0
- package/scripts/workflow-templates/05_release_notes.md.tpl +16 -0
- package/scripts/workflow-templates/05_verification_legacy.md.tpl +6 -0
- package/scripts/workflow-templates/active.md.tpl +18 -0
- package/scripts/workflow-templates/phases.yml +39 -0
- package/stryker.conf.json +8 -0
- package/work/intent/templates/api-endpoint.md +124 -0
- package/work/intent/templates/bugfix.md +116 -0
- package/work/intent/templates/frontend-feature.md +115 -0
- package/work/intent/templates/generic.md +122 -0
- package/work/intent/templates/infra-change.md +121 -0
- package/work/intent/templates/refactor.md +116 -0
package/scripts/usage.sh
ADDED
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
#!/bin/bash
|
|
2
|
+
|
|
3
|
+
# Record token-usage (or cost) for a phase/intent.
|
|
4
|
+
# Values are estimates unless source is "api" (e.g. from provider response).
|
|
5
|
+
# Usage: usage.sh <intent_id> <phase> <tokens_in> <tokens_out> [estimated_cost_usd] [source]
|
|
6
|
+
# Example: ./scripts/usage.sh F-001 analysis 1500 800
|
|
7
|
+
# Example: ./scripts/usage.sh F-001 plan 2000 1200 0.02 cursor_estimate
|
|
8
|
+
|
|
9
|
+
set -euo pipefail
|
|
10
|
+
|
|
11
|
+
SCRIPT_DIR="$(cd "$(dirname "$0")" && pwd)"
|
|
12
|
+
REPO_ROOT="$(cd "$SCRIPT_DIR/.." && pwd)"
|
|
13
|
+
cd "$REPO_ROOT"
|
|
14
|
+
|
|
15
|
+
# shellcheck source=scripts/lib/common.sh
|
|
16
|
+
. "$SCRIPT_DIR/lib/common.sh"
|
|
17
|
+
|
|
18
|
+
require_cmd jq
|
|
19
|
+
|
|
20
|
+
USAGE_FILE="_system/artifacts/usage.json"
|
|
21
|
+
|
|
22
|
+
if [ $# -lt 4 ]; then
|
|
23
|
+
echo "Usage: $0 <intent_id> <phase> <tokens_in> <tokens_out> [estimated_cost_usd] [source]" >&2
|
|
24
|
+
echo " source: cursor_estimate (default) | api" >&2
|
|
25
|
+
exit 1
|
|
26
|
+
fi
|
|
27
|
+
|
|
28
|
+
INTENT_ID="$1"
|
|
29
|
+
PHASE="$2"
|
|
30
|
+
TOKENS_IN="$3"
|
|
31
|
+
TOKENS_OUT="$4"
|
|
32
|
+
COST="${5:-null}"
|
|
33
|
+
SOURCE="${6:-cursor_estimate}"
|
|
34
|
+
|
|
35
|
+
if ! [[ "$TOKENS_IN" =~ ^[0-9]+$ ]] || ! [[ "$TOKENS_OUT" =~ ^[0-9]+$ ]]; then
|
|
36
|
+
error_exit "tokens_in and tokens_out must be non-negative integers" 1
|
|
37
|
+
fi
|
|
38
|
+
|
|
39
|
+
mkdir -p _system/artifacts
|
|
40
|
+
|
|
41
|
+
if [ ! -f "$USAGE_FILE" ]; then
|
|
42
|
+
echo '{"entries":[]}' > "$USAGE_FILE"
|
|
43
|
+
fi
|
|
44
|
+
|
|
45
|
+
TIMESTAMP_ISO="$(date -u +"%Y-%m-%dT%H:%M:%SZ")"
|
|
46
|
+
NEW_ENTRY=$(jq -n \
|
|
47
|
+
--arg intent_id "$INTENT_ID" \
|
|
48
|
+
--arg phase "$PHASE" \
|
|
49
|
+
--argjson tokens_in "$TOKENS_IN" \
|
|
50
|
+
--argjson tokens_out "$TOKENS_OUT" \
|
|
51
|
+
--argjson cost "$COST" \
|
|
52
|
+
--arg ts "$TIMESTAMP_ISO" \
|
|
53
|
+
--arg source "$SOURCE" \
|
|
54
|
+
'{ intent_id: $intent_id, phase: $phase, tokens_in: $tokens_in, tokens_out: $tokens_out, estimated_cost_usd: $cost, timestamp_iso: $ts, source: $source }')
|
|
55
|
+
|
|
56
|
+
jq --argjson entry "$NEW_ENTRY" '.entries += [$entry]' "$USAGE_FILE" > "$USAGE_FILE.nw" && mv "$USAGE_FILE.nw" "$USAGE_FILE"
|
|
57
|
+
|
|
58
|
+
echo "Recorded: $INTENT_ID $PHASE (in=$TOKENS_IN out=$TOKENS_OUT) source=$SOURCE"
|
|
@@ -0,0 +1,151 @@
|
|
|
1
|
+
#!/bin/bash
|
|
2
|
+
|
|
3
|
+
# Cursor Integration Validation Script
|
|
4
|
+
# Checks if Cursor recognizes .mdc files and slash commands
|
|
5
|
+
|
|
6
|
+
set -euo pipefail
|
|
7
|
+
|
|
8
|
+
error_exit() {
|
|
9
|
+
echo "ERROR: $1" >&2
|
|
10
|
+
exit "${2:-1}"
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
# Colors
|
|
14
|
+
GREEN='\033[0;32m'
|
|
15
|
+
YELLOW='\033[1;33m'
|
|
16
|
+
BLUE='\033[0;34m'
|
|
17
|
+
RED='\033[0;31m'
|
|
18
|
+
NC='\033[0m'
|
|
19
|
+
|
|
20
|
+
echo -e "${BLUE}Validating Cursor Integration...${NC}"
|
|
21
|
+
echo ""
|
|
22
|
+
|
|
23
|
+
PASSED=0
|
|
24
|
+
FAILED=0
|
|
25
|
+
WARNINGS=0
|
|
26
|
+
|
|
27
|
+
# Check 1: .mdc files exist
|
|
28
|
+
echo -e "${YELLOW}[1/6] Checking .mdc rule files...${NC}"
|
|
29
|
+
MDC_COUNT=$(find .cursor/rules -name "*.mdc" 2>/dev/null | wc -l | tr -d ' ')
|
|
30
|
+
if [ "$MDC_COUNT" -gt 0 ]; then
|
|
31
|
+
echo -e "${GREEN}✓ Found $MDC_COUNT .mdc rule files${NC}"
|
|
32
|
+
PASSED=$((PASSED + 1))
|
|
33
|
+
find .cursor/rules -name "*.mdc" | sed 's/^/ - /'
|
|
34
|
+
else
|
|
35
|
+
echo -e "${RED}✗ No .mdc rule files found${NC}"
|
|
36
|
+
FAILED=$((FAILED + 1))
|
|
37
|
+
fi
|
|
38
|
+
echo ""
|
|
39
|
+
|
|
40
|
+
# Check 2: Slash commands exist
|
|
41
|
+
echo -e "${YELLOW}[2/6] Checking slash command files...${NC}"
|
|
42
|
+
CMD_COUNT=$(find .cursor/commands -name "*.md" 2>/dev/null | wc -l | tr -d ' ')
|
|
43
|
+
if [ "$CMD_COUNT" -gt 0 ]; then
|
|
44
|
+
echo -e "${GREEN}✓ Found $CMD_COUNT slash command files${NC}"
|
|
45
|
+
PASSED=$((PASSED + 1))
|
|
46
|
+
find .cursor/commands -name "*.md" | sed 's/^/ - /'
|
|
47
|
+
else
|
|
48
|
+
echo -e "${RED}✗ No slash command files found${NC}"
|
|
49
|
+
FAILED=$((FAILED + 1))
|
|
50
|
+
fi
|
|
51
|
+
echo ""
|
|
52
|
+
|
|
53
|
+
# Check 3: Required commands exist
|
|
54
|
+
echo -e "${YELLOW}[3/6] Checking required commands...${NC}"
|
|
55
|
+
REQUIRED_CMDS=("ship.md" "new_intent.md" "init_project.md" "scope_project.md" "deploy.md" "verify.md" "kill.md" "drift_check.md")
|
|
56
|
+
MISSING=0
|
|
57
|
+
for cmd in "${REQUIRED_CMDS[@]}"; do
|
|
58
|
+
if [ -f ".cursor/commands/$cmd" ]; then
|
|
59
|
+
echo -e " ${GREEN}✓${NC} $cmd"
|
|
60
|
+
else
|
|
61
|
+
echo -e " ${RED}✗${NC} $cmd (missing)"
|
|
62
|
+
MISSING=$((MISSING + 1))
|
|
63
|
+
fi
|
|
64
|
+
done
|
|
65
|
+
if [ $MISSING -eq 0 ]; then
|
|
66
|
+
PASSED=$((PASSED + 1))
|
|
67
|
+
else
|
|
68
|
+
FAILED=$((FAILED + 1))
|
|
69
|
+
fi
|
|
70
|
+
echo ""
|
|
71
|
+
|
|
72
|
+
# Check 4: Required rules exist
|
|
73
|
+
echo -e "${YELLOW}[4/6] Checking required rule files...${NC}"
|
|
74
|
+
REQUIRED_RULES=("steward.mdc" "pm.mdc" "architect.mdc" "implementer.mdc" "qa.mdc" "security.mdc" "docs.mdc")
|
|
75
|
+
MISSING=0
|
|
76
|
+
for rule in "${REQUIRED_RULES[@]}"; do
|
|
77
|
+
if [ -f ".cursor/rules/$rule" ]; then
|
|
78
|
+
echo -e " ${GREEN}✓${NC} $rule"
|
|
79
|
+
else
|
|
80
|
+
echo -e " ${RED}✗${NC} $rule (missing)"
|
|
81
|
+
MISSING=$((MISSING + 1))
|
|
82
|
+
fi
|
|
83
|
+
done
|
|
84
|
+
if [ $MISSING -eq 0 ]; then
|
|
85
|
+
PASSED=$((PASSED + 1))
|
|
86
|
+
else
|
|
87
|
+
FAILED=$((FAILED + 1))
|
|
88
|
+
fi
|
|
89
|
+
echo ""
|
|
90
|
+
|
|
91
|
+
# Check 5: Scripts are executable
|
|
92
|
+
echo -e "${YELLOW}[5/6] Checking script executability...${NC}"
|
|
93
|
+
SCRIPTS=("init-project.sh" "scope-project.sh" "deploy.sh" "workflow-orchestrator.sh")
|
|
94
|
+
MISSING=0
|
|
95
|
+
for script in "${SCRIPTS[@]}"; do
|
|
96
|
+
if [ -f "scripts/$script" ] && [ -x "scripts/$script" ]; then
|
|
97
|
+
echo -e " ${GREEN}✓${NC} $script"
|
|
98
|
+
else
|
|
99
|
+
echo -e " ${YELLOW}⚠${NC} $script (not executable or missing)"
|
|
100
|
+
MISSING=$((MISSING + 1))
|
|
101
|
+
WARNINGS=$((WARNINGS + 1))
|
|
102
|
+
fi
|
|
103
|
+
done
|
|
104
|
+
if [ $MISSING -eq 0 ]; then
|
|
105
|
+
PASSED=$((PASSED + 1))
|
|
106
|
+
else
|
|
107
|
+
WARNINGS=$((WARNINGS + 1))
|
|
108
|
+
fi
|
|
109
|
+
echo ""
|
|
110
|
+
|
|
111
|
+
# Check 6: Project structure
|
|
112
|
+
echo -e "${YELLOW}[6/6] Checking project structure...${NC}"
|
|
113
|
+
REQUIRED_DIRS=("intent" "workflow-state" "architecture" "scripts" ".cursor/rules" ".cursor/commands")
|
|
114
|
+
MISSING=0
|
|
115
|
+
for dir in "${REQUIRED_DIRS[@]}"; do
|
|
116
|
+
if [ -d "$dir" ]; then
|
|
117
|
+
echo -e " ${GREEN}✓${NC} $dir/"
|
|
118
|
+
else
|
|
119
|
+
echo -e " ${RED}✗${NC} $dir/ (missing)"
|
|
120
|
+
MISSING=$((MISSING + 1))
|
|
121
|
+
fi
|
|
122
|
+
done
|
|
123
|
+
if [ $MISSING -eq 0 ]; then
|
|
124
|
+
PASSED=$((PASSED + 1))
|
|
125
|
+
else
|
|
126
|
+
FAILED=$((FAILED + 1))
|
|
127
|
+
fi
|
|
128
|
+
echo ""
|
|
129
|
+
|
|
130
|
+
# Summary
|
|
131
|
+
echo -e "${BLUE}════════════════════════════════════════${NC}"
|
|
132
|
+
echo -e "${BLUE}Validation Summary${NC}"
|
|
133
|
+
echo -e "${BLUE}════════════════════════════════════════${NC}"
|
|
134
|
+
echo -e "${GREEN}Passed: $PASSED${NC}"
|
|
135
|
+
echo -e "${RED}Failed: $FAILED${NC}"
|
|
136
|
+
echo -e "${YELLOW}Warnings: $WARNINGS${NC}"
|
|
137
|
+
echo ""
|
|
138
|
+
|
|
139
|
+
if [ $FAILED -eq 0 ]; then
|
|
140
|
+
echo -e "${GREEN}✓ All checks passed!${NC}"
|
|
141
|
+
echo ""
|
|
142
|
+
echo -e "${YELLOW}Manual Validation Required:${NC}"
|
|
143
|
+
echo "1. Open Cursor and type '/' - verify commands appear"
|
|
144
|
+
echo "2. Try /ship F-001 - verify command works"
|
|
145
|
+
echo "3. Check if .mdc rules are recognized (Cursor may show them in settings)"
|
|
146
|
+
echo ""
|
|
147
|
+
exit 0
|
|
148
|
+
else
|
|
149
|
+
echo -e "${RED}✗ Some checks failed. Fix issues above.${NC}"
|
|
150
|
+
exit 1
|
|
151
|
+
fi
|
|
@@ -0,0 +1,71 @@
|
|
|
1
|
+
#!/bin/bash
|
|
2
|
+
|
|
3
|
+
# Validate project.json against schema
|
|
4
|
+
|
|
5
|
+
set -euo pipefail
|
|
6
|
+
|
|
7
|
+
error_exit() {
|
|
8
|
+
echo "ERROR: $1" >&2
|
|
9
|
+
exit "${2:-1}"
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
PROJECT_FILE="${1:-project.json}"
|
|
13
|
+
|
|
14
|
+
if [ ! -f "$PROJECT_FILE" ]; then
|
|
15
|
+
error_exit "Project file not found: $PROJECT_FILE" 1
|
|
16
|
+
fi
|
|
17
|
+
|
|
18
|
+
# Basic validation (check required fields)
|
|
19
|
+
echo "Validating $PROJECT_FILE..."
|
|
20
|
+
|
|
21
|
+
# Check if jq is available
|
|
22
|
+
if ! command -v jq >/dev/null 2>&1; then
|
|
23
|
+
echo "WARNING: jq not found, performing basic validation only"
|
|
24
|
+
|
|
25
|
+
# Basic checks
|
|
26
|
+
if ! grep -q '"name"' "$PROJECT_FILE"; then
|
|
27
|
+
error_exit "Missing required field: name" 1
|
|
28
|
+
fi
|
|
29
|
+
|
|
30
|
+
if ! grep -q '"version"' "$PROJECT_FILE"; then
|
|
31
|
+
error_exit "Missing required field: version" 1
|
|
32
|
+
fi
|
|
33
|
+
|
|
34
|
+
if ! grep -q '"techStack"' "$PROJECT_FILE"; then
|
|
35
|
+
error_exit "Missing required field: techStack" 1
|
|
36
|
+
fi
|
|
37
|
+
|
|
38
|
+
echo "✓ Basic validation passed"
|
|
39
|
+
exit 0
|
|
40
|
+
fi
|
|
41
|
+
|
|
42
|
+
# Advanced validation with jq
|
|
43
|
+
REQUIRED_FIELDS=("name" "version" "techStack" "created")
|
|
44
|
+
|
|
45
|
+
for field in "${REQUIRED_FIELDS[@]}"; do
|
|
46
|
+
if ! jq -e ".$field" "$PROJECT_FILE" >/dev/null 2>&1; then
|
|
47
|
+
error_exit "Missing required field: $field" 1
|
|
48
|
+
fi
|
|
49
|
+
done
|
|
50
|
+
|
|
51
|
+
# Validate techStack enum
|
|
52
|
+
TECH_STACK=$(jq -r '.techStack' "$PROJECT_FILE")
|
|
53
|
+
if [[ ! "$TECH_STACK" =~ ^(typescript-nodejs|python|other)$ ]]; then
|
|
54
|
+
error_exit "Invalid techStack: $TECH_STACK (must be typescript-nodejs, python, or other)" 1
|
|
55
|
+
fi
|
|
56
|
+
|
|
57
|
+
# Validate version format
|
|
58
|
+
VERSION=$(jq -r '.version' "$PROJECT_FILE")
|
|
59
|
+
if [[ ! "$VERSION" =~ ^[0-9]+\.[0-9]+\.[0-9]+$ ]]; then
|
|
60
|
+
error_exit "Invalid version format: $VERSION (must be semantic version like 0.1.0)" 1
|
|
61
|
+
fi
|
|
62
|
+
|
|
63
|
+
# Validate settings if present
|
|
64
|
+
if jq -e '.settings' "$PROJECT_FILE" >/dev/null 2>&1; then
|
|
65
|
+
CONFIDENCE=$(jq -r '.settings.confidenceThreshold // 0.7' "$PROJECT_FILE")
|
|
66
|
+
if (( $(echo "$CONFIDENCE < 0 || $CONFIDENCE > 1" | bc -l) )); then
|
|
67
|
+
error_exit "Invalid confidenceThreshold: $CONFIDENCE (must be 0.0-1.0)" 1
|
|
68
|
+
fi
|
|
69
|
+
fi
|
|
70
|
+
|
|
71
|
+
echo "✓ Validation passed: $PROJECT_FILE"
|
|
@@ -0,0 +1,146 @@
|
|
|
1
|
+
#!/bin/bash
|
|
2
|
+
|
|
3
|
+
# VS Code + ShipIt Extension Validation Script
|
|
4
|
+
# Checks .cursor layout and project structure (same as Cursor). Run from repo root in VS Code.
|
|
5
|
+
|
|
6
|
+
set -euo pipefail
|
|
7
|
+
|
|
8
|
+
# Colors
|
|
9
|
+
GREEN='\033[0;32m'
|
|
10
|
+
YELLOW='\033[1;33m'
|
|
11
|
+
BLUE='\033[0;34m'
|
|
12
|
+
RED='\033[0;31m'
|
|
13
|
+
NC='\033[0m'
|
|
14
|
+
|
|
15
|
+
echo -e "${BLUE}Validating VS Code / ShipIt integration...${NC}"
|
|
16
|
+
echo ""
|
|
17
|
+
|
|
18
|
+
PASSED=0
|
|
19
|
+
FAILED=0
|
|
20
|
+
WARNINGS=0
|
|
21
|
+
|
|
22
|
+
# Check 1: .mdc files exist
|
|
23
|
+
echo -e "${YELLOW}[1/6] Checking .mdc rule files...${NC}"
|
|
24
|
+
MDC_COUNT=$(find .cursor/rules -name "*.mdc" 2>/dev/null | wc -l | tr -d ' ')
|
|
25
|
+
if [ "$MDC_COUNT" -gt 0 ]; then
|
|
26
|
+
echo -e "${GREEN}✓ Found $MDC_COUNT .mdc rule files${NC}"
|
|
27
|
+
PASSED=$((PASSED + 1))
|
|
28
|
+
find .cursor/rules -name "*.mdc" | sed 's/^/ - /'
|
|
29
|
+
else
|
|
30
|
+
echo -e "${RED}✗ No .mdc rule files found${NC}"
|
|
31
|
+
FAILED=$((FAILED + 1))
|
|
32
|
+
fi
|
|
33
|
+
echo ""
|
|
34
|
+
|
|
35
|
+
# Check 2: Slash command files exist (extension reads these)
|
|
36
|
+
echo -e "${YELLOW}[2/6] Checking command files...${NC}"
|
|
37
|
+
CMD_COUNT=$(find .cursor/commands -name "*.md" 2>/dev/null | wc -l | tr -d ' ')
|
|
38
|
+
if [ "$CMD_COUNT" -gt 0 ]; then
|
|
39
|
+
echo -e "${GREEN}✓ Found $CMD_COUNT command files${NC}"
|
|
40
|
+
PASSED=$((PASSED + 1))
|
|
41
|
+
find .cursor/commands -name "*.md" | sed 's/^/ - /'
|
|
42
|
+
else
|
|
43
|
+
echo -e "${RED}✗ No command files found${NC}"
|
|
44
|
+
FAILED=$((FAILED + 1))
|
|
45
|
+
fi
|
|
46
|
+
echo ""
|
|
47
|
+
|
|
48
|
+
# Check 3: Required commands exist
|
|
49
|
+
echo -e "${YELLOW}[3/6] Checking required commands...${NC}"
|
|
50
|
+
REQUIRED_CMDS=("ship.md" "new_intent.md" "init_project.md" "scope_project.md" "deploy.md" "verify.md" "kill.md" "drift_check.md")
|
|
51
|
+
MISSING=0
|
|
52
|
+
for cmd in "${REQUIRED_CMDS[@]}"; do
|
|
53
|
+
if [ -f ".cursor/commands/$cmd" ]; then
|
|
54
|
+
echo -e " ${GREEN}✓${NC} $cmd"
|
|
55
|
+
else
|
|
56
|
+
echo -e " ${RED}✗${NC} $cmd (missing)"
|
|
57
|
+
MISSING=$((MISSING + 1))
|
|
58
|
+
fi
|
|
59
|
+
done
|
|
60
|
+
if [ $MISSING -eq 0 ]; then
|
|
61
|
+
PASSED=$((PASSED + 1))
|
|
62
|
+
else
|
|
63
|
+
FAILED=$((FAILED + 1))
|
|
64
|
+
fi
|
|
65
|
+
echo ""
|
|
66
|
+
|
|
67
|
+
# Check 4: Required rules exist
|
|
68
|
+
echo -e "${YELLOW}[4/6] Checking required rule files...${NC}"
|
|
69
|
+
REQUIRED_RULES=("steward.mdc" "pm.mdc" "architect.mdc" "implementer.mdc" "qa.mdc" "security.mdc" "docs.mdc")
|
|
70
|
+
MISSING=0
|
|
71
|
+
for rule in "${REQUIRED_RULES[@]}"; do
|
|
72
|
+
if [ -f ".cursor/rules/$rule" ]; then
|
|
73
|
+
echo -e " ${GREEN}✓${NC} $rule"
|
|
74
|
+
else
|
|
75
|
+
echo -e " ${RED}✗${NC} $rule (missing)"
|
|
76
|
+
MISSING=$((MISSING + 1))
|
|
77
|
+
fi
|
|
78
|
+
done
|
|
79
|
+
if [ $MISSING -eq 0 ]; then
|
|
80
|
+
PASSED=$((PASSED + 1))
|
|
81
|
+
else
|
|
82
|
+
FAILED=$((FAILED + 1))
|
|
83
|
+
fi
|
|
84
|
+
echo ""
|
|
85
|
+
|
|
86
|
+
# Check 5: Scripts are executable
|
|
87
|
+
echo -e "${YELLOW}[5/6] Checking script executability...${NC}"
|
|
88
|
+
SCRIPTS=("init-project.sh" "scope-project.sh" "deploy.sh" "workflow-orchestrator.sh")
|
|
89
|
+
MISSING=0
|
|
90
|
+
for script in "${SCRIPTS[@]}"; do
|
|
91
|
+
if [ -f "scripts/$script" ] && [ -x "scripts/$script" ]; then
|
|
92
|
+
echo -e " ${GREEN}✓${NC} $script"
|
|
93
|
+
else
|
|
94
|
+
echo -e " ${YELLOW}⚠${NC} $script (not executable or missing)"
|
|
95
|
+
MISSING=$((MISSING + 1))
|
|
96
|
+
WARNINGS=$((WARNINGS + 1))
|
|
97
|
+
fi
|
|
98
|
+
done
|
|
99
|
+
if [ $MISSING -eq 0 ]; then
|
|
100
|
+
PASSED=$((PASSED + 1))
|
|
101
|
+
else
|
|
102
|
+
WARNINGS=$((WARNINGS + 1))
|
|
103
|
+
fi
|
|
104
|
+
echo ""
|
|
105
|
+
|
|
106
|
+
# Check 6: Project structure (work/ layout for ShipIt)
|
|
107
|
+
echo -e "${YELLOW}[6/6] Checking project structure...${NC}"
|
|
108
|
+
REQUIRED_DIRS=("work/intent" "work/workflow-state" "_system/architecture" "scripts" ".cursor/rules" ".cursor/commands")
|
|
109
|
+
MISSING=0
|
|
110
|
+
for dir in "${REQUIRED_DIRS[@]}"; do
|
|
111
|
+
if [ -d "$dir" ]; then
|
|
112
|
+
echo -e " ${GREEN}✓${NC} $dir/"
|
|
113
|
+
else
|
|
114
|
+
echo -e " ${RED}✗${NC} $dir/ (missing)"
|
|
115
|
+
MISSING=$((MISSING + 1))
|
|
116
|
+
fi
|
|
117
|
+
done
|
|
118
|
+
if [ $MISSING -eq 0 ]; then
|
|
119
|
+
PASSED=$((PASSED + 1))
|
|
120
|
+
else
|
|
121
|
+
FAILED=$((FAILED + 1))
|
|
122
|
+
fi
|
|
123
|
+
echo ""
|
|
124
|
+
|
|
125
|
+
# Summary
|
|
126
|
+
echo -e "${BLUE}════════════════════════════════════════${NC}"
|
|
127
|
+
echo -e "${BLUE}Validation Summary${NC}"
|
|
128
|
+
echo -e "${BLUE}════════════════════════════════════════${NC}"
|
|
129
|
+
echo -e "${GREEN}Passed: $PASSED${NC}"
|
|
130
|
+
echo -e "${RED}Failed: $FAILED${NC}"
|
|
131
|
+
echo -e "${YELLOW}Warnings: $WARNINGS${NC}"
|
|
132
|
+
echo ""
|
|
133
|
+
|
|
134
|
+
if [ $FAILED -eq 0 ]; then
|
|
135
|
+
echo -e "${GREEN}✓ All checks passed!${NC}"
|
|
136
|
+
echo ""
|
|
137
|
+
echo -e "${YELLOW}Manual validation (in VS Code):${NC}"
|
|
138
|
+
echo "1. Install the ShipIt extension (from vscode-extension/ or VSIX)."
|
|
139
|
+
echo "2. Open Command Palette (Ctrl+Shift+P / Cmd+Shift+P) and run e.g. \"ShipIt: Ship\"."
|
|
140
|
+
echo "3. Enter intent id when prompted; Copilot Chat should open with the same context as Cursor /ship."
|
|
141
|
+
echo ""
|
|
142
|
+
exit 0
|
|
143
|
+
else
|
|
144
|
+
echo -e "${RED}✗ Some checks failed. Fix issues above.${NC}"
|
|
145
|
+
exit 1
|
|
146
|
+
fi
|
|
@@ -0,0 +1,153 @@
|
|
|
1
|
+
#!/bin/bash
|
|
2
|
+
|
|
3
|
+
# Verification Script
|
|
4
|
+
# Runs verification checks and writes 04_verification.md (flat or per-intent per workflow-state-layout.md).
|
|
5
|
+
|
|
6
|
+
set -euo pipefail
|
|
7
|
+
|
|
8
|
+
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
|
9
|
+
error_exit() {
|
|
10
|
+
echo "ERROR: $1" >&2
|
|
11
|
+
exit "${2:-1}"
|
|
12
|
+
}
|
|
13
|
+
# shellcheck source=lib/workflow_state.sh
|
|
14
|
+
[ -f "$SCRIPT_DIR/lib/workflow_state.sh" ] && source "$SCRIPT_DIR/lib/workflow_state.sh"
|
|
15
|
+
|
|
16
|
+
INTENT_ID="${1:-}"
|
|
17
|
+
if [ -z "$INTENT_ID" ]; then
|
|
18
|
+
error_exit "Usage: ./scripts/verify.sh <intent-id>" 1
|
|
19
|
+
fi
|
|
20
|
+
|
|
21
|
+
WORKFLOW_DIR="$(get_workflow_state_dir "$INTENT_ID")"
|
|
22
|
+
[ -n "$WORKFLOW_DIR" ] || error_exit "No workflow state dir for intent $INTENT_ID. Run /ship $INTENT_ID first." 1
|
|
23
|
+
mkdir -p "$WORKFLOW_DIR"
|
|
24
|
+
|
|
25
|
+
FAILED=0
|
|
26
|
+
TEST_STATUS="not run"
|
|
27
|
+
MUTATE_STATUS="not run"
|
|
28
|
+
AUDIT_STATUS="not run"
|
|
29
|
+
|
|
30
|
+
if command -v pnpm >/dev/null 2>&1; then
|
|
31
|
+
if pnpm test; then
|
|
32
|
+
TEST_STATUS="pass"
|
|
33
|
+
else
|
|
34
|
+
TEST_STATUS="fail"
|
|
35
|
+
FAILED=1
|
|
36
|
+
fi
|
|
37
|
+
|
|
38
|
+
if pnpm -s run test:mutate >/dev/null 2>&1; then
|
|
39
|
+
if pnpm test:mutate; then
|
|
40
|
+
MUTATE_STATUS="pass"
|
|
41
|
+
else
|
|
42
|
+
MUTATE_STATUS="fail"
|
|
43
|
+
FAILED=1
|
|
44
|
+
fi
|
|
45
|
+
else
|
|
46
|
+
MUTATE_STATUS="skipped (test:mutate not defined)"
|
|
47
|
+
fi
|
|
48
|
+
|
|
49
|
+
# Always run audit (no script gate). Use audit-level=high per verification requirements.
|
|
50
|
+
if [ -f "scripts/audit-check.sh" ]; then
|
|
51
|
+
if ./scripts/audit-check.sh high; then
|
|
52
|
+
AUDIT_STATUS="pass"
|
|
53
|
+
else
|
|
54
|
+
AUDIT_STATUS="fail (unlisted or expired advisories)"
|
|
55
|
+
FAILED=1
|
|
56
|
+
fi
|
|
57
|
+
else
|
|
58
|
+
if pnpm audit --audit-level=high; then
|
|
59
|
+
AUDIT_STATUS="pass"
|
|
60
|
+
else
|
|
61
|
+
AUDIT_STATUS="fail (high+ vulnerabilities)"
|
|
62
|
+
FAILED=1
|
|
63
|
+
fi
|
|
64
|
+
fi
|
|
65
|
+
else
|
|
66
|
+
error_exit "pnpm is required to run verification checks" 1
|
|
67
|
+
fi
|
|
68
|
+
|
|
69
|
+
cat > "$WORKFLOW_DIR/04_verification.md" << EOF
|
|
70
|
+
# Verification: $INTENT_ID
|
|
71
|
+
|
|
72
|
+
**Generated:** $(date -u +"%Y-%m-%dT%H:%M:%SZ")
|
|
73
|
+
**Intent:** $INTENT_ID
|
|
74
|
+
|
|
75
|
+
## Test Results
|
|
76
|
+
|
|
77
|
+
- pnpm test: $TEST_STATUS
|
|
78
|
+
- pnpm test:mutate: $MUTATE_STATUS
|
|
79
|
+
|
|
80
|
+
## Security Review
|
|
81
|
+
|
|
82
|
+
- pnpm audit --audit-level=high: $AUDIT_STATUS
|
|
83
|
+
|
|
84
|
+
## Verification Status
|
|
85
|
+
|
|
86
|
+
$(if [ "$FAILED" -eq 0 ]; then echo "- [x] All checks pass"; else echo "- [ ] All checks pass"; fi)
|
|
87
|
+
- [ ] Ready for release
|
|
88
|
+
EOF
|
|
89
|
+
|
|
90
|
+
# Append to confidence-calibration.json if it exists
|
|
91
|
+
mkdir -p _system/artifacts
|
|
92
|
+
CALIBRATION_FILE="_system/artifacts/confidence-calibration.json"
|
|
93
|
+
if [ -f "$CALIBRATION_FILE" ] && command -v jq >/dev/null 2>&1; then
|
|
94
|
+
# Determine outcome
|
|
95
|
+
if [ "$FAILED" -eq 0 ]; then
|
|
96
|
+
OUTCOME="success"
|
|
97
|
+
else
|
|
98
|
+
OUTCOME="failure"
|
|
99
|
+
fi
|
|
100
|
+
|
|
101
|
+
# Generate next decision ID
|
|
102
|
+
LAST_ID=$(jq -r '.decisions[-1].id // "D-000"' "$CALIBRATION_FILE" 2>/dev/null || echo "D-000")
|
|
103
|
+
LAST_NUM=$(echo "$LAST_ID" | sed 's/D-//' | awk '{print int($1)}')
|
|
104
|
+
NEXT_NUM=$((LAST_NUM + 1))
|
|
105
|
+
NEXT_ID=$(printf "D-%03d" "$NEXT_NUM")
|
|
106
|
+
|
|
107
|
+
# Try to read stated_confidence from analysis file if available
|
|
108
|
+
STATED_CONFIDENCE="null"
|
|
109
|
+
ANALYSIS_FILE="$WORKFLOW_DIR/01_analysis.md"
|
|
110
|
+
if [ -f "$ANALYSIS_FILE" ]; then
|
|
111
|
+
# Try to extract confidence from analysis file (look for "Requirements clarity: X.XX" pattern)
|
|
112
|
+
CONF_LINE=$(grep -i "requirements clarity:" "$ANALYSIS_FILE" 2>/dev/null | head -1)
|
|
113
|
+
if [ -n "$CONF_LINE" ]; then
|
|
114
|
+
EXTRACTED_CONF=$(echo "$CONF_LINE" | grep -oE '[0-9]+\.[0-9]+' | head -1)
|
|
115
|
+
if [ -n "$EXTRACTED_CONF" ]; then
|
|
116
|
+
STATED_CONFIDENCE="$EXTRACTED_CONF"
|
|
117
|
+
fi
|
|
118
|
+
fi
|
|
119
|
+
fi
|
|
120
|
+
|
|
121
|
+
# Build notes
|
|
122
|
+
NOTES="Intent: $INTENT_ID. Tests: $TEST_STATUS, Mutation: $MUTATE_STATUS, Audit: $AUDIT_STATUS"
|
|
123
|
+
|
|
124
|
+
# Append new decision
|
|
125
|
+
if [ "$STATED_CONFIDENCE" != "null" ]; then
|
|
126
|
+
# Use --argjson when we have a numeric value
|
|
127
|
+
jq --arg id "$NEXT_ID" \
|
|
128
|
+
--argjson confidence "$STATED_CONFIDENCE" \
|
|
129
|
+
--arg outcome "$OUTCOME" \
|
|
130
|
+
--arg notes "$NOTES" \
|
|
131
|
+
'.decisions += [{
|
|
132
|
+
"id": $id,
|
|
133
|
+
"stated_confidence": $confidence,
|
|
134
|
+
"actual_outcome": $outcome,
|
|
135
|
+
"notes": $notes
|
|
136
|
+
}]' "$CALIBRATION_FILE" > "${CALIBRATION_FILE}.tmp" && \
|
|
137
|
+
mv "${CALIBRATION_FILE}.tmp" "$CALIBRATION_FILE" || true
|
|
138
|
+
else
|
|
139
|
+
# Use null explicitly when confidence is not available
|
|
140
|
+
jq --arg id "$NEXT_ID" \
|
|
141
|
+
--arg outcome "$OUTCOME" \
|
|
142
|
+
--arg notes "$NOTES" \
|
|
143
|
+
'.decisions += [{
|
|
144
|
+
"id": $id,
|
|
145
|
+
"stated_confidence": null,
|
|
146
|
+
"actual_outcome": $outcome,
|
|
147
|
+
"notes": $notes
|
|
148
|
+
}]' "$CALIBRATION_FILE" > "${CALIBRATION_FILE}.tmp" && \
|
|
149
|
+
mv "${CALIBRATION_FILE}.tmp" "$CALIBRATION_FILE" || true
|
|
150
|
+
fi
|
|
151
|
+
fi
|
|
152
|
+
|
|
153
|
+
exit "$FAILED"
|
|
@@ -0,0 +1,97 @@
|
|
|
1
|
+
#!/bin/bash
|
|
2
|
+
|
|
3
|
+
# Workflow Orchestrator Script
|
|
4
|
+
# Automates workflow state file generation from phase spec and templates.
|
|
5
|
+
# Phase list: scripts/workflow-templates/phases.yml. Add a phase there and a .tpl file.
|
|
6
|
+
|
|
7
|
+
set -euo pipefail
|
|
8
|
+
|
|
9
|
+
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
|
10
|
+
ORCHESTRATOR_DIR="$SCRIPT_DIR"
|
|
11
|
+
TEMPLATES_DIR="$SCRIPT_DIR/workflow-templates"
|
|
12
|
+
# shellcheck source=lib/intent.sh
|
|
13
|
+
[ -f "$SCRIPT_DIR/lib/intent.sh" ] && source "$SCRIPT_DIR/lib/intent.sh"
|
|
14
|
+
# shellcheck source=lib/workflow_state.sh (use ORCHESTRATOR_DIR so intent.sh doesn't overwrite SCRIPT_DIR)
|
|
15
|
+
[ -f "$ORCHESTRATOR_DIR/lib/workflow_state.sh" ] && source "$ORCHESTRATOR_DIR/lib/workflow_state.sh"
|
|
16
|
+
|
|
17
|
+
INTENT_ID="${1:-}"
|
|
18
|
+
if [ -z "$INTENT_ID" ]; then
|
|
19
|
+
error_exit "Usage: $0 <intent-id>" 1
|
|
20
|
+
fi
|
|
21
|
+
|
|
22
|
+
INTENT_FILE="$(require_intent_file "$INTENT_ID")"
|
|
23
|
+
|
|
24
|
+
# Resolve workflow dir: flat for single intent, per-intent for multiple (see workflow-state-layout.md).
|
|
25
|
+
WORKFLOW_DIR="$(ensure_workflow_state_dir "$INTENT_ID")"
|
|
26
|
+
[ -n "$WORKFLOW_DIR" ] || error_exit "Failed to resolve workflow state dir for $INTENT_ID" 1
|
|
27
|
+
mkdir -p "$WORKFLOW_DIR"
|
|
28
|
+
|
|
29
|
+
# Source progress library
|
|
30
|
+
if [ -f "$SCRIPT_DIR/lib/progress.sh" ]; then
|
|
31
|
+
source "$SCRIPT_DIR/lib/progress.sh"
|
|
32
|
+
fi
|
|
33
|
+
|
|
34
|
+
DATE_UTC="$(date -u +"%Y-%m-%dT%H:%M:%SZ")"
|
|
35
|
+
PHASE_COUNT=$(node -e "
|
|
36
|
+
const yaml = require('yaml');
|
|
37
|
+
const fs = require('fs');
|
|
38
|
+
const spec = yaml.parse(fs.readFileSync('$TEMPLATES_DIR/phases.yml', 'utf8'));
|
|
39
|
+
console.log(spec.phases.length);
|
|
40
|
+
")
|
|
41
|
+
|
|
42
|
+
echo -e "${BLUE}Orchestrating workflow for $INTENT_ID...${NC}"
|
|
43
|
+
echo -e "${BLUE}Using intent file: ${INTENT_FILE}${NC}"
|
|
44
|
+
echo ""
|
|
45
|
+
|
|
46
|
+
phase_num=0
|
|
47
|
+
while IFS='|' read -r output_file template_file phase_name; do
|
|
48
|
+
[ -z "$output_file" ] && continue
|
|
49
|
+
phase_num=$((phase_num + 1))
|
|
50
|
+
if command -v show_phase_progress >/dev/null 2>&1; then
|
|
51
|
+
show_phase_progress "$phase_num" "$PHASE_COUNT" "$phase_name" "running"
|
|
52
|
+
else
|
|
53
|
+
echo -e "${YELLOW}[Phase $phase_num/$PHASE_COUNT] $phase_name... ⏳${NC}"
|
|
54
|
+
fi
|
|
55
|
+
|
|
56
|
+
template_path="$TEMPLATES_DIR/$template_file"
|
|
57
|
+
if [ ! -f "$template_path" ]; then
|
|
58
|
+
error_exit "Template not found: $template_path" 1
|
|
59
|
+
fi
|
|
60
|
+
|
|
61
|
+
# active.md lives at top level only; update it for this intent (multi-intent list).
|
|
62
|
+
if [ "$output_file" = "active.md" ]; then
|
|
63
|
+
append_or_set_active_intent "$INTENT_ID" "$phase_name" || true
|
|
64
|
+
if command -v show_phase_progress >/dev/null 2>&1; then
|
|
65
|
+
show_phase_progress "$phase_num" "$PHASE_COUNT" "$phase_name" "complete"
|
|
66
|
+
else
|
|
67
|
+
echo -e "${GREEN}✓ Updated $WS_BASE/active.md${NC}"
|
|
68
|
+
fi
|
|
69
|
+
else
|
|
70
|
+
sed -e "s/{{INTENT_ID}}/$INTENT_ID/g" -e "s/{{DATE_UTC}}/$DATE_UTC/g" "$template_path" > "$WORKFLOW_DIR/$output_file" \
|
|
71
|
+
|| error_exit "Failed to create $WORKFLOW_DIR/$output_file" 1
|
|
72
|
+
|
|
73
|
+
if command -v show_phase_progress >/dev/null 2>&1; then
|
|
74
|
+
show_phase_progress "$phase_num" "$PHASE_COUNT" "$phase_name" "complete"
|
|
75
|
+
else
|
|
76
|
+
echo -e "${GREEN}✓ Created $WORKFLOW_DIR/$output_file${NC}"
|
|
77
|
+
fi
|
|
78
|
+
fi
|
|
79
|
+
done < <(node -e "
|
|
80
|
+
const yaml = require('yaml');
|
|
81
|
+
const fs = require('fs');
|
|
82
|
+
const spec = yaml.parse(fs.readFileSync('$TEMPLATES_DIR/phases.yml', 'utf8'));
|
|
83
|
+
spec.phases.forEach(p => console.log(p.output + '|' + p.template + '|' + (p.name || '')));
|
|
84
|
+
")
|
|
85
|
+
|
|
86
|
+
echo ""
|
|
87
|
+
echo -e "${GREEN}════════════════════════════════════════${NC}"
|
|
88
|
+
echo -e "${GREEN}✓ Workflow state files created${NC}"
|
|
89
|
+
echo -e "${GREEN}════════════════════════════════════════${NC}"
|
|
90
|
+
echo ""
|
|
91
|
+
echo -e "${YELLOW}Next steps:${NC}"
|
|
92
|
+
echo "1. Fill in $WORKFLOW_DIR/01_analysis.md (PM role)"
|
|
93
|
+
echo "2. Fill in $WORKFLOW_DIR/02_plan.md (Architect role)"
|
|
94
|
+
echo "3. Fill in $WORKFLOW_DIR/03_implementation.md (Implementer role)"
|
|
95
|
+
echo "4. Fill in $WORKFLOW_DIR/04_verification.md (QA + Security roles)"
|
|
96
|
+
echo "5. Fill in $WORKFLOW_DIR/05_release_notes.md (Docs + Steward roles)"
|
|
97
|
+
echo ""
|