cc-devflow 1.0.3 → 2.4.1
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/.claude/CLAUDE.md +123 -4
- package/.claude/agents/code-quality-reviewer.md +205 -0
- package/.claude/agents/spec-reviewer.md +221 -0
- package/.claude/commands/cancel-ralph.md +59 -0
- package/.claude/commands/flow-dev.md +202 -21
- package/.claude/commands/flow-epic.md +33 -0
- package/.claude/commands/flow-fix.md +138 -20
- package/.claude/commands/flow-init.md +104 -15
- package/.claude/commands/flow-new.md +84 -35
- package/.claude/commands/flow-prd.md +16 -3
- package/.claude/commands/flow-release.md +33 -0
- package/.claude/commands/flow-review.md +257 -0
- package/.claude/docs/templates/ATTEMPT_TEMPLATE.md +156 -0
- package/.claude/docs/templates/BRAINSTORM_TEMPLATE.md +148 -0
- package/.claude/docs/templates/ERROR_LOG_TEMPLATE.md +80 -0
- package/.claude/docs/templates/INIT_FLOW_TEMPLATE.md +22 -14
- package/.claude/guides/workflow-guides/flow-orchestrator.md +2 -2
- package/.claude/hooks/hooks.json +15 -0
- package/.claude/hooks/ralph-stop-hook.sh +190 -0
- package/.claude/rules/devflow-conventions.md +3 -1
- package/.claude/rules/project-constitution.md +256 -2
- package/.claude/rules/rationalization-library.md +282 -0
- package/.claude/scripts/create-requirement.sh +19 -6
- package/.claude/scripts/setup-ralph-loop.sh +155 -0
- package/.claude/scripts/verify-gate.sh +269 -0
- package/.claude/skills/cc-devflow-orchestrator/SKILL.md +70 -20
- package/.claude/skills/file-header-guardian/SKILL.md +56 -0
- package/.claude/skills/flow-attention-refresh/SKILL.md +170 -0
- package/.claude/skills/flow-brainstorming/SKILL.md +161 -0
- package/.claude/skills/flow-debugging/SKILL.md +221 -0
- package/.claude/skills/flow-finishing-branch/SKILL.md +189 -0
- package/.claude/skills/flow-receiving-review/SKILL.md +153 -0
- package/.claude/skills/flow-tdd/SKILL.md +218 -0
- package/.claude/skills/fractal-docs-generator/SKILL.md +45 -0
- package/.claude/skills/skill-rules.json +75 -0
- package/.claude/skills/verification-before-completion/SKILL.md +158 -0
- package/CHANGELOG.md +17 -1
- package/README.md +104 -19
- package/README.zh-CN.md +79 -1
- package/bin/cc-devflow-cli.js +38 -8
- package/docs/commands/flow-init.md +3 -1
- package/docs/commands/flow-init.zh-CN.md +3 -1
- package/package.json +1 -1
- package/.claude/tsc-cache/777aa1de-497e-411b-a40f-13b74efcec58/affected-repos.txt +0 -1
|
@@ -44,7 +44,7 @@ You MUST follow these rules during orchestration:
|
|
|
44
44
|
|
|
45
45
|
2. **DevFlow Patterns**:
|
|
46
46
|
- Enforce REQ-ID format validation: REQ-\d+
|
|
47
|
-
- Use standard branch naming: feature/${reqId}-${slug(
|
|
47
|
+
- Use standard branch naming: feature/${reqId}-${slug(BRANCH_TITLE_EN)} (模型意译生成,禁止拼音/音译)
|
|
48
48
|
- Apply commit message format: feat(${reqId}): ${taskTitle}
|
|
49
49
|
- Maintain complete document chain: PRD → EPIC → TASKS
|
|
50
50
|
|
|
@@ -96,7 +96,7 @@ Steps:
|
|
|
96
96
|
- Read local .claude/docs/plan/*.md and CLAUDE.md to learn codebase constraints.
|
|
97
97
|
|
|
98
98
|
2) Git branch
|
|
99
|
-
- git switch -c feature/${reqId}-${slug(
|
|
99
|
+
- git switch -c feature/${reqId}-${slug(BRANCH_TITLE_EN)}
|
|
100
100
|
|
|
101
101
|
## 标准作业流程
|
|
102
102
|
|
|
@@ -0,0 +1,190 @@
|
|
|
1
|
+
#!/bin/bash
|
|
2
|
+
|
|
3
|
+
# Ralph Wiggum Stop Hook
|
|
4
|
+
# Prevents session exit when a ralph-loop is active
|
|
5
|
+
# Feeds Claude's output back as input to continue the loop
|
|
6
|
+
|
|
7
|
+
set -euo pipefail
|
|
8
|
+
|
|
9
|
+
# Read hook input from stdin (advanced stop hook API)
|
|
10
|
+
HOOK_INPUT=$(cat)
|
|
11
|
+
|
|
12
|
+
# Check if ralph-loop is active
|
|
13
|
+
RALPH_STATE_FILE=".claude/ralph-loop.local.md"
|
|
14
|
+
|
|
15
|
+
if [[ ! -f "$RALPH_STATE_FILE" ]]; then
|
|
16
|
+
# No active loop - allow exit
|
|
17
|
+
exit 0
|
|
18
|
+
fi
|
|
19
|
+
|
|
20
|
+
# Parse markdown frontmatter (YAML between ---) and extract values
|
|
21
|
+
FRONTMATTER=$(sed -n '/^---$/,/^---$/{ /^---$/d; p; }' "$RALPH_STATE_FILE")
|
|
22
|
+
ITERATION=$(echo "$FRONTMATTER" | grep '^iteration:' | sed 's/iteration: *//')
|
|
23
|
+
MAX_ITERATIONS=$(echo "$FRONTMATTER" | grep '^max_iterations:' | sed 's/max_iterations: *//')
|
|
24
|
+
# Extract completion_promise and strip surrounding quotes if present
|
|
25
|
+
COMPLETION_PROMISE=$(echo "$FRONTMATTER" | grep '^completion_promise:' | sed 's/completion_promise: *//' | sed 's/^"\(.*\)"$/\1/')
|
|
26
|
+
# Extract REQ_ID for CC-DevFlow task status checking
|
|
27
|
+
REQ_ID=$(echo "$FRONTMATTER" | grep '^req_id:' | sed 's/req_id: *//' | sed 's/^"\(.*\)"$/\1/' || echo "")
|
|
28
|
+
|
|
29
|
+
# Validate numeric fields before arithmetic operations
|
|
30
|
+
if [[ ! "$ITERATION" =~ ^[0-9]+$ ]]; then
|
|
31
|
+
echo "⚠️ Ralph loop: State file corrupted" >&2
|
|
32
|
+
echo " File: $RALPH_STATE_FILE" >&2
|
|
33
|
+
echo " Problem: 'iteration' field is not a valid number (got: '$ITERATION')" >&2
|
|
34
|
+
echo "" >&2
|
|
35
|
+
echo " This usually means the state file was manually edited or corrupted." >&2
|
|
36
|
+
echo " Ralph loop is stopping. Run /ralph-loop again to start fresh." >&2
|
|
37
|
+
rm "$RALPH_STATE_FILE"
|
|
38
|
+
exit 0
|
|
39
|
+
fi
|
|
40
|
+
|
|
41
|
+
if [[ ! "$MAX_ITERATIONS" =~ ^[0-9]+$ ]]; then
|
|
42
|
+
echo "⚠️ Ralph loop: State file corrupted" >&2
|
|
43
|
+
echo " File: $RALPH_STATE_FILE" >&2
|
|
44
|
+
echo " Problem: 'max_iterations' field is not a valid number (got: '$MAX_ITERATIONS')" >&2
|
|
45
|
+
echo "" >&2
|
|
46
|
+
echo " This usually means the state file was manually edited or corrupted." >&2
|
|
47
|
+
echo " Ralph loop is stopping. Run /ralph-loop again to start fresh." >&2
|
|
48
|
+
rm "$RALPH_STATE_FILE"
|
|
49
|
+
exit 0
|
|
50
|
+
fi
|
|
51
|
+
|
|
52
|
+
# Check if max iterations reached
|
|
53
|
+
if [[ $MAX_ITERATIONS -gt 0 ]] && [[ $ITERATION -ge $MAX_ITERATIONS ]]; then
|
|
54
|
+
echo "🛑 Ralph loop: Max iterations ($MAX_ITERATIONS) reached."
|
|
55
|
+
rm "$RALPH_STATE_FILE"
|
|
56
|
+
exit 0
|
|
57
|
+
fi
|
|
58
|
+
|
|
59
|
+
# Get transcript path from hook input
|
|
60
|
+
TRANSCRIPT_PATH=$(echo "$HOOK_INPUT" | jq -r '.transcript_path')
|
|
61
|
+
|
|
62
|
+
if [[ ! -f "$TRANSCRIPT_PATH" ]]; then
|
|
63
|
+
echo "⚠️ Ralph loop: Transcript file not found" >&2
|
|
64
|
+
echo " Expected: $TRANSCRIPT_PATH" >&2
|
|
65
|
+
echo " This is unusual and may indicate a Claude Code internal issue." >&2
|
|
66
|
+
echo " Ralph loop is stopping." >&2
|
|
67
|
+
rm "$RALPH_STATE_FILE"
|
|
68
|
+
exit 0
|
|
69
|
+
fi
|
|
70
|
+
|
|
71
|
+
# Read last assistant message from transcript (JSONL format - one JSON per line)
|
|
72
|
+
# First check if there are any assistant messages
|
|
73
|
+
if ! grep -q '"role":"assistant"' "$TRANSCRIPT_PATH"; then
|
|
74
|
+
echo "⚠️ Ralph loop: No assistant messages found in transcript" >&2
|
|
75
|
+
echo " Transcript: $TRANSCRIPT_PATH" >&2
|
|
76
|
+
echo " This is unusual and may indicate a transcript format issue" >&2
|
|
77
|
+
echo " Ralph loop is stopping." >&2
|
|
78
|
+
rm "$RALPH_STATE_FILE"
|
|
79
|
+
exit 0
|
|
80
|
+
fi
|
|
81
|
+
|
|
82
|
+
# Extract last assistant message with explicit error handling
|
|
83
|
+
LAST_LINE=$(grep '"role":"assistant"' "$TRANSCRIPT_PATH" | tail -1)
|
|
84
|
+
if [[ -z "$LAST_LINE" ]]; then
|
|
85
|
+
echo "⚠️ Ralph loop: Failed to extract last assistant message" >&2
|
|
86
|
+
echo " Ralph loop is stopping." >&2
|
|
87
|
+
rm "$RALPH_STATE_FILE"
|
|
88
|
+
exit 0
|
|
89
|
+
fi
|
|
90
|
+
|
|
91
|
+
# Parse JSON with error handling
|
|
92
|
+
LAST_OUTPUT=$(echo "$LAST_LINE" | jq -r '
|
|
93
|
+
.message.content |
|
|
94
|
+
map(select(.type == "text")) |
|
|
95
|
+
map(.text) |
|
|
96
|
+
join("\n")
|
|
97
|
+
' 2>&1)
|
|
98
|
+
|
|
99
|
+
# Check if jq succeeded
|
|
100
|
+
if [[ $? -ne 0 ]]; then
|
|
101
|
+
echo "⚠️ Ralph loop: Failed to parse assistant message JSON" >&2
|
|
102
|
+
echo " Error: $LAST_OUTPUT" >&2
|
|
103
|
+
echo " This may indicate a transcript format issue" >&2
|
|
104
|
+
echo " Ralph loop is stopping." >&2
|
|
105
|
+
rm "$RALPH_STATE_FILE"
|
|
106
|
+
exit 0
|
|
107
|
+
fi
|
|
108
|
+
|
|
109
|
+
if [[ -z "$LAST_OUTPUT" ]]; then
|
|
110
|
+
echo "⚠️ Ralph loop: Assistant message contained no text content" >&2
|
|
111
|
+
echo " Ralph loop is stopping." >&2
|
|
112
|
+
rm "$RALPH_STATE_FILE"
|
|
113
|
+
exit 0
|
|
114
|
+
fi
|
|
115
|
+
|
|
116
|
+
# Check for completion promise (only if set)
|
|
117
|
+
if [[ "$COMPLETION_PROMISE" != "null" ]] && [[ -n "$COMPLETION_PROMISE" ]]; then
|
|
118
|
+
# Extract text from <promise> tags using Perl for multiline support
|
|
119
|
+
# -0777 slurps entire input, s flag makes . match newlines
|
|
120
|
+
# .*? is non-greedy (takes FIRST tag), whitespace normalized
|
|
121
|
+
PROMISE_TEXT=$(echo "$LAST_OUTPUT" | perl -0777 -pe 's/.*?<promise>(.*?)<\/promise>.*/$1/s; s/^\s+|\s+$//g; s/\s+/ /g' 2>/dev/null || echo "")
|
|
122
|
+
|
|
123
|
+
# Use = for literal string comparison (not pattern matching)
|
|
124
|
+
# == in [[ ]] does glob pattern matching which breaks with *, ?, [ characters
|
|
125
|
+
if [[ -n "$PROMISE_TEXT" ]] && [[ "$PROMISE_TEXT" = "$COMPLETION_PROMISE" ]]; then
|
|
126
|
+
echo "✅ Ralph loop: Detected <promise>$COMPLETION_PROMISE</promise>"
|
|
127
|
+
rm "$RALPH_STATE_FILE"
|
|
128
|
+
exit 0
|
|
129
|
+
fi
|
|
130
|
+
fi
|
|
131
|
+
|
|
132
|
+
# CC-DevFlow specific: Check if all tasks completed
|
|
133
|
+
if [[ -n "$REQ_ID" ]] && [[ -f ".claude/scripts/check-task-status.sh" ]]; then
|
|
134
|
+
remaining_count=$(bash .claude/scripts/check-task-status.sh --json 2>/dev/null | jq -r '.remaining' 2>/dev/null || echo "999")
|
|
135
|
+
|
|
136
|
+
if [[ "$remaining_count" == "0" ]]; then
|
|
137
|
+
echo "✅ Ralph loop: All tasks in TASKS.md completed!"
|
|
138
|
+
rm "$RALPH_STATE_FILE"
|
|
139
|
+
exit 0
|
|
140
|
+
fi
|
|
141
|
+
fi
|
|
142
|
+
|
|
143
|
+
# Not complete - continue loop with SAME PROMPT
|
|
144
|
+
NEXT_ITERATION=$((ITERATION + 1))
|
|
145
|
+
|
|
146
|
+
# Extract prompt (everything after the closing ---)
|
|
147
|
+
# Skip first --- line, skip until second --- line, then print everything after
|
|
148
|
+
# Use i>=2 instead of i==2 to handle --- in prompt content
|
|
149
|
+
PROMPT_TEXT=$(awk '/^---$/{i++; next} i>=2' "$RALPH_STATE_FILE")
|
|
150
|
+
|
|
151
|
+
if [[ -z "$PROMPT_TEXT" ]]; then
|
|
152
|
+
echo "⚠️ Ralph loop: State file corrupted or incomplete" >&2
|
|
153
|
+
echo " File: $RALPH_STATE_FILE" >&2
|
|
154
|
+
echo " Problem: No prompt text found" >&2
|
|
155
|
+
echo "" >&2
|
|
156
|
+
echo " This usually means:" >&2
|
|
157
|
+
echo " • State file was manually edited" >&2
|
|
158
|
+
echo " • File was corrupted during writing" >&2
|
|
159
|
+
echo "" >&2
|
|
160
|
+
echo " Ralph loop is stopping. Run /ralph-loop again to start fresh." >&2
|
|
161
|
+
rm "$RALPH_STATE_FILE"
|
|
162
|
+
exit 0
|
|
163
|
+
fi
|
|
164
|
+
|
|
165
|
+
# Update iteration in frontmatter (portable across macOS and Linux)
|
|
166
|
+
# Create temp file, then atomically replace
|
|
167
|
+
TEMP_FILE="${RALPH_STATE_FILE}.tmp.$$"
|
|
168
|
+
sed "s/^iteration: .*/iteration: $NEXT_ITERATION/" "$RALPH_STATE_FILE" > "$TEMP_FILE"
|
|
169
|
+
mv "$TEMP_FILE" "$RALPH_STATE_FILE"
|
|
170
|
+
|
|
171
|
+
# Build system message with iteration count and completion promise info
|
|
172
|
+
if [[ "$COMPLETION_PROMISE" != "null" ]] && [[ -n "$COMPLETION_PROMISE" ]]; then
|
|
173
|
+
SYSTEM_MSG="🔄 Ralph iteration $NEXT_ITERATION | To stop: output <promise>$COMPLETION_PROMISE</promise> (ONLY when statement is TRUE - do not lie to exit!)"
|
|
174
|
+
else
|
|
175
|
+
SYSTEM_MSG="🔄 Ralph iteration $NEXT_ITERATION | No completion promise set - loop runs infinitely"
|
|
176
|
+
fi
|
|
177
|
+
|
|
178
|
+
# Output JSON to block the stop and feed prompt back
|
|
179
|
+
# The "reason" field contains the prompt that will be sent back to Claude
|
|
180
|
+
jq -n \
|
|
181
|
+
--arg prompt "$PROMPT_TEXT" \
|
|
182
|
+
--arg msg "$SYSTEM_MSG" \
|
|
183
|
+
'{
|
|
184
|
+
"decision": "block",
|
|
185
|
+
"reason": $prompt,
|
|
186
|
+
"systemMessage": $msg
|
|
187
|
+
}'
|
|
188
|
+
|
|
189
|
+
# Exit 0 for successful hook execution
|
|
190
|
+
exit 0
|
|
@@ -69,13 +69,15 @@ devflow/requirements/${reqId}/
|
|
|
69
69
|
### 分支命名
|
|
70
70
|
```bash
|
|
71
71
|
# 标准格式
|
|
72
|
-
feature/${reqId}-${slug(
|
|
72
|
+
feature/${reqId}-${slug(BRANCH_TITLE_EN)}
|
|
73
73
|
|
|
74
74
|
# 示例
|
|
75
75
|
feature/REQ-123-user-order-support
|
|
76
76
|
feature/REQ-124-permission-management
|
|
77
77
|
```
|
|
78
78
|
|
|
79
|
+
> BRANCH_TITLE_EN 为 TITLE 的英文意译 (语义为准,非拼音,使用模型意译)
|
|
80
|
+
|
|
79
81
|
### 分支操作流程
|
|
80
82
|
1. 检查当前在 main 分支且状态干净
|
|
81
83
|
2. 创建特性分支
|
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
# CC-DevFlow Project Constitution
|
|
2
2
|
|
|
3
|
-
> **Version**: v2.
|
|
3
|
+
> **Version**: v2.1.0
|
|
4
4
|
> **Effective Date**: 2025-01-10
|
|
5
|
-
> **Last Amended**:
|
|
5
|
+
> **Last Amended**: 2026-01-08
|
|
6
6
|
> **Status**: Active
|
|
7
7
|
> **Amendment Process**: See Section IX
|
|
8
8
|
|
|
@@ -24,6 +24,31 @@ This Constitution establishes the **immutable architectural DNA** of the CC-DevF
|
|
|
24
24
|
|
|
25
25
|
**Principle**: Quality is the non-negotiable baseline.
|
|
26
26
|
|
|
27
|
+
### The Iron Law
|
|
28
|
+
|
|
29
|
+
```
|
|
30
|
+
NO PARTIAL IMPLEMENTATION - COMPLETE OR NOTHING
|
|
31
|
+
```
|
|
32
|
+
|
|
33
|
+
### Rationalization Defense
|
|
34
|
+
|
|
35
|
+
> See [rationalization-library.md](./rationalization-library.md#article-i-quality-first---rationalization-table) for full table.
|
|
36
|
+
|
|
37
|
+
| Excuse | Reality |
|
|
38
|
+
|--------|---------|
|
|
39
|
+
| "This is simplified for now" | CONSTITUTIONAL VIOLATION. Complete it or don't ship it. |
|
|
40
|
+
| "Will complete in v2" | Future versions don't exist. Implement fully now. |
|
|
41
|
+
| "80% is good enough" | 80% = broken for 20% of users. Not good enough. |
|
|
42
|
+
|
|
43
|
+
### Red Flags - STOP
|
|
44
|
+
|
|
45
|
+
If you find yourself thinking:
|
|
46
|
+
- "This is good enough for now"
|
|
47
|
+
- "I'll fix it before PR"
|
|
48
|
+
- "Core logic works, edge cases later"
|
|
49
|
+
|
|
50
|
+
**STOP. You are rationalizing. Complete the implementation or don't ship.**
|
|
51
|
+
|
|
27
52
|
### I.1 Complete Implementation Mandate
|
|
28
53
|
|
|
29
54
|
```yaml
|
|
@@ -70,6 +95,31 @@ All code must pass:
|
|
|
70
95
|
|
|
71
96
|
**Principle**: Maintain codebase uniformity and predictability.
|
|
72
97
|
|
|
98
|
+
### The Iron Law
|
|
99
|
+
|
|
100
|
+
```
|
|
101
|
+
REUSE EXISTING CODE - NO DUPLICATION
|
|
102
|
+
```
|
|
103
|
+
|
|
104
|
+
### Rationalization Defense
|
|
105
|
+
|
|
106
|
+
> See [rationalization-library.md](./rationalization-library.md#article-ii-architectural-consistency---rationalization-table) for full table.
|
|
107
|
+
|
|
108
|
+
| Excuse | Reality |
|
|
109
|
+
|--------|---------|
|
|
110
|
+
| "Faster to rewrite" | Faster now = slower forever. Find and reuse. |
|
|
111
|
+
| "Slightly different use case" | Extract common, parameterize difference. |
|
|
112
|
+
| "I understand my version better" | Understand the shared version. That's your job. |
|
|
113
|
+
|
|
114
|
+
### Red Flags - STOP
|
|
115
|
+
|
|
116
|
+
If you find yourself thinking:
|
|
117
|
+
- "That code is messy, I'll write my own"
|
|
118
|
+
- "I don't have time to search"
|
|
119
|
+
- "It's just a small function"
|
|
120
|
+
|
|
121
|
+
**STOP. Search the codebase. Reuse or refactor existing code.**
|
|
122
|
+
|
|
73
123
|
### II.1 No Code Duplication
|
|
74
124
|
|
|
75
125
|
```yaml
|
|
@@ -136,6 +186,31 @@ MODULE COHESION:
|
|
|
136
186
|
|
|
137
187
|
**Principle**: Security is foundational, not an afterthought.
|
|
138
188
|
|
|
189
|
+
### The Iron Law
|
|
190
|
+
|
|
191
|
+
```
|
|
192
|
+
NO HARDCODED SECRETS - ENVIRONMENT VARIABLES ONLY
|
|
193
|
+
```
|
|
194
|
+
|
|
195
|
+
### Rationalization Defense
|
|
196
|
+
|
|
197
|
+
> See [rationalization-library.md](./rationalization-library.md#article-iii-security-first---rationalization-table) for full table.
|
|
198
|
+
|
|
199
|
+
| Excuse | Reality |
|
|
200
|
+
|--------|---------|
|
|
201
|
+
| "It's just for testing" | Commits are forever. Use env vars even for tests. |
|
|
202
|
+
| "I'll remove it before commit" | You won't. You'll forget. Use env vars. |
|
|
203
|
+
| "Local development only" | Local becomes production. Start secure. |
|
|
204
|
+
|
|
205
|
+
### Red Flags - STOP
|
|
206
|
+
|
|
207
|
+
If you find yourself thinking:
|
|
208
|
+
- "Nobody will see the repo"
|
|
209
|
+
- "It's not a real secret"
|
|
210
|
+
- "I'll rotate it later"
|
|
211
|
+
|
|
212
|
+
**STOP. Never commit secrets. Use environment variables from the start.**
|
|
213
|
+
|
|
139
214
|
### III.1 No Hardcoded Secrets
|
|
140
215
|
|
|
141
216
|
```yaml
|
|
@@ -200,6 +275,31 @@ DEFAULT SECURITY:
|
|
|
200
275
|
|
|
201
276
|
**Principle**: Performance is user experience; proactive optimization required.
|
|
202
277
|
|
|
278
|
+
### The Iron Law
|
|
279
|
+
|
|
280
|
+
```
|
|
281
|
+
NO RESOURCE LEAKS - ALWAYS CLEANUP
|
|
282
|
+
```
|
|
283
|
+
|
|
284
|
+
### Rationalization Defense
|
|
285
|
+
|
|
286
|
+
> See [rationalization-library.md](./rationalization-library.md#article-iv-performance-accountability---rationalization-table) for full table.
|
|
287
|
+
|
|
288
|
+
| Excuse | Reality |
|
|
289
|
+
|--------|---------|
|
|
290
|
+
| "Garbage collector will handle it" | GC doesn't close files/connections. Explicit cleanup. |
|
|
291
|
+
| "Small leak, won't matter" | Small leaks become big crashes. Fix now. |
|
|
292
|
+
| "Framework handles it" | Verify that. Don't assume. |
|
|
293
|
+
|
|
294
|
+
### Red Flags - STOP
|
|
295
|
+
|
|
296
|
+
If you find yourself thinking:
|
|
297
|
+
- "It's a short-lived process"
|
|
298
|
+
- "I'll add cleanup later"
|
|
299
|
+
- "Only happens in edge case"
|
|
300
|
+
|
|
301
|
+
**STOP. Add cleanup with creation. Edge cases run in production.**
|
|
302
|
+
|
|
203
303
|
### IV.1 No Resource Leaks
|
|
204
304
|
|
|
205
305
|
```yaml
|
|
@@ -272,6 +372,31 @@ INTELLIGENT CACHING:
|
|
|
272
372
|
|
|
273
373
|
**Principle**: Code must be understandable, modifiable, and extensible.
|
|
274
374
|
|
|
375
|
+
### The Iron Law
|
|
376
|
+
|
|
377
|
+
```
|
|
378
|
+
NO DEAD CODE - USE IT OR DELETE IT
|
|
379
|
+
```
|
|
380
|
+
|
|
381
|
+
### Rationalization Defense
|
|
382
|
+
|
|
383
|
+
> See [rationalization-library.md](./rationalization-library.md#article-v-maintainability---rationalization-table) for full table.
|
|
384
|
+
|
|
385
|
+
| Excuse | Reality |
|
|
386
|
+
|--------|---------|
|
|
387
|
+
| "Might need it later" | Git history exists. Delete now, retrieve if needed. |
|
|
388
|
+
| "It's just commented out" | Commented code = noise. Delete it. |
|
|
389
|
+
| "Too risky to delete" | Tests exist. If tests pass after delete, it's safe. |
|
|
390
|
+
|
|
391
|
+
### Red Flags - STOP
|
|
392
|
+
|
|
393
|
+
If you find yourself thinking:
|
|
394
|
+
- "Reference for future work"
|
|
395
|
+
- "Someone else might need it"
|
|
396
|
+
- "I worked hard on this"
|
|
397
|
+
|
|
398
|
+
**STOP. Sunk cost fallacy. Delete dead code. Git remembers.**
|
|
399
|
+
|
|
275
400
|
### V.1 No Dead Code
|
|
276
401
|
|
|
277
402
|
```yaml
|
|
@@ -340,6 +465,33 @@ SIZE CONSTRAINTS:
|
|
|
340
465
|
|
|
341
466
|
**Principle**: Tests define behavior; implementation makes tests pass.
|
|
342
467
|
|
|
468
|
+
### The Iron Law
|
|
469
|
+
|
|
470
|
+
```
|
|
471
|
+
NO PRODUCTION CODE WITHOUT A FAILING TEST FIRST
|
|
472
|
+
```
|
|
473
|
+
|
|
474
|
+
### Rationalization Defense
|
|
475
|
+
|
|
476
|
+
> See [rationalization-library.md](./rationalization-library.md#article-vi-test-first-development---rationalization-table) for full table.
|
|
477
|
+
|
|
478
|
+
| Excuse | Reality |
|
|
479
|
+
|--------|---------|
|
|
480
|
+
| "Too simple to test" | Simple code breaks. Test takes 30 seconds. |
|
|
481
|
+
| "I'll test after" | Tests passing immediately prove nothing. |
|
|
482
|
+
| "TDD slows me down" | TDD faster than debugging. Pragmatic = test-first. |
|
|
483
|
+
| "This is different because..." | No. This is rationalization. Follow the law. |
|
|
484
|
+
|
|
485
|
+
### Red Flags - STOP
|
|
486
|
+
|
|
487
|
+
If you find yourself thinking:
|
|
488
|
+
- "Just this once"
|
|
489
|
+
- "I'm being pragmatic, not dogmatic"
|
|
490
|
+
- "Spirit not letter"
|
|
491
|
+
- "Need to explore first" (without deleting exploration code)
|
|
492
|
+
|
|
493
|
+
**STOP. You are rationalizing. Delete the code. Write the test first.**
|
|
494
|
+
|
|
343
495
|
### VI.1 TDD Mandate (NON-NEGOTIABLE)
|
|
344
496
|
|
|
345
497
|
```yaml
|
|
@@ -399,6 +551,31 @@ TEST QUALITY:
|
|
|
399
551
|
|
|
400
552
|
**Principle**: Default to simplicity; complexity requires justification.
|
|
401
553
|
|
|
554
|
+
### The Iron Law
|
|
555
|
+
|
|
556
|
+
```
|
|
557
|
+
MAXIMUM 3 PROJECTS - JUSTIFY ANY ADDITIONAL COMPLEXITY
|
|
558
|
+
```
|
|
559
|
+
|
|
560
|
+
### Rationalization Defense
|
|
561
|
+
|
|
562
|
+
> See [rationalization-library.md](./rationalization-library.md#article-vii-simplicity-gate---rationalization-table) for full table.
|
|
563
|
+
|
|
564
|
+
| Excuse | Reality |
|
|
565
|
+
|--------|---------|
|
|
566
|
+
| "Microservices are better" | For your scale? Monolith is simpler. Start there. |
|
|
567
|
+
| "Future scalability" | YAGNI. Scale when you need to. |
|
|
568
|
+
| "Best practices say..." | Best practices assume scale you don't have. |
|
|
569
|
+
|
|
570
|
+
### Red Flags - STOP
|
|
571
|
+
|
|
572
|
+
If you find yourself thinking:
|
|
573
|
+
- "Separation of concerns" (as justification for new project)
|
|
574
|
+
- "Team autonomy"
|
|
575
|
+
- "We might need it"
|
|
576
|
+
|
|
577
|
+
**STOP. Build for now. Refactor when needed. Complexity is the enemy.**
|
|
578
|
+
|
|
402
579
|
### VII.1 Project Count Limit
|
|
403
580
|
|
|
404
581
|
```yaml
|
|
@@ -434,6 +611,31 @@ YAGNI ENFORCEMENT:
|
|
|
434
611
|
|
|
435
612
|
**Principle**: Trust frameworks; avoid unnecessary wrapping.
|
|
436
613
|
|
|
614
|
+
### The Iron Law
|
|
615
|
+
|
|
616
|
+
```
|
|
617
|
+
USE FRAMEWORKS DIRECTLY - NO UNNECESSARY WRAPPERS
|
|
618
|
+
```
|
|
619
|
+
|
|
620
|
+
### Rationalization Defense
|
|
621
|
+
|
|
622
|
+
> See [rationalization-library.md](./rationalization-library.md#article-viii-anti-abstraction---rationalization-table) for full table.
|
|
623
|
+
|
|
624
|
+
| Excuse | Reality |
|
|
625
|
+
|--------|---------|
|
|
626
|
+
| "Abstraction for future flexibility" | YAGNI. You won't switch frameworks. |
|
|
627
|
+
| "Cleaner interface" | Framework interface IS clean. Learn it. |
|
|
628
|
+
| "Easier testing" | Mock the framework. Don't wrap it. |
|
|
629
|
+
|
|
630
|
+
### Red Flags - STOP
|
|
631
|
+
|
|
632
|
+
If you find yourself thinking:
|
|
633
|
+
- "Hide implementation details"
|
|
634
|
+
- "Consistent with other projects"
|
|
635
|
+
- "Best practice pattern"
|
|
636
|
+
|
|
637
|
+
**STOP. Use the framework directly. Wrappers add complexity, not value.**
|
|
638
|
+
|
|
437
639
|
### VIII.1 Direct Framework Usage
|
|
438
640
|
|
|
439
641
|
```yaml
|
|
@@ -470,6 +672,31 @@ ONE ENTITY, ONE REPRESENTATION:
|
|
|
470
672
|
|
|
471
673
|
**Principle**: Test with real environments, not mocks.
|
|
472
674
|
|
|
675
|
+
### The Iron Law
|
|
676
|
+
|
|
677
|
+
```
|
|
678
|
+
CONTRACTS FIRST - REAL ENVIRONMENTS
|
|
679
|
+
```
|
|
680
|
+
|
|
681
|
+
### Rationalization Defense
|
|
682
|
+
|
|
683
|
+
> See [rationalization-library.md](./rationalization-library.md#article-ix-integration-first-testing---rationalization-table) for full table.
|
|
684
|
+
|
|
685
|
+
| Excuse | Reality |
|
|
686
|
+
|--------|---------|
|
|
687
|
+
| "Unit tests are faster" | Fast wrong tests waste time. Integration tests catch real bugs. |
|
|
688
|
+
| "Mocks are simpler" | Mocks hide integration issues. Real databases find them. |
|
|
689
|
+
| "In-memory database works" | In-memory differs from production. Test with real DB. |
|
|
690
|
+
|
|
691
|
+
### Red Flags - STOP
|
|
692
|
+
|
|
693
|
+
If you find yourself thinking:
|
|
694
|
+
- "CI is slow"
|
|
695
|
+
- "Docker is complex"
|
|
696
|
+
- "We can mock this"
|
|
697
|
+
|
|
698
|
+
**STOP. Production bugs are expensive. Test with real environments.**
|
|
699
|
+
|
|
473
700
|
### IX.1 Contract-First
|
|
474
701
|
|
|
475
702
|
```yaml
|
|
@@ -507,6 +734,32 @@ INTEGRATION TESTING:
|
|
|
507
734
|
|
|
508
735
|
**Principle**: Implement what's requested, nothing more.
|
|
509
736
|
|
|
737
|
+
### The Iron Law
|
|
738
|
+
|
|
739
|
+
```
|
|
740
|
+
IMPLEMENT WHAT'S REQUESTED, NOTHING MORE
|
|
741
|
+
```
|
|
742
|
+
|
|
743
|
+
### Rationalization Defense
|
|
744
|
+
|
|
745
|
+
> See [rationalization-library.md](./rationalization-library.md#article-x-requirement-boundary---rationalization-table) for full table.
|
|
746
|
+
|
|
747
|
+
| Excuse | Reality |
|
|
748
|
+
|--------|---------|
|
|
749
|
+
| "User might need this later" | User didn't ask. Don't add. YAGNI. |
|
|
750
|
+
| "It's just a small addition" | Small additions compound. Scope creep. |
|
|
751
|
+
| "I'm being helpful" | Helpful = following spec. Unhelpful = scope creep. |
|
|
752
|
+
|
|
753
|
+
### Red Flags - STOP
|
|
754
|
+
|
|
755
|
+
If you find yourself thinking:
|
|
756
|
+
- "While I'm here anyway"
|
|
757
|
+
- "It's only 5 more lines"
|
|
758
|
+
- "User will thank me"
|
|
759
|
+
- "This is a natural extension"
|
|
760
|
+
|
|
761
|
+
**STOP. Stay on task. Create separate requirement for extensions.**
|
|
762
|
+
|
|
510
763
|
### X.1 Forced Clarification
|
|
511
764
|
|
|
512
765
|
```yaml
|
|
@@ -744,5 +997,6 @@ This Constitution is the **architectural DNA** of CC-DevFlow. All templates, age
|
|
|
744
997
|
*CC-DevFlow Project Constitution - Ensuring Excellence, Rejecting Compromise*
|
|
745
998
|
|
|
746
999
|
**Version History**:
|
|
1000
|
+
- v2.1.0 (2026-01-08): Added Iron Law + Rationalization Defense + Red Flags to all 10 Articles
|
|
747
1001
|
- v2.0.0 (2025-10-09): Article-based restructure, enforcement mechanisms, amendment process
|
|
748
1002
|
- v1.0.0 (2025-01-20): Initial version with five core principles
|