specweave 0.23.10 → 0.23.14

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.
Files changed (135) hide show
  1. package/.claude-plugin/marketplace.json +7 -7
  2. package/CLAUDE.md +384 -1449
  3. package/dist/src/cli/commands/cleanup-cache.d.ts +14 -0
  4. package/dist/src/cli/commands/cleanup-cache.d.ts.map +1 -0
  5. package/dist/src/cli/commands/cleanup-cache.js +63 -0
  6. package/dist/src/cli/commands/cleanup-cache.js.map +1 -0
  7. package/dist/src/cli/commands/init.js +40 -0
  8. package/dist/src/cli/commands/init.js.map +1 -1
  9. package/dist/src/cli/helpers/async-project-loader.d.ts +148 -0
  10. package/dist/src/cli/helpers/async-project-loader.d.ts.map +1 -0
  11. package/dist/src/cli/helpers/async-project-loader.js +351 -0
  12. package/dist/src/cli/helpers/async-project-loader.js.map +1 -0
  13. package/dist/src/cli/helpers/cancelation-handler.d.ts +123 -0
  14. package/dist/src/cli/helpers/cancelation-handler.d.ts.map +1 -0
  15. package/dist/src/cli/helpers/cancelation-handler.js +187 -0
  16. package/dist/src/cli/helpers/cancelation-handler.js.map +1 -0
  17. package/dist/src/cli/helpers/import-strategy-prompter.d.ts +43 -0
  18. package/dist/src/cli/helpers/import-strategy-prompter.d.ts.map +1 -0
  19. package/dist/src/cli/helpers/import-strategy-prompter.js +136 -0
  20. package/dist/src/cli/helpers/import-strategy-prompter.js.map +1 -0
  21. package/dist/src/cli/helpers/issue-tracker/ado.d.ts +5 -2
  22. package/dist/src/cli/helpers/issue-tracker/ado.d.ts.map +1 -1
  23. package/dist/src/cli/helpers/issue-tracker/ado.js +90 -40
  24. package/dist/src/cli/helpers/issue-tracker/ado.js.map +1 -1
  25. package/dist/src/cli/helpers/issue-tracker/jira.d.ts +2 -1
  26. package/dist/src/cli/helpers/issue-tracker/jira.d.ts.map +1 -1
  27. package/dist/src/cli/helpers/issue-tracker/jira.js +120 -35
  28. package/dist/src/cli/helpers/issue-tracker/jira.js.map +1 -1
  29. package/dist/src/cli/helpers/progress-tracker.d.ts +121 -0
  30. package/dist/src/cli/helpers/progress-tracker.d.ts.map +1 -0
  31. package/dist/src/cli/helpers/progress-tracker.js +202 -0
  32. package/dist/src/cli/helpers/progress-tracker.js.map +1 -0
  33. package/dist/src/cli/helpers/project-count-fetcher.d.ts +69 -0
  34. package/dist/src/cli/helpers/project-count-fetcher.d.ts.map +1 -0
  35. package/dist/src/cli/helpers/project-count-fetcher.js +173 -0
  36. package/dist/src/cli/helpers/project-count-fetcher.js.map +1 -0
  37. package/dist/src/config/types.d.ts +14 -14
  38. package/dist/src/core/cache/cache-manager.d.ts +119 -0
  39. package/dist/src/core/cache/cache-manager.d.ts.map +1 -0
  40. package/dist/src/core/cache/cache-manager.js +304 -0
  41. package/dist/src/core/cache/cache-manager.js.map +1 -0
  42. package/dist/src/core/cache/rate-limit-checker.d.ts +92 -0
  43. package/dist/src/core/cache/rate-limit-checker.d.ts.map +1 -0
  44. package/dist/src/core/cache/rate-limit-checker.js +160 -0
  45. package/dist/src/core/cache/rate-limit-checker.js.map +1 -0
  46. package/dist/src/core/progress/cancelation-handler.d.ts +79 -0
  47. package/dist/src/core/progress/cancelation-handler.d.ts.map +1 -0
  48. package/dist/src/core/progress/cancelation-handler.js +111 -0
  49. package/dist/src/core/progress/cancelation-handler.js.map +1 -0
  50. package/dist/src/core/progress/error-logger.d.ts +58 -0
  51. package/dist/src/core/progress/error-logger.d.ts.map +1 -0
  52. package/dist/src/core/progress/error-logger.js +99 -0
  53. package/dist/src/core/progress/error-logger.js.map +1 -0
  54. package/dist/src/core/progress/import-state.d.ts +71 -0
  55. package/dist/src/core/progress/import-state.d.ts.map +1 -0
  56. package/dist/src/core/progress/import-state.js +96 -0
  57. package/dist/src/core/progress/import-state.js.map +1 -0
  58. package/dist/src/core/progress/progress-tracker.d.ts +139 -0
  59. package/dist/src/core/progress/progress-tracker.d.ts.map +1 -0
  60. package/dist/src/core/progress/progress-tracker.js +223 -0
  61. package/dist/src/core/progress/progress-tracker.js.map +1 -0
  62. package/dist/src/init/architecture/types.d.ts +6 -6
  63. package/dist/src/integrations/ado/ado-client.d.ts +25 -0
  64. package/dist/src/integrations/ado/ado-client.d.ts.map +1 -1
  65. package/dist/src/integrations/ado/ado-client.js +67 -0
  66. package/dist/src/integrations/ado/ado-client.js.map +1 -1
  67. package/dist/src/integrations/ado/ado-dependency-loader.d.ts +99 -0
  68. package/dist/src/integrations/ado/ado-dependency-loader.d.ts.map +1 -0
  69. package/dist/src/integrations/ado/ado-dependency-loader.js +207 -0
  70. package/dist/src/integrations/ado/ado-dependency-loader.js.map +1 -0
  71. package/dist/src/integrations/jira/jira-client.d.ts +32 -0
  72. package/dist/src/integrations/jira/jira-client.d.ts.map +1 -1
  73. package/dist/src/integrations/jira/jira-client.js +81 -0
  74. package/dist/src/integrations/jira/jira-client.js.map +1 -1
  75. package/dist/src/integrations/jira/jira-dependency-loader.d.ts +101 -0
  76. package/dist/src/integrations/jira/jira-dependency-loader.d.ts.map +1 -0
  77. package/dist/src/integrations/jira/jira-dependency-loader.js +200 -0
  78. package/dist/src/integrations/jira/jira-dependency-loader.js.map +1 -0
  79. package/package.json +1 -1
  80. package/plugins/specweave/.claude-plugin/plugin.json +20 -0
  81. package/plugins/specweave/agents/architect/AGENT.md +100 -602
  82. package/plugins/specweave/agents/pm/AGENT.md +96 -597
  83. package/plugins/specweave/agents/pm/AGENT.md.bak +1893 -0
  84. package/plugins/specweave/agents/pm/AGENT.md.bak2 +1754 -0
  85. package/plugins/specweave/commands/check-hooks.md +257 -0
  86. package/plugins/specweave/hooks/docs-changed.sh +9 -1
  87. package/plugins/specweave/hooks/docs-changed.sh.backup +79 -0
  88. package/plugins/specweave/hooks/human-input-required.sh +9 -1
  89. package/plugins/specweave/hooks/human-input-required.sh.backup +75 -0
  90. package/plugins/specweave/hooks/post-edit-spec.sh +202 -31
  91. package/plugins/specweave/hooks/post-first-increment.sh.backup +61 -0
  92. package/plugins/specweave/hooks/post-increment-change.sh +6 -1
  93. package/plugins/specweave/hooks/post-increment-change.sh.backup +98 -0
  94. package/plugins/specweave/hooks/post-increment-completion.sh +6 -1
  95. package/plugins/specweave/hooks/post-increment-completion.sh.backup +231 -0
  96. package/plugins/specweave/hooks/post-increment-planning.sh +6 -1
  97. package/plugins/specweave/hooks/post-increment-planning.sh.backup +1048 -0
  98. package/plugins/specweave/hooks/post-increment-status-change.sh +6 -1
  99. package/plugins/specweave/hooks/post-increment-status-change.sh.backup +147 -0
  100. package/plugins/specweave/hooks/post-metadata-change.sh +7 -1
  101. package/plugins/specweave/hooks/post-spec-update.sh.backup +158 -0
  102. package/plugins/specweave/hooks/post-task-completion.sh +225 -228
  103. package/plugins/specweave/hooks/post-user-story-complete.sh.backup +179 -0
  104. package/plugins/specweave/hooks/post-write-spec.sh +207 -31
  105. package/plugins/specweave/hooks/pre-command-deduplication.sh.backup +83 -0
  106. package/plugins/specweave/hooks/pre-edit-spec.sh +151 -0
  107. package/plugins/specweave/hooks/pre-implementation.sh +9 -1
  108. package/plugins/specweave/hooks/pre-implementation.sh.backup +67 -0
  109. package/plugins/specweave/hooks/pre-task-completion.sh +14 -8
  110. package/plugins/specweave/hooks/pre-task-completion.sh.backup +194 -0
  111. package/plugins/specweave/hooks/pre-tool-use.sh +9 -1
  112. package/plugins/specweave/hooks/pre-tool-use.sh.backup +133 -0
  113. package/plugins/specweave/hooks/pre-write-spec.sh +151 -0
  114. package/plugins/specweave/hooks/test-pretooluse-env.sh +72 -0
  115. package/plugins/specweave/hooks/user-prompt-submit.sh.backup +386 -0
  116. package/plugins/specweave/skills/compliance-architecture/SKILL.md +374 -0
  117. package/plugins/specweave/skills/external-sync-wizard/SKILL.md +610 -0
  118. package/plugins/specweave/skills/pm-closure-validation/SKILL.md +541 -0
  119. package/plugins/specweave/skills/roadmap-planner/SKILL.md +473 -0
  120. package/plugins/specweave-ado/commands/refresh-cache.js +25 -0
  121. package/plugins/specweave-ado/commands/refresh-cache.ts +40 -0
  122. package/plugins/specweave-ado/hooks/post-living-docs-update.sh +9 -2
  123. package/plugins/specweave-ado/hooks/post-living-docs-update.sh.backup +353 -0
  124. package/plugins/specweave-ado/hooks/post-task-completion.sh +10 -2
  125. package/plugins/specweave-ado/hooks/post-task-completion.sh.backup +172 -0
  126. package/plugins/specweave-github/hooks/post-task-completion.sh +10 -2
  127. package/plugins/specweave-github/hooks/post-task-completion.sh.backup +258 -0
  128. package/plugins/specweave-jira/commands/refresh-cache.js +25 -0
  129. package/plugins/specweave-jira/commands/refresh-cache.ts +40 -0
  130. package/plugins/specweave-jira/hooks/post-task-completion.sh +10 -2
  131. package/plugins/specweave-jira/hooks/post-task-completion.sh.backup +172 -0
  132. package/plugins/specweave-kafka-streams/commands/topology.md +437 -0
  133. package/plugins/specweave-n8n/commands/workflow-template.md +262 -0
  134. package/plugins/specweave-release/hooks/.specweave/logs/dora-tracking.log +252 -6465
  135. package/plugins/specweave-release/hooks/post-task-completion.sh.backup +110 -0
