opencode-swarm-plugin 0.44.1 → 0.45.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/README.md +277 -54
- package/bin/swarm.ts +3 -3
- package/dist/decision-trace-integration.d.ts +204 -0
- package/dist/decision-trace-integration.d.ts.map +1 -0
- package/dist/hive.d.ts.map +1 -1
- package/dist/hive.js +14834 -0
- package/dist/index.d.ts +50 -2
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +640 -27
- package/dist/plugin.js +395 -27
- package/dist/query-tools.d.ts +20 -12
- package/dist/query-tools.d.ts.map +1 -1
- package/dist/swarm-decompose.d.ts +4 -4
- package/dist/swarm-decompose.d.ts.map +1 -1
- package/dist/swarm-prompts.d.ts.map +1 -1
- package/dist/swarm-prompts.js +39605 -0
- package/dist/swarm-review.d.ts.map +1 -1
- package/dist/swarm-signature.d.ts +106 -0
- package/dist/swarm-signature.d.ts.map +1 -0
- package/dist/swarm-strategies.d.ts +16 -3
- package/dist/swarm-strategies.d.ts.map +1 -1
- package/dist/swarm-validation.d.ts +127 -0
- package/dist/swarm-validation.d.ts.map +1 -0
- package/dist/swarm.d.ts +4 -2
- package/dist/swarm.d.ts.map +1 -1
- package/dist/validators/index.d.ts +7 -0
- package/dist/validators/index.d.ts.map +1 -0
- package/dist/validators/schema-validator.d.ts +58 -0
- package/dist/validators/schema-validator.d.ts.map +1 -0
- package/examples/commands/swarm.md +745 -0
- package/examples/plugin-wrapper-template.ts +2611 -0
- package/examples/skills/hive-workflow/SKILL.md +212 -0
- package/examples/skills/skill-creator/SKILL.md +223 -0
- package/examples/skills/swarm-coordination/SKILL.md +292 -0
- package/global-skills/cli-builder/SKILL.md +344 -0
- package/global-skills/cli-builder/references/advanced-patterns.md +244 -0
- package/global-skills/learning-systems/SKILL.md +644 -0
- package/global-skills/skill-creator/LICENSE.txt +202 -0
- package/global-skills/skill-creator/SKILL.md +352 -0
- package/global-skills/skill-creator/references/output-patterns.md +82 -0
- package/global-skills/skill-creator/references/workflows.md +28 -0
- package/global-skills/swarm-coordination/SKILL.md +995 -0
- package/global-skills/swarm-coordination/references/coordinator-patterns.md +235 -0
- package/global-skills/swarm-coordination/references/strategies.md +138 -0
- package/global-skills/system-design/SKILL.md +213 -0
- package/global-skills/testing-patterns/SKILL.md +430 -0
- package/global-skills/testing-patterns/references/dependency-breaking-catalog.md +586 -0
- package/package.json +6 -3
|
@@ -0,0 +1,235 @@
|
|
|
1
|
+
# Coordinator Patterns
|
|
2
|
+
|
|
3
|
+
The coordinator is the orchestration layer that manages the swarm. This document covers the coordinator's responsibilities, decision points, and intervention patterns.
|
|
4
|
+
|
|
5
|
+
## Coordinator Responsibilities
|
|
6
|
+
|
|
7
|
+
### 1. Knowledge Gathering (BEFORE decomposition)
|
|
8
|
+
|
|
9
|
+
**MANDATORY**: Before decomposing any task, the coordinator MUST query all available knowledge sources:
|
|
10
|
+
|
|
11
|
+
```
|
|
12
|
+
# 1. Search semantic memory for past learnings
|
|
13
|
+
semantic-memory_find(query="<task keywords>", limit=5)
|
|
14
|
+
|
|
15
|
+
# 2. Search CASS for similar past tasks
|
|
16
|
+
cass_search(query="<task description>", limit=5)
|
|
17
|
+
|
|
18
|
+
# 3. Search pdf-brain for design patterns and prior art
|
|
19
|
+
pdf-brain_search(query="<domain concepts>", limit=5)
|
|
20
|
+
|
|
21
|
+
# 4. List available skills
|
|
22
|
+
skills_list()
|
|
23
|
+
```
|
|
24
|
+
|
|
25
|
+
**Why this matters:** From "Patterns for Building AI Agents":
|
|
26
|
+
|
|
27
|
+
> "AI agents, like people, make better decisions when they understand the full context rather than working from fragments."
|
|
28
|
+
|
|
29
|
+
The coordinator synthesizes findings into `shared_context` that all workers receive.
|
|
30
|
+
|
|
31
|
+
### 2. Task Decomposition
|
|
32
|
+
|
|
33
|
+
After knowledge gathering:
|
|
34
|
+
|
|
35
|
+
1. Select strategy (auto or explicit)
|
|
36
|
+
2. Generate decomposition with `swarm_plan_prompt` or `swarm_decompose`
|
|
37
|
+
3. Validate with `swarm_validate_decomposition`
|
|
38
|
+
4. Create cells with `hive_create_epic`
|
|
39
|
+
|
|
40
|
+
### 3. Worker Spawning
|
|
41
|
+
|
|
42
|
+
For each subtask:
|
|
43
|
+
|
|
44
|
+
1. Generate worker prompt with `swarm_spawn_subtask`
|
|
45
|
+
2. Include relevant skills in prompt
|
|
46
|
+
3. Spawn worker agent via Task tool
|
|
47
|
+
4. Track bead status
|
|
48
|
+
|
|
49
|
+
### 4. Progress Monitoring
|
|
50
|
+
|
|
51
|
+
- Check `hive_query(status="in_progress")` for active work
|
|
52
|
+
- Check `swarmmail_inbox()` for worker messages
|
|
53
|
+
- Intervene on blockers (see Intervention Patterns below)
|
|
54
|
+
|
|
55
|
+
### 5. Completion & Aggregation
|
|
56
|
+
|
|
57
|
+
- Verify all subtasks completed via bead status
|
|
58
|
+
- Aggregate results from worker summaries
|
|
59
|
+
- Run final verification (typecheck, tests)
|
|
60
|
+
- Close epic bead with summary
|
|
61
|
+
|
|
62
|
+
---
|
|
63
|
+
|
|
64
|
+
## Decision Points
|
|
65
|
+
|
|
66
|
+
### When to Swarm vs Single Agent
|
|
67
|
+
|
|
68
|
+
**Swarm when:**
|
|
69
|
+
|
|
70
|
+
- 3+ files need modification
|
|
71
|
+
- Task has natural parallel boundaries
|
|
72
|
+
- Different specializations needed (frontend/backend/tests)
|
|
73
|
+
- Time-to-completion matters
|
|
74
|
+
|
|
75
|
+
**Single agent when:**
|
|
76
|
+
|
|
77
|
+
- Task touches 1-2 files
|
|
78
|
+
- Heavy sequential dependencies
|
|
79
|
+
- Coordination overhead > parallelization benefit
|
|
80
|
+
- Task requires tight feedback loop
|
|
81
|
+
|
|
82
|
+
**Heuristic:** If you can describe the task in one sentence without "and", probably single agent.
|
|
83
|
+
|
|
84
|
+
### When to Intervene
|
|
85
|
+
|
|
86
|
+
| Signal | Action |
|
|
87
|
+
| ------------------------- | ----------------------------------------------------- |
|
|
88
|
+
| Worker blocked >5 min | Check inbox, offer guidance |
|
|
89
|
+
| File conflict detected | Mediate, reassign files |
|
|
90
|
+
| Worker asking questions | Answer directly, don't spawn new agent |
|
|
91
|
+
| Scope creep detected | Redirect to original task, create new bead for extras |
|
|
92
|
+
| Worker failing repeatedly | Take over subtask or reassign |
|
|
93
|
+
|
|
94
|
+
### When to Abort
|
|
95
|
+
|
|
96
|
+
- Critical blocker affects all subtasks
|
|
97
|
+
- Scope changed fundamentally mid-swarm
|
|
98
|
+
- Resource exhaustion (context, time, cost)
|
|
99
|
+
|
|
100
|
+
On abort: Close all cells with reason, summarize partial progress.
|
|
101
|
+
|
|
102
|
+
---
|
|
103
|
+
|
|
104
|
+
## Context Engineering
|
|
105
|
+
|
|
106
|
+
From "Patterns for Building AI Agents":
|
|
107
|
+
|
|
108
|
+
> "Instead of just instructing subagents 'Do this specific task,' you should try to ensure they are able to share context along the way."
|
|
109
|
+
|
|
110
|
+
### Shared Context Template
|
|
111
|
+
|
|
112
|
+
```markdown
|
|
113
|
+
## Project Context
|
|
114
|
+
|
|
115
|
+
- Repository: {repo_name}
|
|
116
|
+
- Tech stack: {stack}
|
|
117
|
+
- Relevant patterns: {patterns from pdf-brain}
|
|
118
|
+
|
|
119
|
+
## Task Context
|
|
120
|
+
|
|
121
|
+
- Epic: {epic_title}
|
|
122
|
+
- Goal: {what success looks like}
|
|
123
|
+
- Constraints: {time, scope, dependencies}
|
|
124
|
+
|
|
125
|
+
## Prior Art
|
|
126
|
+
|
|
127
|
+
- Similar past tasks: {from CASS}
|
|
128
|
+
- Relevant learnings: {from semantic-memory}
|
|
129
|
+
|
|
130
|
+
## Coordination
|
|
131
|
+
|
|
132
|
+
- Other active subtasks: {list}
|
|
133
|
+
- Shared files to avoid: {reserved files}
|
|
134
|
+
- Communication channel: thread_id={epic_id}
|
|
135
|
+
```
|
|
136
|
+
|
|
137
|
+
### Context Compression
|
|
138
|
+
|
|
139
|
+
For long-running swarms, compress context periodically:
|
|
140
|
+
|
|
141
|
+
- Summarize completed subtasks (don't list all details)
|
|
142
|
+
- Keep only active blockers and decisions
|
|
143
|
+
- Preserve key learnings for remaining work
|
|
144
|
+
|
|
145
|
+
---
|
|
146
|
+
|
|
147
|
+
## Failure Modes & Recovery
|
|
148
|
+
|
|
149
|
+
### Incompatible Parallel Outputs
|
|
150
|
+
|
|
151
|
+
**Problem:** Two agents produce conflicting results that can't be merged.
|
|
152
|
+
|
|
153
|
+
**From "Patterns for Building AI Agents":**
|
|
154
|
+
|
|
155
|
+
> "Subagents can create responses that are in conflict — forcing the final agent to combine two incompatible, intermediate products."
|
|
156
|
+
|
|
157
|
+
**Prevention:**
|
|
158
|
+
|
|
159
|
+
- Clear file boundaries (no overlap)
|
|
160
|
+
- Explicit interface contracts in shared_context
|
|
161
|
+
- Sequential phases for tightly coupled work
|
|
162
|
+
|
|
163
|
+
**Recovery:**
|
|
164
|
+
|
|
165
|
+
- Identify conflict source
|
|
166
|
+
- Pick one approach, discard other
|
|
167
|
+
- Re-run losing subtask with winning approach as constraint
|
|
168
|
+
|
|
169
|
+
### Worker Drift
|
|
170
|
+
|
|
171
|
+
**Problem:** Worker goes off-task, implements something different.
|
|
172
|
+
|
|
173
|
+
**Prevention:**
|
|
174
|
+
|
|
175
|
+
- Specific, actionable subtask descriptions
|
|
176
|
+
- Clear success criteria in prompt
|
|
177
|
+
- File list as hard constraint
|
|
178
|
+
|
|
179
|
+
**Recovery:**
|
|
180
|
+
|
|
181
|
+
- Revert changes
|
|
182
|
+
- Re-run with more explicit instructions
|
|
183
|
+
- Consider taking over manually
|
|
184
|
+
|
|
185
|
+
### Cascade Failure
|
|
186
|
+
|
|
187
|
+
**Problem:** One failure blocks multiple dependent subtasks.
|
|
188
|
+
|
|
189
|
+
**Prevention:**
|
|
190
|
+
|
|
191
|
+
- Minimize dependencies in decomposition
|
|
192
|
+
- Front-load risky/uncertain work
|
|
193
|
+
- Have fallback plans for critical paths
|
|
194
|
+
|
|
195
|
+
**Recovery:**
|
|
196
|
+
|
|
197
|
+
- Unblock manually if possible
|
|
198
|
+
- Reassign dependent work
|
|
199
|
+
- Partial completion is okay - close what's done
|
|
200
|
+
|
|
201
|
+
---
|
|
202
|
+
|
|
203
|
+
## Anti-Patterns
|
|
204
|
+
|
|
205
|
+
### The Mega-Coordinator
|
|
206
|
+
|
|
207
|
+
**Problem:** Coordinator does too much work itself instead of delegating.
|
|
208
|
+
|
|
209
|
+
**Symptom:** Coordinator editing files, running tests, debugging.
|
|
210
|
+
|
|
211
|
+
**Fix:** Coordinator only orchestrates. If you're writing code, you're a worker.
|
|
212
|
+
|
|
213
|
+
### The Silent Swarm
|
|
214
|
+
|
|
215
|
+
**Problem:** Workers don't communicate, coordinator doesn't monitor.
|
|
216
|
+
|
|
217
|
+
**Symptom:** Swarm runs for 30 minutes, then fails with conflicts.
|
|
218
|
+
|
|
219
|
+
**Fix:** Require progress updates. Check inbox regularly. Intervene early.
|
|
220
|
+
|
|
221
|
+
### The Over-Decomposed Task
|
|
222
|
+
|
|
223
|
+
**Problem:** 10 subtasks for a 20-line change.
|
|
224
|
+
|
|
225
|
+
**Symptom:** Coordination overhead exceeds actual work.
|
|
226
|
+
|
|
227
|
+
**Fix:** 2-5 subtasks is the sweet spot. If task is small, don't swarm.
|
|
228
|
+
|
|
229
|
+
### The Under-Specified Subtask
|
|
230
|
+
|
|
231
|
+
**Problem:** "Implement the backend" with no details.
|
|
232
|
+
|
|
233
|
+
**Symptom:** Worker asks questions, guesses wrong, or stalls.
|
|
234
|
+
|
|
235
|
+
**Fix:** Each subtask needs: clear goal, file list, success criteria, context.
|
|
@@ -0,0 +1,138 @@
|
|
|
1
|
+
# Decomposition Strategies
|
|
2
|
+
|
|
3
|
+
Four strategies for breaking tasks into parallelizable subtasks. The coordinator auto-selects based on task keywords, or you can specify explicitly.
|
|
4
|
+
|
|
5
|
+
## File-Based Strategy
|
|
6
|
+
|
|
7
|
+
**Best for:** Refactoring, migrations, pattern changes across codebase
|
|
8
|
+
|
|
9
|
+
**Keywords:** refactor, migrate, update all, rename, replace, convert, upgrade, deprecate, remove, cleanup, lint, format
|
|
10
|
+
|
|
11
|
+
### Guidelines
|
|
12
|
+
|
|
13
|
+
- Group files by directory or type (e.g., all components, all tests)
|
|
14
|
+
- Minimize cross-directory dependencies within a subtask
|
|
15
|
+
- Handle shared types/utilities FIRST if they change
|
|
16
|
+
- Each subtask should be a complete transformation of its file set
|
|
17
|
+
- Consider import/export relationships when grouping
|
|
18
|
+
|
|
19
|
+
### Anti-Patterns
|
|
20
|
+
|
|
21
|
+
- Don't split tightly coupled files across subtasks
|
|
22
|
+
- Don't group files that have no relationship
|
|
23
|
+
- Don't forget to update imports when moving/renaming
|
|
24
|
+
|
|
25
|
+
### Examples
|
|
26
|
+
|
|
27
|
+
| Task | Decomposition |
|
|
28
|
+
| ----------------------------------- | --------------------------------------------- |
|
|
29
|
+
| Migrate all components to new API | Split by component directory |
|
|
30
|
+
| Rename `userId` to `accountId` | Split by module (types first, then consumers) |
|
|
31
|
+
| Update all tests to use new matcher | Split by test directory |
|
|
32
|
+
|
|
33
|
+
---
|
|
34
|
+
|
|
35
|
+
## Feature-Based Strategy
|
|
36
|
+
|
|
37
|
+
**Best for:** New features, adding functionality, vertical slices
|
|
38
|
+
|
|
39
|
+
**Keywords:** add, implement, build, create, feature, new, integrate, connect, enable, support
|
|
40
|
+
|
|
41
|
+
### Guidelines
|
|
42
|
+
|
|
43
|
+
- Each subtask is a complete vertical slice (UI + logic + data)
|
|
44
|
+
- Start with data layer/types, then logic, then UI
|
|
45
|
+
- Keep related components together (form + validation + submission)
|
|
46
|
+
- Separate concerns that can be developed independently
|
|
47
|
+
- Consider user-facing features as natural boundaries
|
|
48
|
+
|
|
49
|
+
### Anti-Patterns
|
|
50
|
+
|
|
51
|
+
- Don't split a single feature across multiple subtasks
|
|
52
|
+
- Don't create subtasks that can't be tested independently
|
|
53
|
+
- Don't forget integration points between features
|
|
54
|
+
|
|
55
|
+
### Examples
|
|
56
|
+
|
|
57
|
+
| Task | Decomposition |
|
|
58
|
+
| --------------- | ---------------------------------------------------- |
|
|
59
|
+
| Add user auth | [OAuth setup, Session management, Protected routes] |
|
|
60
|
+
| Build dashboard | [Data fetching, Chart components, Layout/navigation] |
|
|
61
|
+
| Add search | [Search API, Search UI, Results display] |
|
|
62
|
+
|
|
63
|
+
---
|
|
64
|
+
|
|
65
|
+
## Risk-Based Strategy
|
|
66
|
+
|
|
67
|
+
**Best for:** Bug fixes, security issues, critical changes, hotfixes
|
|
68
|
+
|
|
69
|
+
**Keywords:** fix, bug, security, vulnerability, critical, urgent, hotfix, patch, audit, review
|
|
70
|
+
|
|
71
|
+
### Guidelines
|
|
72
|
+
|
|
73
|
+
- Write tests FIRST to capture expected behavior
|
|
74
|
+
- Isolate the risky change to minimize blast radius
|
|
75
|
+
- Add monitoring/logging around the change
|
|
76
|
+
- Create rollback plan as part of the task
|
|
77
|
+
- Audit similar code for the same issue
|
|
78
|
+
|
|
79
|
+
### Anti-Patterns
|
|
80
|
+
|
|
81
|
+
- Don't make multiple risky changes in one subtask
|
|
82
|
+
- Don't skip tests for "simple" fixes
|
|
83
|
+
- Don't forget to check for similar issues elsewhere
|
|
84
|
+
|
|
85
|
+
### Examples
|
|
86
|
+
|
|
87
|
+
| Task | Decomposition |
|
|
88
|
+
| ------------------ | ------------------------------------------------------------------------- |
|
|
89
|
+
| Fix auth bypass | [Add regression test, Fix vulnerability, Audit similar endpoints] |
|
|
90
|
+
| Fix race condition | [Add test reproducing issue, Implement fix, Add concurrency tests] |
|
|
91
|
+
| Security audit | [Scan for vulnerabilities, Fix critical issues, Document remaining risks] |
|
|
92
|
+
|
|
93
|
+
---
|
|
94
|
+
|
|
95
|
+
## Research-Based Strategy
|
|
96
|
+
|
|
97
|
+
**Best for:** Investigation, learning, discovery, debugging options
|
|
98
|
+
|
|
99
|
+
**Keywords:** research, investigate, explore, find out, discover, understand, learn about, analyze, compare, evaluate, study, debug options, configuration options
|
|
100
|
+
|
|
101
|
+
### Guidelines
|
|
102
|
+
|
|
103
|
+
- Split by information source (PDFs, repos, history, web)
|
|
104
|
+
- Each agent searches with different query angles
|
|
105
|
+
- Include a synthesis subtask that depends on all search subtasks
|
|
106
|
+
- Use pdf-brain for documentation/books if available
|
|
107
|
+
- Use repo-crawl for GitHub repos if URL provided
|
|
108
|
+
- Use CASS for past agent session history
|
|
109
|
+
- Assign NO files to research subtasks (read-only)
|
|
110
|
+
|
|
111
|
+
### Anti-Patterns
|
|
112
|
+
|
|
113
|
+
- Don't have one agent search everything sequentially
|
|
114
|
+
- Don't skip synthesis - raw search results need consolidation
|
|
115
|
+
- Don't forget to check tool availability before assigning sources
|
|
116
|
+
|
|
117
|
+
### Examples
|
|
118
|
+
|
|
119
|
+
| Task | Decomposition |
|
|
120
|
+
| ---------------------- | ---------------------------------------------------------------------------- |
|
|
121
|
+
| Research auth patterns | [Search PDFs, Search repos, Search history, Synthesize] |
|
|
122
|
+
| Investigate error | [Search CASS for similar errors, Search repo for error handling, Synthesize] |
|
|
123
|
+
| Learn about library | [Search docs, Search examples, Search issues, Synthesize findings] |
|
|
124
|
+
|
|
125
|
+
---
|
|
126
|
+
|
|
127
|
+
## Strategy Selection
|
|
128
|
+
|
|
129
|
+
The coordinator auto-selects strategy by matching task keywords. Override with explicit strategy when:
|
|
130
|
+
|
|
131
|
+
- Task spans multiple categories (e.g., "fix bug and add feature")
|
|
132
|
+
- You have domain knowledge the keywords don't capture
|
|
133
|
+
- Past experience suggests a different approach
|
|
134
|
+
|
|
135
|
+
```
|
|
136
|
+
swarm_plan_prompt(task="...", strategy="risk-based") // explicit override
|
|
137
|
+
swarm_plan_prompt(task="...") // auto-select
|
|
138
|
+
```
|
|
@@ -0,0 +1,213 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: system-design
|
|
3
|
+
description: Principles for building reusable coding systems. Use when designing modules, APIs, CLIs, or any code meant to be used by others. Based on "A Philosophy of Software Design" by John Ousterhout. Covers deep modules, complexity management, and design red flags.
|
|
4
|
+
tags:
|
|
5
|
+
- design
|
|
6
|
+
- architecture
|
|
7
|
+
- modules
|
|
8
|
+
- complexity
|
|
9
|
+
---
|
|
10
|
+
|
|
11
|
+
# System Design
|
|
12
|
+
|
|
13
|
+
Principles for building reusable, maintainable coding systems. From "A Philosophy of Software Design" by John Ousterhout.
|
|
14
|
+
|
|
15
|
+
## Core Principle: Fight Complexity
|
|
16
|
+
|
|
17
|
+
Complexity is the root cause of most software problems. It accumulates incrementally—each shortcut adds a little, until the system becomes unmaintainable.
|
|
18
|
+
|
|
19
|
+
**Complexity defined:** Anything that makes software hard to understand or modify.
|
|
20
|
+
|
|
21
|
+
**Symptoms:**
|
|
22
|
+
|
|
23
|
+
- Change amplification: simple change requires many modifications
|
|
24
|
+
- Cognitive load: how much you need to know to make a change
|
|
25
|
+
- Unknown unknowns: not obvious what needs to change
|
|
26
|
+
|
|
27
|
+
## Deep Modules
|
|
28
|
+
|
|
29
|
+
The most important design principle: **make modules deep**.
|
|
30
|
+
|
|
31
|
+
```
|
|
32
|
+
┌─────────────────────────────┐
|
|
33
|
+
│ Simple Interface │ ← Small surface area
|
|
34
|
+
├─────────────────────────────┤
|
|
35
|
+
│ │
|
|
36
|
+
│ │
|
|
37
|
+
│ Deep Implementation │ ← Lots of functionality
|
|
38
|
+
│ │
|
|
39
|
+
│ │
|
|
40
|
+
└─────────────────────────────┘
|
|
41
|
+
```
|
|
42
|
+
|
|
43
|
+
**Deep module:** Simple interface, lots of functionality hidden behind it.
|
|
44
|
+
|
|
45
|
+
**Shallow module:** Complex interface relative to functionality provided. Red flag.
|
|
46
|
+
|
|
47
|
+
### Examples
|
|
48
|
+
|
|
49
|
+
**Deep:** Unix file I/O - just 5 calls (open, read, write, lseek, close) hide enormous complexity (buffering, caching, device drivers, permissions, journaling).
|
|
50
|
+
|
|
51
|
+
**Shallow:** Java's file reading requires BufferedReader wrapping FileReader wrapping FileInputStream. Interface complexity matches implementation complexity.
|
|
52
|
+
|
|
53
|
+
### Apply This
|
|
54
|
+
|
|
55
|
+
- Prefer fewer methods that do more over many small methods
|
|
56
|
+
- Hide implementation details aggressively
|
|
57
|
+
- A module's interface should be much simpler than its implementation
|
|
58
|
+
- If interface is as complex as implementation, reconsider the abstraction
|
|
59
|
+
|
|
60
|
+
## Strategic vs Tactical Programming
|
|
61
|
+
|
|
62
|
+
**Tactical:** Get it working now. Each task adds small complexities. Debt accumulates.
|
|
63
|
+
|
|
64
|
+
**Strategic:** Invest time in good design. Slower initially, faster long-term.
|
|
65
|
+
|
|
66
|
+
```
|
|
67
|
+
Progress
|
|
68
|
+
│
|
|
69
|
+
│ Strategic ────────────────→
|
|
70
|
+
│ /
|
|
71
|
+
│ /
|
|
72
|
+
│ / Tactical ─────────→
|
|
73
|
+
│ / ↘ (slows down)
|
|
74
|
+
│ /
|
|
75
|
+
└──┴─────────────────────────────────→ Time
|
|
76
|
+
```
|
|
77
|
+
|
|
78
|
+
**Rule of thumb:** Spend 10-20% of development time on design improvements.
|
|
79
|
+
|
|
80
|
+
### Working Code Isn't Enough
|
|
81
|
+
|
|
82
|
+
"Working code" is not the goal. The goal is a great design that also works. If you're satisfied with "it works," you're programming tactically.
|
|
83
|
+
|
|
84
|
+
## Information Hiding
|
|
85
|
+
|
|
86
|
+
Each module should encapsulate knowledge that other modules don't need.
|
|
87
|
+
|
|
88
|
+
**Information leakage (red flag):** Same knowledge appears in multiple places. If one changes, all must change.
|
|
89
|
+
|
|
90
|
+
**Temporal decomposition (red flag):** Splitting code based on when things happen rather than what information they use. Often causes leakage.
|
|
91
|
+
|
|
92
|
+
### Apply This
|
|
93
|
+
|
|
94
|
+
- Ask: "What knowledge does this module encapsulate?"
|
|
95
|
+
- If the answer is "not much," the module is probably shallow
|
|
96
|
+
- Group code by what it knows, not when it runs
|
|
97
|
+
- Private by default; expose only what's necessary
|
|
98
|
+
|
|
99
|
+
## Define Errors Out of Existence
|
|
100
|
+
|
|
101
|
+
Exceptions add complexity. The best way to handle them: design so they can't happen.
|
|
102
|
+
|
|
103
|
+
**Instead of:**
|
|
104
|
+
|
|
105
|
+
```typescript
|
|
106
|
+
function deleteFile(path: string): void {
|
|
107
|
+
if (!exists(path)) throw new FileNotFoundError();
|
|
108
|
+
// delete...
|
|
109
|
+
}
|
|
110
|
+
```
|
|
111
|
+
|
|
112
|
+
**Do:**
|
|
113
|
+
|
|
114
|
+
```typescript
|
|
115
|
+
function deleteFile(path: string): void {
|
|
116
|
+
// Just delete. If it doesn't exist, goal is achieved.
|
|
117
|
+
// No error to handle.
|
|
118
|
+
}
|
|
119
|
+
```
|
|
120
|
+
|
|
121
|
+
### Apply This
|
|
122
|
+
|
|
123
|
+
- Redefine semantics so errors become non-issues
|
|
124
|
+
- Handle edge cases internally rather than exposing them
|
|
125
|
+
- Fewer exceptions = simpler interface = deeper module
|
|
126
|
+
- Ask: "Can I change the definition so this isn't an error?"
|
|
127
|
+
|
|
128
|
+
## General-Purpose Modules
|
|
129
|
+
|
|
130
|
+
Somewhat general-purpose modules are deeper than special-purpose ones.
|
|
131
|
+
|
|
132
|
+
**Not too general:** Don't build a framework when you need a function.
|
|
133
|
+
|
|
134
|
+
**Not too specific:** Don't hardcode assumptions that limit reuse.
|
|
135
|
+
|
|
136
|
+
**Sweet spot:** Solve today's problem in a way that naturally handles tomorrow's.
|
|
137
|
+
|
|
138
|
+
### Questions to Ask
|
|
139
|
+
|
|
140
|
+
1. What is the simplest interface that covers all current needs?
|
|
141
|
+
2. How many situations will this method be used in?
|
|
142
|
+
3. Is this API easy to use for my current needs?
|
|
143
|
+
|
|
144
|
+
## Pull Complexity Downward
|
|
145
|
+
|
|
146
|
+
When complexity is unavoidable, put it in the implementation, not the interface.
|
|
147
|
+
|
|
148
|
+
**Bad:** Expose complexity to all callers.
|
|
149
|
+
**Good:** Handle complexity once, internally.
|
|
150
|
+
|
|
151
|
+
It's more important for a module to have a simple interface than a simple implementation.
|
|
152
|
+
|
|
153
|
+
### Example
|
|
154
|
+
|
|
155
|
+
Configuration: Instead of requiring callers to configure everything, provide sensible defaults. Handle the complexity of choosing defaults internally.
|
|
156
|
+
|
|
157
|
+
## Design Twice
|
|
158
|
+
|
|
159
|
+
Before implementing, consider at least two different designs. Compare them.
|
|
160
|
+
|
|
161
|
+
**Benefits:**
|
|
162
|
+
|
|
163
|
+
- Reveals assumptions you didn't know you were making
|
|
164
|
+
- Often the second design is better
|
|
165
|
+
- Even if first design wins, you understand why
|
|
166
|
+
|
|
167
|
+
**Don't skip this:** "I can't think of another approach" usually means you haven't tried hard enough.
|
|
168
|
+
|
|
169
|
+
## Red Flags Summary
|
|
170
|
+
|
|
171
|
+
| Red Flag | Symptom |
|
|
172
|
+
| ----------------------- | ------------------------------------------------ |
|
|
173
|
+
| Shallow module | Interface complexity ≈ implementation complexity |
|
|
174
|
+
| Information leakage | Same knowledge in multiple modules |
|
|
175
|
+
| Temporal decomposition | Code split by time, not information |
|
|
176
|
+
| Overexposure | Too many methods/params in interface |
|
|
177
|
+
| Pass-through methods | Method does little except call another |
|
|
178
|
+
| Repetition | Same code pattern appears multiple times |
|
|
179
|
+
| Special-general mixture | General-purpose code mixed with special-purpose |
|
|
180
|
+
| Conjoined methods | Can't understand one without reading another |
|
|
181
|
+
| Comment repeats code | Comment says what code obviously does |
|
|
182
|
+
| Vague name | Name doesn't convey much information |
|
|
183
|
+
|
|
184
|
+
## Applying to CLI/Tool Design
|
|
185
|
+
|
|
186
|
+
When building CLIs, plugins, or tools:
|
|
187
|
+
|
|
188
|
+
1. **Deep commands:** Few commands that do a lot, not many shallow ones
|
|
189
|
+
2. **Sensible defaults:** Work without configuration for common cases
|
|
190
|
+
3. **Progressive disclosure:** Simple usage first, advanced options available
|
|
191
|
+
4. **Consistent interface:** Same patterns across all commands
|
|
192
|
+
5. **Error elimination:** Design so common mistakes are impossible
|
|
193
|
+
|
|
194
|
+
### Example: Good CLI Design
|
|
195
|
+
|
|
196
|
+
```bash
|
|
197
|
+
# Deep: one command handles the common case well
|
|
198
|
+
swarm setup
|
|
199
|
+
|
|
200
|
+
# Not shallow: doesn't require 10 flags for basic usage
|
|
201
|
+
# Sensible defaults: picks reasonable models
|
|
202
|
+
# Progressive: advanced users can customize later
|
|
203
|
+
```
|
|
204
|
+
|
|
205
|
+
## Key Takeaways
|
|
206
|
+
|
|
207
|
+
1. **Complexity is the enemy.** Every design decision should reduce it.
|
|
208
|
+
2. **Deep modules win.** Simple interface, rich functionality.
|
|
209
|
+
3. **Hide information.** Each module owns specific knowledge.
|
|
210
|
+
4. **Define errors away.** Change semantics to eliminate edge cases.
|
|
211
|
+
5. **Design twice.** Always consider alternatives.
|
|
212
|
+
6. **Strategic > tactical.** Invest in design, not just working code.
|
|
213
|
+
7. **Pull complexity down.** Implementation absorbs complexity, interface stays simple.
|