@@ -0,0 +1,151 @@
1
+ #!/bin/bash
2
+ #
3
+ # Pre-Edit Hook: Capture File Path BEFORE Edit Executes (Tier 2)
4
+ #
5
+ # Purpose: Detect which file will be edited BEFORE the Edit tool runs
6
+ # Strategy: PreToolUse has better access to tool arguments than PostToolUse
7
+ #
8
+ # TIER 2 COORDINATION:
9
+ # 1. Extract file_path from TOOL_USE_ARGS (more reliable in PreToolUse)
10
+ # 2. If it's spec.md/tasks.md in increments folder, signal PostToolUse hook
11
+ # 3. Write file path to .pending-status-update for PostToolUse to consume
12
+ #
13
+ # This eliminates the need for mtime-based fallback detection (Tier 1)
14
+ # and reduces false positives to near zero.
15
+ #
16
+ # Architecture:
17
+ # PreToolUse:Edit → pre-edit-spec.sh (this file)
18
+ # ↓ writes to
19
+ # .specweave/state/.pending-status-update
20
+ # ↓ read by
21
+ # PostToolUse:Edit → post-edit-spec.sh
22
+ #
23
+ # Version: v0.24.3 (EMERGENCY FIXES)
24
+ # Date: 2025-11-22
25
+
26
+ # EMERGENCY FIX: Remove set -e - it causes Claude Code crashes!
27
+ set +e
28
+
29
+ # EMERGENCY KILL SWITCH: Disable all hooks if env variable set
30
+ if [[ "${SPECWEAVE_DISABLE_HOOKS:-0}" == "1" ]]; then
31
+ exit 0
32
+ fi
33
+
34
+ # Find project root
35
+ find_project_root() {
36
+ local dir="$PWD"
37
+ while [[ "$dir" != "/" ]]; do
38
+ if [[ -d "$dir/.specweave" ]]; then
39
+ echo "$dir"
40
+ return 0
41
+ fi
42
+ dir=$(dirname "$dir")
43
+ done
44
+ echo "$PWD"
45
+ }
46
+
47
+ PROJECT_ROOT=$(find_project_root)
48
+ STATE_DIR="$PROJECT_ROOT/.specweave/state"
49
+ LOGS_DIR="$PROJECT_ROOT/.specweave/logs"
50
+ DEBUG_LOG="$LOGS_DIR/hooks-debug.log"
51
+ PENDING_FILE="$STATE_DIR/.pending-status-update"
52
+ METRICS_FILE="$STATE_DIR/hook-metrics.jsonl"
53
+
54
+ # Ensure directories exist
55
+ mkdir -p "$STATE_DIR" "$LOGS_DIR" 2>/dev/null || true
56
+
57
+ # ============================================================================
58
+ # TIER 2: Extract File Path from Tool Arguments
59
+ # ============================================================================
60
+ # PreToolUse should have access to tool arguments BEFORE execution
61
+ # Try multiple methods to extract file_path
62
+
63
+ FILE_PATH=""
64
+
65
+ # Method 1: TOOL_USE_ARGS environment variable (primary for PreToolUse)
66
+ if [[ -n "${TOOL_USE_ARGS:-}" ]]; then
67
+ # Try to parse JSON with jq if available
68
+ if command -v jq &> /dev/null; then
69
+ FILE_PATH=$(echo "$TOOL_USE_ARGS" | jq -r '.file_path // empty' 2>/dev/null || echo "")
70
+ fi
71
+
72
+ # Fallback: Regex extraction if jq not available or failed
73
+ if [[ -z "$FILE_PATH" ]]; then
74
+ FILE_PATH=$(echo "$TOOL_USE_ARGS" | grep -o '"file_path"[[:space:]]*:[[:space:]]*"[^"]*"' | head -1 | sed 's/.*"\([^"]*\)".*/\1/' || echo "")
75
+ fi
76
+ fi
77
+
78
+ # Method 2: TOOL_USE_CONTENT (fallback)
79
+ if [[ -z "$FILE_PATH" ]] && [[ -n "${TOOL_USE_CONTENT:-}" ]]; then
80
+ FILE_PATH="$TOOL_USE_CONTENT"
81
+ fi
82
+
83
+ # Method 3: Parse from stdin (last resort - experimental)
84
+ if [[ -z "$FILE_PATH" ]] && [[ ! -t 0 ]]; then
85
+ # Read stdin and try to extract file_path
86
+ STDIN_DATA=$(cat 2>/dev/null || echo "")
87
+ if [[ -n "$STDIN_DATA" ]] && command -v jq &> /dev/null; then
88
+ FILE_PATH=$(echo "$STDIN_DATA" | jq -r '.file_path // empty' 2>/dev/null || echo "")
89
+ fi
90
+ fi
91
+
92
+ # ============================================================================
93
+ # TIER 2: Signal Detection and Validation
94
+ # ============================================================================
95
+
96
+ # Log what we detected (for debugging PreToolUse effectiveness)
97
+ if [[ -n "$FILE_PATH" ]]; then
98
+ echo "[$(date)] pre-edit-spec: Detected file_path: $FILE_PATH" >> "$DEBUG_LOG" 2>/dev/null || true
99
+ else
100
+ echo "[$(date)] pre-edit-spec: No file_path detected (will fall back to Tier 1)" >> "$DEBUG_LOG" 2>/dev/null || true
101
+ exit 0 # Let PostToolUse handle it with mtime fallback
102
+ fi
103
+
104
+ # Check if this is a spec.md or tasks.md file in increments folder
105
+ IS_SPEC_FILE=false
106
+ if [[ "$FILE_PATH" == *"/spec.md" ]] || [[ "$FILE_PATH" == *"/tasks.md" ]]; then
107
+ if [[ "$FILE_PATH" == *"/.specweave/increments/"* ]]; then
108
+ # Exclude archived increments
109
+ if [[ "$FILE_PATH" != *"/_archive/"* ]]; then
110
+ IS_SPEC_FILE=true
111
+ fi
112
+ fi
113
+ fi
114
+
115
+ # If not a spec/tasks file, exit silently (no signal to PostToolUse)
116
+ if [[ "$IS_SPEC_FILE" != "true" ]]; then
117
+ echo "[$(date)] pre-edit-spec: Not a spec/tasks file - no signal" >> "$DEBUG_LOG" 2>/dev/null || true
118
+ exit 0
119
+ fi
120
+
121
+ # ============================================================================
122
+ # TIER 2: Write Signal for PostToolUse Hook
123
+ # ============================================================================
124
+
125
+ # Write file path to pending file for PostToolUse to consume
126
+ echo "$FILE_PATH" > "$PENDING_FILE" 2>/dev/null || true
127
+
128
+ echo "[$(date)] pre-edit-spec: Signaled PostToolUse for: $FILE_PATH" >> "$DEBUG_LOG" 2>/dev/null || true
129
+
130
+ # ============================================================================
131
+ # TIER 2: Metrics Collection
132
+ # ============================================================================
133
+
134
+ # Record metrics (JSONL format - one JSON object per line)
135
+ TIMESTAMP=$(date -u +%Y-%m-%dT%H:%M:%SZ)
136
+ METRIC_ENTRY="{\"timestamp\":\"$TIMESTAMP\",\"hook\":\"pre-edit-spec\",\"event\":\"file_detected\",\"file_path\":\"$FILE_PATH\",\"method\":\"TOOL_USE_ARGS\"}"
137
+
138
+ # Append to metrics file (JSONL)
139
+ echo "$METRIC_ENTRY" >> "$METRICS_FILE" 2>/dev/null || true
140
+
141
+ # Log rotation for metrics (keep last 1000 entries)
142
+ if [[ -f "$METRICS_FILE" ]]; then
143
+ LINE_COUNT=$(wc -l < "$METRICS_FILE" 2>/dev/null || echo 0)
144
+ if (( LINE_COUNT > 1000 )); then
145
+ tail -1000 "$METRICS_FILE" > "$METRICS_FILE.tmp" 2>/dev/null || true
146
+ mv "$METRICS_FILE.tmp" "$METRICS_FILE" 2>/dev/null || true
147
+ fi
148
+ fi
149
+
150
+ # ALWAYS exit 0 - NEVER let hook errors crash Claude Code
151
+ exit 0
@@ -4,7 +4,12 @@
4
4
  # Runs before starting implementation of a task
5
5
  # Checks regression risk for brownfield projects
6
6
 
7
- set -e
7
+ set +e # EMERGENCY FIX: Prevents Claude Code crashes
8
+
9
+ # EMERGENCY KILL SWITCH
10
+ if [[ "${SPECWEAVE_DISABLE_HOOKS:-0}" == "1" ]]; then
11
+ exit 0
12
+ fi
8
13
 
9
14
  # Find project root by searching upward for .specweave/ directory
10
15
  # Works regardless of where hook is installed (source or .claude/hooks/)
@@ -65,3 +70,6 @@ echo "[$(date)] Pre-implementation check complete" >> "$LOGS_DIR/hooks.log"
65
70
 
66
71
  echo ""
67
72
  echo -e "${GREEN}✅ Pre-implementation check complete${NC}"
73
+
74
+ # ALWAYS exit 0 - NEVER let hook errors crash Claude Code
75
+ exit 0
@@ -0,0 +1,67 @@
1
+ #!/bin/bash
2
+
3
+ # SpecWeave Pre-Implementation Hook
4
+ # Runs before starting implementation of a task
5
+ # Checks regression risk for brownfield projects
6
+
7
+ set -e
8
+
9
+ # Find project root by searching upward for .specweave/ directory
10
+ # Works regardless of where hook is installed (source or .claude/hooks/)
11
+ find_project_root() {
12
+ local dir="$1"
13
+ while [ "$dir" != "/" ]; do
14
+ if [ -d "$dir/.specweave" ]; then
15
+ echo "$dir"
16
+ return 0
17
+ fi
18
+ dir="$(dirname "$dir")"
19
+ done
20
+ # Fallback: try current directory
21
+ if [ -d "$(pwd)/.specweave" ]; then
22
+ pwd
23
+ else
24
+ echo "$(pwd)"
25
+ fi
26
+ }
27
+
28
+ PROJECT_ROOT="$(find_project_root "$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)")"
29
+ cd "$PROJECT_ROOT"
30
+
31
+ # Colors
32
+ YELLOW='\033[1;33m'
33
+ BLUE='\033[0;34m'
34
+ GREEN='\033[0;32m'
35
+ NC='\033[0m'
36
+
37
+ echo -e "${BLUE}🔍 Pre-Implementation Check${NC}"
38
+
39
+ # Check if this is a brownfield project (has existing code)
40
+ if [ -d "src" ] || [ -d "app" ] || [ -d "lib" ]; then
41
+ echo -e "${YELLOW}⚠️ Brownfield project detected${NC}"
42
+ echo ""
43
+ echo "Recommendations:"
44
+ echo " 1. Create baseline tests before changes"
45
+ echo " 2. Check for existing tests that may break"
46
+ echo " 3. Review impact on existing features"
47
+ echo ""
48
+
49
+ # Check if baseline tests exist
50
+ if [ -d ".specweave/tests/baseline" ]; then
51
+ echo -e "${GREEN}✅ Baseline tests exist${NC}"
52
+ else
53
+ echo -e "${YELLOW}⚠️ No baseline tests found${NC}"
54
+ echo " Consider creating baseline tests first"
55
+ echo " This captures current state before changes"
56
+ fi
57
+ else
58
+ echo -e "${GREEN}✅ Greenfield project - no regression risk${NC}"
59
+ fi
60
+
61
+ # Log to hooks log
62
+ LOGS_DIR=".specweave/logs"
63
+ mkdir -p "$LOGS_DIR"
64
+ echo "[$(date)] Pre-implementation check complete" >> "$LOGS_DIR/hooks.log"
65
+
66
+ echo ""
67
+ echo -e "${GREEN}✅ Pre-implementation check complete${NC}"
@@ -20,7 +20,12 @@
20
20
  # This is the ONLY way to mark tasks complete in SpecWeave.
21
21
  # Manual edits to tasks.md are detected and flagged by pre-commit hooks.
22
22
 
23
- set -e
23
+ set +e # EMERGENCY FIX: Prevents Claude Code crashes
24
+
25
+ # EMERGENCY KILL SWITCH
26
+ if [[ "${SPECWEAVE_DISABLE_HOOKS:-0}" == "1" ]]; then
27
+ exit 0
28
+ fi
24
29
 
25
30
  # Find project root
26
31
  find_project_root() {
@@ -92,15 +97,14 @@ fi
92
97
  # DETECT CURRENT INCREMENT
93
98
  # ============================================================================
94
99
 
95
- CURRENT_INCREMENT=$(ls -t .specweave/increments/ 2>/dev/null | grep -v "_backlog" | grep -v "_archive" | grep -v "_working" | head -1)
100
+ CURRENT_INCREMENT=$(ls -td .specweave/increments/*/ 2>/dev/null | xargs -n1 basename | grep -v "_backlog" | grep -v "_archive" | grep -v "_working" | head -1)
96
101
 
97
102
  if [ -z "$CURRENT_INCREMENT" ]; then
98
- echo "[$(date)] ⚠️ No active increment found, skipping validation" >> "$DEBUG_LOG" 2>/dev/null || true
103
+ echo "[$(date)] ℹ️ No active increment found, skipping validation" >> "$DEBUG_LOG" 2>/dev/null || true
99
104
  rm -f "$STDIN_DATA"
100
105
  cat <<EOF
101
106
  {
102
- "continue": true,
103
- "systemMessage": "⚠️ Warning: No active increment found. Task completion validation skipped."
107
+ "continue": true
104
108
  }
105
109
  EOF
106
110
  exit 0
@@ -109,12 +113,11 @@ fi
109
113
  TASKS_MD=".specweave/increments/$CURRENT_INCREMENT/tasks.md"
110
114
 
111
115
  if [ ! -f "$TASKS_MD" ]; then
112
- echo "[$(date)] ⚠️ tasks.md not found for $CURRENT_INCREMENT" >> "$DEBUG_LOG" 2>/dev/null || true
116
+ echo "[$(date)] ℹ️ tasks.md not found for $CURRENT_INCREMENT (increment may be in planning stage)" >> "$DEBUG_LOG" 2>/dev/null || true
113
117
  rm -f "$STDIN_DATA"
114
118
  cat <<EOF
115
119
  {
116
- "continue": true,
117
- "systemMessage": "⚠️ Warning: tasks.md not found. Task completion validation skipped."
120
+ "continue": true
118
121
  }
119
122
  EOF
120
123
  exit 0
@@ -194,3 +197,6 @@ Fix the failing tests and try again. Run tests manually: npm test"
194
197
  }
195
198
  EOF
196
199
  fi
200
+
201
+ # ALWAYS exit 0 - NEVER let hook errors crash Claude Code
202
+ exit 0
@@ -0,0 +1,194 @@
1
+ #!/bin/bash
2
+
3
+ # SpecWeave Pre-Task-Completion Hook
4
+ # CRITICAL QUALITY GATE: Validates AC tests before allowing task completion
5
+ #
6
+ # Runs automatically BEFORE any task is marked complete via TodoWrite
7
+ #
8
+ # WORKFLOW:
9
+ # =========
10
+ # 1. TodoWrite called with status="completed"
11
+ # 2. This hook fires (pre-completion validation)
12
+ # 3. Extract task ID from TodoWrite input
13
+ # 4. Find task in tasks.md
14
+ # 5. Run AC test validator
15
+ # 6. If tests PASS → Allow completion (continue: true)
16
+ # 7. If tests FAIL → Block completion (continue: false, show error)
17
+ #
18
+ # ENFORCEMENT:
19
+ # ============
20
+ # This is the ONLY way to mark tasks complete in SpecWeave.
21
+ # Manual edits to tasks.md are detected and flagged by pre-commit hooks.
22
+
23
+ set -e
24
+
25
+ # Find project root
26
+ find_project_root() {
27
+ local dir="$1"
28
+ while [ "$dir" != "/" ]; do
29
+ if [ -d "$dir/.specweave" ]; then
30
+ echo "$dir"
31
+ return 0
32
+ fi
33
+ dir="$(dirname "$dir")"
34
+ done
35
+ pwd
36
+ }
37
+
38
+ PROJECT_ROOT="$(find_project_root "$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)")"
39
+ cd "$PROJECT_ROOT" 2>/dev/null || true
40
+
41
+ # ============================================================================
42
+ # CONFIGURATION
43
+ # ============================================================================
44
+
45
+ LOGS_DIR=".specweave/logs"
46
+ DEBUG_LOG="$LOGS_DIR/hooks-debug.log"
47
+
48
+ mkdir -p "$LOGS_DIR" 2>/dev/null || true
49
+
50
+ echo "[$(date)] 🔒 Pre-task-completion hook fired" >> "$DEBUG_LOG" 2>/dev/null || true
51
+
52
+ # ============================================================================
53
+ # CAPTURE INPUT
54
+ # ============================================================================
55
+
56
+ STDIN_DATA=$(mktemp)
57
+ cat > "$STDIN_DATA"
58
+
59
+ echo "[$(date)] Input JSON:" >> "$DEBUG_LOG" 2>/dev/null || true
60
+ cat "$STDIN_DATA" >> "$DEBUG_LOG" 2>/dev/null || true
61
+
62
+ # ============================================================================
63
+ # CHECK FOR TASK COMPLETION
64
+ # ============================================================================
65
+
66
+ # Only validate if a task is being marked complete
67
+ COMPLETING_TASK=false
68
+
69
+ if command -v jq >/dev/null 2>&1; then
70
+ # Check if any task is transitioning to "completed" status
71
+ COMPLETED_COUNT=$(jq -r '.tool_input.todos // [] | map(select(.status == "completed")) | length' "$STDIN_DATA" 2>/dev/null || echo "0")
72
+
73
+ if [ "$COMPLETED_COUNT" != "0" ]; then
74
+ COMPLETING_TASK=true
75
+ echo "[$(date)] ✓ Detected task completion (${COMPLETED_COUNT} tasks)" >> "$DEBUG_LOG" 2>/dev/null || true
76
+ fi
77
+ fi
78
+
79
+ # If no tasks being completed, allow without validation
80
+ if [ "$COMPLETING_TASK" = "false" ]; then
81
+ echo "[$(date)] ⏭️ No tasks being completed, skipping validation" >> "$DEBUG_LOG" 2>/dev/null || true
82
+ rm -f "$STDIN_DATA"
83
+ cat <<EOF
84
+ {
85
+ "continue": true
86
+ }
87
+ EOF
88
+ exit 0
89
+ fi
90
+
91
+ # ============================================================================
92
+ # DETECT CURRENT INCREMENT
93
+ # ============================================================================
94
+
95
+ CURRENT_INCREMENT=$(ls -td .specweave/increments/*/ 2>/dev/null | xargs -n1 basename | grep -v "_backlog" | grep -v "_archive" | grep -v "_working" | head -1)
96
+
97
+ if [ -z "$CURRENT_INCREMENT" ]; then
98
+ echo "[$(date)] ℹ️ No active increment found, skipping validation" >> "$DEBUG_LOG" 2>/dev/null || true
99
+ rm -f "$STDIN_DATA"
100
+ cat <<EOF
101
+ {
102
+ "continue": true
103
+ }
104
+ EOF
105
+ exit 0
106
+ fi
107
+
108
+ TASKS_MD=".specweave/increments/$CURRENT_INCREMENT/tasks.md"
109
+
110
+ if [ ! -f "$TASKS_MD" ]; then
111
+ echo "[$(date)] ℹ️ tasks.md not found for $CURRENT_INCREMENT (increment may be in planning stage)" >> "$DEBUG_LOG" 2>/dev/null || true
112
+ rm -f "$STDIN_DATA"
113
+ cat <<EOF
114
+ {
115
+ "continue": true
116
+ }
117
+ EOF
118
+ exit 0
119
+ fi
120
+
121
+ # ============================================================================
122
+ # RUN AC TEST VALIDATION
123
+ # ============================================================================
124
+
125
+ echo "[$(date)] 🧪 Running AC test validation for $CURRENT_INCREMENT" >> "$DEBUG_LOG" 2>/dev/null || true
126
+
127
+ # Determine which validation script to use
128
+ VALIDATOR_SCRIPT=""
129
+ if [ -f "$PROJECT_ROOT/dist/src/core/ac-test-validator-cli.js" ]; then
130
+ VALIDATOR_SCRIPT="$PROJECT_ROOT/dist/src/core/ac-test-validator-cli.js"
131
+ elif [ -f "$PROJECT_ROOT/node_modules/specweave/dist/src/core/ac-test-validator-cli.js" ]; then
132
+ VALIDATOR_SCRIPT="$PROJECT_ROOT/node_modules/specweave/dist/src/core/ac-test-validator-cli.js"
133
+ elif [ -n "${CLAUDE_PLUGIN_ROOT}" ] && [ -f "${CLAUDE_PLUGIN_ROOT}/dist/src/core/ac-test-validator-cli.js" ]; then
134
+ VALIDATOR_SCRIPT="${CLAUDE_PLUGIN_ROOT}/dist/src/core/ac-test-validator-cli.js"
135
+ fi
136
+
137
+ if [ -z "$VALIDATOR_SCRIPT" ] || ! command -v node &> /dev/null; then
138
+ echo "[$(date)] ⚠️ AC test validator not found or Node.js missing" >> "$DEBUG_LOG" 2>/dev/null || true
139
+ rm -f "$STDIN_DATA"
140
+ cat <<EOF
141
+ {
142
+ "continue": true,
143
+ "systemMessage": "⚠️ Warning: AC test validator not available. Task completion validation skipped. Install Node.js and rebuild SpecWeave to enable validation."
144
+ }
145
+ EOF
146
+ exit 0
147
+ fi
148
+
149
+ # Run validator (captures exit code)
150
+ VALIDATION_OUTPUT=$(mktemp)
151
+ VALIDATION_EXIT_CODE=0
152
+
153
+ (cd "$PROJECT_ROOT" && node "$VALIDATOR_SCRIPT" "$CURRENT_INCREMENT") > "$VALIDATION_OUTPUT" 2>&1 || VALIDATION_EXIT_CODE=$?
154
+
155
+ echo "[$(date)] Validator exit code: $VALIDATION_EXIT_CODE" >> "$DEBUG_LOG" 2>/dev/null || true
156
+ cat "$VALIDATION_OUTPUT" >> "$DEBUG_LOG" 2>/dev/null || true
157
+
158
+ rm -f "$STDIN_DATA"
159
+
160
+ # ============================================================================
161
+ # DECISION LOGIC
162
+ # ============================================================================
163
+
164
+ if [ "$VALIDATION_EXIT_CODE" = "0" ]; then
165
+ # Validation passed - allow completion
166
+ echo "[$(date)] ✅ AC test validation passed" >> "$DEBUG_LOG" 2>/dev/null || true
167
+
168
+ VALIDATION_SUMMARY=$(cat "$VALIDATION_OUTPUT" | tail -5 | tr '\n' ' ')
169
+
170
+ rm -f "$VALIDATION_OUTPUT"
171
+
172
+ cat <<EOF
173
+ {
174
+ "continue": true,
175
+ "systemMessage": "✅ AC Test Validation Passed: All acceptance criteria have passing tests. Task completion allowed. ${VALIDATION_SUMMARY}"
176
+ }
177
+ EOF
178
+ else
179
+ # Validation failed - block completion
180
+ echo "[$(date)] ❌ AC test validation failed" >> "$DEBUG_LOG" 2>/dev/null || true
181
+
182
+ VALIDATION_ERROR=$(cat "$VALIDATION_OUTPUT" | grep -A 10 "VALIDATION FAILED" | tr '\n' ' ' | cut -c 1-300)
183
+
184
+ rm -f "$VALIDATION_OUTPUT"
185
+
186
+ cat <<EOF
187
+ {
188
+ "continue": false,
189
+ "systemMessage": "❌ AC TEST VALIDATION FAILED: Cannot mark task as complete until all acceptance criteria have passing tests. ${VALIDATION_ERROR}
190
+
191
+ Fix the failing tests and try again. Run tests manually: npm test"
192
+ }
193
+ EOF
194
+ fi
@@ -13,7 +13,12 @@
13
13
  # - We filter for AskUserQuestion specifically to play sound
14
14
  # - Non-blocking and fast (<10ms overhead)
15
15
 
16
- set -e
16
+ set +e # EMERGENCY FIX: Prevents Claude Code crashes
17
+
18
+ # EMERGENCY KILL SWITCH
19
+ if [[ "${SPECWEAVE_DISABLE_HOOKS:-0}" == "1" ]]; then
20
+ exit 0
21
+ fi
17
22
 
18
23
  # ============================================================================
19
24
  # CONFIGURATION
@@ -131,3 +136,6 @@ else
131
136
  }
132
137
  EOF
133
138
  fi
139
+
140
+ # ALWAYS exit 0 - NEVER let hook errors crash Claude Code
141
+ exit 0
@@ -0,0 +1,133 @@
1
+ #!/bin/bash
2
+
3
+ # SpecWeave Pre-Tool-Use Hook
4
+ # Runs BEFORE Claude calls any tool (PreToolUse event)
5
+ #
6
+ # PURPOSE: Detect when Claude asks questions via AskUserQuestion
7
+ # - Plays sound IMMEDIATELY when question is about to be asked
8
+ # - Complements post-task-completion hook (which only fires after TodoWrite)
9
+ # - Ensures user is always notified when Claude needs input
10
+ #
11
+ # SCOPE:
12
+ # - This hook fires for ALL tool calls (Read, Edit, Write, AskUserQuestion, etc.)
13
+ # - We filter for AskUserQuestion specifically to play sound
14
+ # - Non-blocking and fast (<10ms overhead)
15
+
16
+ set -e
17
+
18
+ # ============================================================================
19
+ # CONFIGURATION
20
+ # ============================================================================
21
+
22
+ # Find project root
23
+ find_project_root() {
24
+ local dir="$1"
25
+ while [ "$dir" != "/" ]; do
26
+ if [ -d "$dir/.specweave" ]; then
27
+ echo "$dir"
28
+ return 0
29
+ fi
30
+ dir="$(dirname "$dir")"
31
+ done
32
+ # Fallback
33
+ if [ -d "$(pwd)/.specweave" ]; then
34
+ pwd
35
+ else
36
+ echo "$(pwd)"
37
+ fi
38
+ }
39
+
40
+ PROJECT_ROOT="$(find_project_root "$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)")"
41
+ cd "$PROJECT_ROOT" 2>/dev/null || true
42
+
43
+ LOGS_DIR=".specweave/logs"
44
+ DEBUG_LOG="$LOGS_DIR/hooks-debug.log"
45
+
46
+ mkdir -p "$LOGS_DIR" 2>/dev/null || true
47
+
48
+ # ============================================================================
49
+ # CAPTURE INPUT (Tool Call Details)
50
+ # ============================================================================
51
+
52
+ STDIN_DATA=$(mktemp)
53
+ cat > "$STDIN_DATA"
54
+
55
+ # Log the tool call for debugging
56
+ echo "[$(date)] 🔧 PreToolUse hook fired" >> "$DEBUG_LOG" 2>/dev/null || true
57
+ echo "[$(date)] Tool call JSON:" >> "$DEBUG_LOG" 2>/dev/null || true
58
+ cat "$STDIN_DATA" >> "$DEBUG_LOG" 2>/dev/null || true
59
+ echo "" >> "$DEBUG_LOG" 2>/dev/null || true
60
+
61
+ # ============================================================================
62
+ # DETECT AskUserQuestion TOOL
63
+ # ============================================================================
64
+
65
+ TOOL_NAME=""
66
+
67
+ if command -v jq >/dev/null 2>&1; then
68
+ # Use jq if available (most reliable)
69
+ TOOL_NAME=$(jq -r '.tool_name // empty' "$STDIN_DATA" 2>/dev/null)
70
+ else
71
+ # Fallback: grep-based detection
72
+ if grep -q '"tool_name"' "$STDIN_DATA" 2>/dev/null; then
73
+ TOOL_NAME=$(grep -o '"tool_name":"[^"]*"' "$STDIN_DATA" | cut -d'"' -f4)
74
+ fi
75
+ fi
76
+
77
+ echo "[$(date)] Tool name: $TOOL_NAME" >> "$DEBUG_LOG" 2>/dev/null || true
78
+
79
+ # ============================================================================
80
+ # PLAY SOUND IF AskUserQuestion
81
+ # ============================================================================
82
+
83
+ play_sound() {
84
+ case "$(uname -s)" in
85
+ Darwin)
86
+ # macOS: Use afplay with a distinctive sound for questions
87
+ afplay /System/Library/Sounds/Tink.aiff 2>/dev/null || true
88
+ ;;
89
+ Linux)
90
+ # Linux: Use paplay or aplay
91
+ paplay /usr/share/sounds/freedesktop/stereo/dialog-question.oga 2>/dev/null || \
92
+ paplay /usr/share/sounds/freedesktop/stereo/message-new-instant.oga 2>/dev/null || \
93
+ aplay /usr/share/sounds/alsa/Front_Center.wav 2>/dev/null || true
94
+ ;;
95
+ MINGW*|MSYS*|CYGWIN*)
96
+ # Windows: Use PowerShell
97
+ powershell -c "(New-Object Media.SoundPlayer 'C:\Windows\Media\Windows Notify.wav').PlaySync();" 2>/dev/null || true
98
+ ;;
99
+ esac
100
+ }
101
+
102
+ if [ "$TOOL_NAME" = "AskUserQuestion" ]; then
103
+ echo "[$(date)] 🔔 QUESTION DETECTED! Playing notification sound" >> "$DEBUG_LOG" 2>/dev/null || true
104
+ play_sound
105
+
106
+ # Log this event
107
+ echo "[$(date)] Claude is asking for user input via AskUserQuestion" >> "$DEBUG_LOG" 2>/dev/null || true
108
+ fi
109
+
110
+ # ============================================================================
111
+ # CLEANUP
112
+ # ============================================================================
113
+
114
+ rm -f "$STDIN_DATA"
115
+
116
+ # ============================================================================
117
+ # OUTPUT TO CLAUDE (Always continue)
118
+ # ============================================================================
119
+
120
+ if [ "$TOOL_NAME" = "AskUserQuestion" ]; then
121
+ cat <<EOF
122
+ {
123
+ "continue": true,
124
+ "systemMessage": "🔔 Sound played - user notified of question request"
125
+ }
126
+ EOF
127
+ else
128
+ cat <<EOF
129
+ {
130
+ "continue": true
131
+ }
132
+ EOF
133
+ fi