vibe-forge 0.4.0 → 0.8.2

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 (129) hide show
  1. package/.claude/commands/clear-attention.md +63 -63
  2. package/.claude/commands/compact-context.md +52 -0
  3. package/.claude/commands/configure-vcs.md +5 -5
  4. package/.claude/commands/forge.md +50 -3
  5. package/.claude/commands/need-help.md +77 -77
  6. package/.claude/commands/update-status.md +64 -64
  7. package/.claude/commands/worker-loop.md +106 -106
  8. package/.claude/hooks/worker-loop.js +37 -4
  9. package/.claude/scripts/setup-worker-loop.sh +45 -45
  10. package/.claude/settings.json +89 -0
  11. package/LICENSE +21 -21
  12. package/README.md +211 -232
  13. package/agents/aegis/personality.md +35 -1
  14. package/agents/anvil/personality.md +39 -1
  15. package/agents/architect/personality.md +26 -0
  16. package/agents/crucible/personality.md +54 -1
  17. package/agents/crucible-x/personality.md +210 -0
  18. package/agents/ember/personality.md +29 -1
  19. package/agents/flux/personality.md +248 -0
  20. package/agents/furnace/personality.md +52 -1
  21. package/agents/herald/personality.md +3 -1
  22. package/agents/loki/personality.md +108 -0
  23. package/agents/oracle/personality.md +284 -0
  24. package/agents/pixel/personality.md +140 -0
  25. package/agents/planning-hub/personality.md +222 -0
  26. package/agents/scribe/personality.md +3 -1
  27. package/agents/slag/personality.md +268 -0
  28. package/agents/{sentinel → temper}/personality.md +85 -9
  29. package/bin/cli.js +77 -30
  30. package/bin/dashboard/api/agents.js +333 -0
  31. package/bin/dashboard/api/dispatch.js +507 -0
  32. package/bin/dashboard/api/tasks.js +416 -0
  33. package/bin/dashboard/public/assets/index-BpHfsx1r.js +2 -0
  34. package/bin/dashboard/public/assets/index-QODv4Zn9.css +1 -0
  35. package/bin/dashboard/public/index.html +14 -0
  36. package/bin/dashboard/server.js +645 -0
  37. package/bin/forge-daemon.sh +176 -550
  38. package/bin/forge-setup.sh +28 -11
  39. package/bin/forge-spawn.sh +5 -5
  40. package/bin/forge.cmd +83 -83
  41. package/bin/forge.sh +210 -31
  42. package/config/agent-manifest.yaml +237 -243
  43. package/config/agents.json +207 -132
  44. package/config/task-types.yaml +111 -106
  45. package/context/agent-overrides/README.md +41 -0
  46. package/context/architecture.md +42 -0
  47. package/context/modern-conventions.md +129 -129
  48. package/docs/agents.md +473 -409
  49. package/docs/architecture.md +194 -162
  50. package/docs/commands.md +451 -388
  51. package/docs/security.md +195 -144
  52. package/package.json +38 -11
  53. package/src/lib/check-aliases.js +50 -0
  54. package/{bin → src}/lib/colors.sh +2 -1
  55. package/src/lib/config.sh +347 -0
  56. package/{bin → src}/lib/constants.sh +48 -13
  57. package/src/lib/daemon/budgets.sh +107 -0
  58. package/src/lib/daemon/dependencies.sh +146 -0
  59. package/src/lib/daemon/display.sh +128 -0
  60. package/src/lib/daemon/notifications.sh +273 -0
  61. package/src/lib/daemon/routing.sh +93 -0
  62. package/src/lib/daemon/state.sh +163 -0
  63. package/src/lib/daemon/sync.sh +103 -0
  64. package/{bin → src}/lib/database.sh +52 -0
  65. package/src/lib/frontmatter.js +106 -0
  66. package/src/lib/heimdall-setup.js +113 -0
  67. package/src/lib/heimdall.js +265 -0
  68. package/src/lib/index.sh +25 -0
  69. package/{bin → src}/lib/json.sh +7 -1
  70. package/{bin → src}/lib/terminal.js +7 -1
  71. package/.claude/settings.local.json +0 -33
  72. package/agents/forge-master/capabilities.md +0 -144
  73. package/agents/forge-master/context-template.md +0 -128
  74. package/agents/forge-master/personality.md +0 -138
  75. package/bin/lib/config.sh +0 -313
  76. package/config/task-template.md +0 -87
  77. package/context/forge-state.yaml +0 -19
  78. package/docs/TODO.md +0 -150
  79. package/docs/getting-started.md +0 -243
  80. package/docs/npm-publishing.md +0 -95
  81. package/docs/workflows/README.md +0 -32
  82. package/docs/workflows/azure-devops.md +0 -108
  83. package/docs/workflows/bitbucket.md +0 -104
  84. package/docs/workflows/git-only.md +0 -130
  85. package/docs/workflows/gitea.md +0 -168
  86. package/docs/workflows/github.md +0 -103
  87. package/docs/workflows/gitlab.md +0 -105
  88. package/docs/workflows.md +0 -454
  89. package/tasks/completed/ARCH-001-duplicate-agent-config.md +0 -121
  90. package/tasks/completed/ARCH-002-mixed-bash-node-implementation.md +0 -88
  91. package/tasks/completed/ARCH-003-worker-loop-hook-duplication.md +0 -77
  92. package/tasks/completed/ARCH-009-test-organization.md +0 -78
  93. package/tasks/completed/ARCH-011-jq-vs-nodejs-json.md +0 -94
  94. package/tasks/completed/ARCH-012-tmp-files-in-root.md +0 -71
  95. package/tasks/completed/ARCH-013-exit-code-constants.md +0 -65
  96. package/tasks/completed/ARCH-014-sed-incompatibility.md +0 -96
  97. package/tasks/completed/ARCH-015-docs-todo-tracking.md +0 -83
  98. package/tasks/completed/CLEAN-001.md +0 -38
  99. package/tasks/completed/CLEAN-003.md +0 -47
  100. package/tasks/completed/CLEAN-004.md +0 -56
  101. package/tasks/completed/CLEAN-005.md +0 -75
  102. package/tasks/completed/CLEAN-006.md +0 -47
  103. package/tasks/completed/CLEAN-007.md +0 -34
  104. package/tasks/completed/CLEAN-008.md +0 -49
  105. package/tasks/completed/CLEAN-012.md +0 -58
  106. package/tasks/completed/CLEAN-013.md +0 -45
  107. package/tasks/completed/SEC-001-sql-injection-fix.md +0 -58
  108. package/tasks/completed/SEC-002-notification-injection-fix.md +0 -45
  109. package/tasks/completed/SEC-003-eval-injection-fix.md +0 -54
  110. package/tasks/completed/SEC-004-pid-race-condition-fix.md +0 -49
  111. package/tasks/completed/SEC-005-worker-loop-path-fix.md +0 -51
  112. package/tasks/completed/SEC-006-eval-agent-names.md +0 -55
  113. package/tasks/completed/SEC-007-spawn-escaping.md +0 -67
  114. package/tasks/pending/ARCH-004-git-bash-detection-duplication.md +0 -72
  115. package/tasks/pending/ARCH-005-missing-src-directory.md +0 -95
  116. package/tasks/pending/ARCH-006-task-template-location.md +0 -64
  117. package/tasks/pending/ARCH-007-daemon-monolith.md +0 -91
  118. package/tasks/pending/ARCH-008-forge-master-vs-hub.md +0 -81
  119. package/tasks/pending/ARCH-010-missing-index-files.md +0 -84
  120. package/tasks/pending/CLEAN-002.md +0 -29
  121. package/tasks/pending/CLEAN-009.md +0 -31
  122. package/tasks/pending/CLEAN-010.md +0 -30
  123. package/tasks/pending/CLEAN-011.md +0 -30
  124. package/tasks/pending/CLEAN-014.md +0 -32
  125. package/tasks/review/task-001.md +0 -78
  126. /package/{bin → src}/lib/agents.sh +0 -0
  127. /package/{bin → src}/lib/util.sh +0 -0
  128. /package/{bin → src}/lib/vcs.js +0 -0
  129. /package/{context → templates}/project-context-template.md +0 -0
@@ -0,0 +1,265 @@
1
+ #!/usr/bin/env node
2
+ /**
3
+ * Heimdall -- Forge worker pre-tool hook interceptor (PLAT-1)
4
+ *
5
+ * Guards the Bifrost: intercepts every tool call before execution,
6
+ * checks it against per-task policy, and blocks or allows.
7
+ *
8
+ * Registered as a PreToolUse hook via .claude/settings.local.json
9
+ * written by the forge daemon at worker startup.
10
+ *
11
+ * Exit codes:
12
+ * 0 -- allow (optionally with audit log entry)
13
+ * 2 -- block (explanation written to stdout, fed back to model)
14
+ *
15
+ * Context file (.context.json in process.cwd()) is written by the forge
16
+ * daemon alongside each inbox task. If absent, Heimdall exits 0 immediately
17
+ * -- forge-native tasks are not restricted.
18
+ */
19
+
20
+ 'use strict'
21
+
22
+ const fs = require('fs')
23
+ const path = require('path')
24
+
25
+ // ── Input ─────────────────────────────────────────────────────────────────────
26
+
27
+ let input
28
+ try {
29
+ input = JSON.parse(fs.readFileSync(0, 'utf8'))
30
+ } catch (e) {
31
+ // Malformed input -- allow and exit rather than blocking the worker
32
+ process.exit(0)
33
+ }
34
+
35
+ const { tool_name, tool_input } = input
36
+
37
+ // ── Context file ──────────────────────────────────────────────────────────────
38
+
39
+ const contextPath = path.join(process.cwd(), '.context.json')
40
+
41
+ // No context file = forge-native task. Heimdall does not restrict forge-native work.
42
+ if (!fs.existsSync(contextPath)) {
43
+ process.exit(0)
44
+ }
45
+
46
+ let ctx
47
+ try {
48
+ ctx = JSON.parse(fs.readFileSync(contextPath, 'utf8'))
49
+ } catch (e) {
50
+ // Unreadable context -- fail open to avoid blocking forge-native work
51
+ process.exit(0)
52
+ }
53
+
54
+ const {
55
+ story_id,
56
+ agent,
57
+ worktree_path,
58
+ has_db_migration,
59
+ allowed_paths,
60
+ escalation_dir,
61
+ audit_log: ctxAuditLog,
62
+ } = ctx
63
+
64
+ // ── Logging ───────────────────────────────────────────────────────────────────
65
+
66
+ const AUDIT_LOG = ctxAuditLog
67
+ || path.join(process.cwd(), '_vibe-chain-output', 'heimdall-audit.log')
68
+
69
+ const MAX_VIOLATIONS = parseInt(process.env.HEIMDALL_MAX_VIOLATIONS || '3', 10)
70
+
71
+ // Violation tracking lives in the worktree root (process.cwd())
72
+ const VIOLATION_FILE = path.join(process.cwd(), `.${story_id}.violations`)
73
+
74
+ // Escalation signal written to the inbox agent dir so the daemon detects it
75
+ const ESCALATION_DIR = escalation_dir || process.cwd()
76
+
77
+ function timestamp() {
78
+ return new Date().toISOString()
79
+ }
80
+
81
+ function audit(level, message) {
82
+ const line = `[${timestamp()}] HEIMDALL ${level} ${agent}/${story_id}: ${message}\n`
83
+ try {
84
+ const dir = path.dirname(AUDIT_LOG)
85
+ if (!fs.existsSync(dir)) fs.mkdirSync(dir, { recursive: true })
86
+ fs.appendFileSync(AUDIT_LOG, line)
87
+ } catch (_) {
88
+ // Audit log write failure must never block or crash the hook
89
+ }
90
+ }
91
+
92
+ function block(reason) {
93
+ audit('BLOCKED', reason)
94
+
95
+ // Track violations
96
+ let violations = 0
97
+ try {
98
+ if (fs.existsSync(VIOLATION_FILE)) {
99
+ violations = parseInt(fs.readFileSync(VIOLATION_FILE, 'utf8').trim(), 10) || 0
100
+ }
101
+ } catch (_) {}
102
+
103
+ violations++
104
+
105
+ try {
106
+ fs.writeFileSync(VIOLATION_FILE, String(violations))
107
+ } catch (_) {}
108
+
109
+ if (violations >= MAX_VIOLATIONS) {
110
+ // Sound the Gjallarhorn
111
+ const escalationFile = path.join(ESCALATION_DIR, `${story_id}.escalation`)
112
+ try {
113
+ fs.writeFileSync(escalationFile, JSON.stringify({
114
+ story_id,
115
+ agent,
116
+ violations,
117
+ last_reason: reason,
118
+ timestamp: timestamp(),
119
+ }, null, 2))
120
+ } catch (_) {}
121
+
122
+ audit('SOUNDED', `${violations} violations -- escalating to human review`)
123
+
124
+ console.log(
125
+ `[HEIMDALL] Action blocked: ${reason}\n` +
126
+ `[HEIMDALL] GJALLARHORN SOUNDED: ${violations} violations recorded.\n` +
127
+ `[HEIMDALL] Story ${story_id} has been escalated to human review. Stop working on this story.`
128
+ )
129
+ } else {
130
+ console.log(
131
+ `[HEIMDALL] Action blocked: ${reason}\n` +
132
+ `[HEIMDALL] Violation ${violations}/${MAX_VIOLATIONS}. Self-correct and continue.`
133
+ )
134
+ }
135
+
136
+ process.exit(2)
137
+ }
138
+
139
+ function allow(note) {
140
+ if (note) audit('ALLOWED', note)
141
+ process.exit(0)
142
+ }
143
+
144
+ // ── Path helpers ──────────────────────────────────────────────────────────────
145
+
146
+ function isOutsideAllowedPaths(targetPath) {
147
+ if (!targetPath) return false
148
+ try {
149
+ const resolved = path.resolve(targetPath)
150
+ return !allowed_paths.some(p => resolved.startsWith(path.resolve(p)))
151
+ } catch (_) {
152
+ return true // Unresolvable path -- treat as outside
153
+ }
154
+ }
155
+
156
+ // ── Bash tool checks ──────────────────────────────────────────────────────────
157
+
158
+ if (tool_name === 'Bash') {
159
+ const cmd = (tool_input && tool_input.command || '').trim()
160
+
161
+ // Destructive rm -- check if target escapes worktree
162
+ if (/rm\s+-[a-zA-Z]*r[a-zA-Z]*f|-[a-zA-Z]*f[a-zA-Z]*r/.test(cmd) && /\brm\b/.test(cmd)) {
163
+ // Extract everything after the flags as the target
164
+ const rmMatch = cmd.match(/rm\s+(?:-\S+\s+)(.+)/)
165
+ const rmTarget = rmMatch ? rmMatch[1].trim().replace(/^['"]|['"]$/g, '') : ''
166
+
167
+ const isRootTarget = /^(\/|~)/.test(rmTarget) || rmTarget === '' || rmTarget.includes('..')
168
+ const isOutside = !rmTarget || isRootTarget || isOutsideAllowedPaths(rmTarget)
169
+
170
+ if (isOutside) {
171
+ block(`destructive rm outside worktree: ${cmd}`)
172
+ }
173
+ }
174
+
175
+ // Credential access
176
+ if (/\.(env|pem|key|cert)\b/.test(cmd) && !/\.env\.(example|sample|template)/.test(cmd)) {
177
+ block(`credential file access: ${cmd}`)
178
+ }
179
+ if (/~\/\.(ssh|aws|gnupg)\b/.test(cmd)) {
180
+ block(`credential directory access: ${cmd}`)
181
+ }
182
+ // Echoing or exporting secrets (but not reading them as part of build)
183
+ if (/(echo|printf|export)\s+.*\b(TOKEN|SECRET|PASSWORD|API_KEY)\s*=/.test(cmd)) {
184
+ block(`credential assignment in shell: ${cmd}`)
185
+ }
186
+
187
+ // Dangerous git operations
188
+ if (/git\s+push\b.*--force(-with-lease)?/.test(cmd)) {
189
+ block(`force push blocked: ${cmd}`)
190
+ }
191
+ if (/git\s+reset\s+--hard\s+HEAD~[2-9]/.test(cmd)) {
192
+ block(`multi-commit hard reset blocked: ${cmd}`)
193
+ }
194
+ if (/git\s+clean\s+-[a-zA-Z]*f[a-zA-Z]*d|-[a-zA-Z]*d[a-zA-Z]*f/.test(cmd) && /\bgit\b/.test(cmd)) {
195
+ block(`git clean -fd blocked: ${cmd}`)
196
+ }
197
+ // Push to a non-origin remote (e.g. git push upstream)
198
+ if (/git\s+push\s+(?!origin\b)(\S+)/.test(cmd)) {
199
+ const remoteMatch = cmd.match(/git\s+push\s+(\S+)/)
200
+ if (remoteMatch && remoteMatch[1] !== 'origin' && !remoteMatch[1].startsWith('-')) {
201
+ block(`push to non-origin remote blocked: ${cmd}`)
202
+ }
203
+ }
204
+ // Direct push to main/master — all changes must go through PRs
205
+ if (/git\s+push\b/.test(cmd) && /\b(main|master)\b/.test(cmd)) {
206
+ block(`direct push to main/master blocked — create a feature branch and open a PR`)
207
+ }
208
+
209
+ // DB destructive operations without authorization
210
+ if (/(DROP\s+TABLE|TRUNCATE\s+TABLE)/i.test(cmd) && !has_db_migration) {
211
+ block(`DROP/TRUNCATE requires has_db_migration: true on the story`)
212
+ }
213
+ if (/DELETE\s+FROM\s+\S+\s*;?\s*$/i.test(cmd) && !/WHERE\s+/i.test(cmd)) {
214
+ block(`DELETE without WHERE clause blocked: ${cmd}`)
215
+ }
216
+
217
+ // High-risk but legitimate -- audit log only
218
+ if (/\b(npm|yarn|pnpm)\s+(install|add|ci)\b/.test(cmd)) {
219
+ allow(`dependency install: ${cmd}`)
220
+ }
221
+ if (/\b(pip|pip3)\s+install\b/.test(cmd)) {
222
+ allow(`pip install: ${cmd}`)
223
+ }
224
+ if (/\bcargo\s+(build|install)\b/.test(cmd)) {
225
+ allow(`cargo build: ${cmd}`)
226
+ }
227
+ if (/\b(curl|wget)\b/.test(cmd)) {
228
+ allow(`network request: ${cmd}`)
229
+ }
230
+ if (/git\s+commit\s+--amend/.test(cmd)) {
231
+ allow(`git commit --amend`)
232
+ }
233
+ }
234
+
235
+ // ── Write / Edit tool checks ──────────────────────────────────────────────────
236
+
237
+ if (tool_name === 'Write' || tool_name === 'Edit') {
238
+ const filePath = tool_input && (tool_input.file_path || tool_input.path) || ''
239
+
240
+ if (filePath) {
241
+ // Credential files
242
+ if (/\.(env|pem|key|cert)$/.test(filePath) && !/\.(example|sample|template)$/.test(filePath)) {
243
+ block(`write to credential file: ${filePath}`)
244
+ }
245
+
246
+ // Settings that could override Heimdall
247
+ if (/\.claude[/\\]settings(\.local)?\.json$/.test(filePath)) {
248
+ block(`write to .claude/settings blocked -- Heimdall config is daemon-managed`)
249
+ }
250
+
251
+ // Path escape check
252
+ if (isOutsideAllowedPaths(filePath)) {
253
+ block(`path escape: ${filePath} is outside allowed paths`)
254
+ }
255
+
256
+ // Pipeline output writes -- allowed but logged
257
+ if (filePath.includes('_vibe-chain-output')) {
258
+ allow(`pipeline output write: ${filePath}`)
259
+ }
260
+ }
261
+ }
262
+
263
+ // ── Default: allow ────────────────────────────────────────────────────────────
264
+
265
+ allow(null)
@@ -0,0 +1,25 @@
1
+ #!/usr/bin/env bash
2
+ #
3
+ # src/lib/index.sh
4
+ #
5
+ # Central entry point for sourcing common libraries.
6
+ # Scripts source this instead of individually sourcing each lib.
7
+ #
8
+ # Usage: source "$LIB_DIR/index.sh"
9
+
10
+ # Prevent double-sourcing
11
+ [[ -n "${_LIB_INDEX_LOADED:-}" ]] && return 0
12
+ _LIB_INDEX_LOADED=1
13
+
14
+ _LIB_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
15
+
16
+ # Core libraries (order matters: colors first, then constants, then the rest)
17
+ source "$_LIB_DIR/colors.sh"
18
+ source "$_LIB_DIR/constants.sh"
19
+ source "$_LIB_DIR/json.sh"
20
+ source "$_LIB_DIR/util.sh"
21
+
22
+ # Optional libraries (sourced on demand by scripts that need them)
23
+ # source "$_LIB_DIR/config.sh" # Agent config loading
24
+ # source "$_LIB_DIR/agents.sh" # Agent resolution
25
+ # source "$_LIB_DIR/database.sh" # SQLite operations (daemon only)
@@ -102,7 +102,13 @@ json_read_multi() {
102
102
  # Reads all keys from a JSON file and outputs key=value lines.
103
103
  # Useful for loading all config values at once.
104
104
  #
105
- # Example: eval "$(json_read_all config.json | sed 's/^/export /')"
105
+ # SECURITY WARNING: Do NOT use this function with eval on untrusted JSON files.
106
+ # JSON key names are NOT validated or escaped - a malicious key name like
107
+ # "FOO=1; evil_command; export BAR" would result in arbitrary code execution.
108
+ # Only use with fully trusted, version-controlled config files.
109
+ #
110
+ # Safe usage (read individual values): json_read FILE KEY
111
+ # Unsafe pattern to avoid: eval "$(json_read_all untrusted.json | sed 's/^/export /')"
106
112
  json_read_all() {
107
113
  local file="$1"
108
114
 
@@ -142,11 +142,16 @@ function getBestTerminal() {
142
142
  // =============================================================================
143
143
 
144
144
  function spawnWindowsTerminal(title, command, opts = {}) {
145
- const { cwd, tabColor } = opts;
145
+ const { cwd, tabColor, suppressApplicationTitle = true } = opts;
146
146
 
147
147
  // Build wt arguments
148
148
  const args = ['-w', '0', 'new-tab', '--title', title];
149
149
 
150
+ // FORGE-9: Prevent the spawned process from overwriting the tab title
151
+ if (suppressApplicationTitle) {
152
+ args.push('--suppressApplicationTitle');
153
+ }
154
+
150
155
  if (tabColor) {
151
156
  args.push('--tabColor', tabColor);
152
157
  }
@@ -436,6 +441,7 @@ module.exports = {
436
441
  detectTerminals,
437
442
  getBestTerminal,
438
443
  spawnTerminal,
444
+ findGitBash,
439
445
  TERMINALS,
440
446
  getPlatform,
441
447
  };
@@ -1,33 +0,0 @@
1
- {
2
- "permissions": {
3
- "allow": [
4
- "Bash(ls:*)",
5
- "Bash(git pull:*)",
6
- "Bash(npm view:*)",
7
- "Bash(gh run list:*)",
8
- "Bash(gh run view:*)",
9
- "Bash(gh secret list:*)",
10
- "Bash(git add:*)",
11
- "Bash(git commit:*)",
12
- "Bash(gh workflow run:*)",
13
- "Bash(gh repo view:*)",
14
- "Bash(git push:*)",
15
- "Bash(sqlite3:*)",
16
- "Bash(npm test)",
17
- "Bash(git rm:*)"
18
- ]
19
- },
20
- "hooks": {
21
- "Stop": [
22
- {
23
- "matcher": "",
24
- "hooks": [
25
- {
26
- "type": "command",
27
- "command": "node .claude/hooks/worker-loop.js"
28
- }
29
- ]
30
- }
31
- ]
32
- }
33
- }
@@ -1,144 +0,0 @@
1
- # Forge Master Capabilities
2
-
3
- ## Tools & Commands
4
-
5
- ### Task Management
6
-
7
- | Command | Description | Example |
8
- |---------|-------------|---------|
9
- | `/forge task:create` | Create a new task file | `/forge task:create --type=backend --title="Add auth endpoint"` |
10
- | `/forge task:assign` | Assign task to agent | `/forge task:assign task-021 furnace` |
11
- | `/forge task:status` | Get status of task(s) | `/forge task:status` or `/forge task:status task-021` |
12
- | `/forge task:block` | Mark task as blocked | `/forge task:block task-022 --reason="Awaiting API spec"` |
13
- | `/forge task:unblock` | Unblock a task | `/forge task:unblock task-022` |
14
- | `/forge task:priority` | Change task priority | `/forge task:priority task-021 critical` |
15
-
16
- ### Agent Coordination
17
-
18
- | Command | Description | Example |
19
- |---------|-------------|---------|
20
- | `/forge agents` | List all agents and status | `/forge agents` |
21
- | `/forge agent:wake` | Spin up an agent terminal | `/forge agent:wake anvil` |
22
- | `/forge agent:status` | Check specific agent status | `/forge agent:status furnace` |
23
- | `/forge agent:notify` | Send message to agent | `/forge agent:notify anvil "task-015 priority elevated"` |
24
-
25
- ### Progress & Reporting
26
-
27
- | Command | Description | Example |
28
- |---------|-------------|---------|
29
- | `/forge status` | Full forge status dashboard | `/forge status` |
30
- | `/forge progress` | Progress on current epic | `/forge progress epic-003` |
31
- | `/forge blockers` | List all current blockers | `/forge blockers` |
32
- | `/forge today` | Summary of today's activity | `/forge today` |
33
-
34
- ### Epic & Planning
35
-
36
- | Command | Description | Example |
37
- |---------|-------------|---------|
38
- | `/forge epic:decompose` | Break epic into tasks | `/forge epic:decompose epic-003` |
39
- | `/forge epic:status` | Epic completion status | `/forge epic:status epic-003` |
40
-
41
- ---
42
-
43
- ## File Operations
44
-
45
- ### Task Lifecycle Management
46
-
47
- ```
48
- READ: /tasks/*/task-*.md # Monitor all task states
49
- WRITE: /tasks/pending/*.md # Create new tasks
50
- MOVE: /tasks/{from}/* → /tasks/{to}/* # Transition task states
51
- ```
52
-
53
- ### Directories Monitored
54
-
55
- | Directory | Watches For | Action |
56
- |-----------|-------------|--------|
57
- | `/tasks/completed/` | New completions | Route to Sentinel |
58
- | `/tasks/needs-changes/` | Review rejections | Re-assign to original worker |
59
- | `/tasks/approved/` | Review passes | Move to merged, notify Planning Hub |
60
-
61
- ---
62
-
63
- ## Decision Matrix
64
-
65
- ### Task Assignment Logic
66
-
67
- ```
68
- IF task.type == "frontend" OR task.type == "component" OR task.type == "ui"
69
- → Assign to Anvil
70
-
71
- IF task.type == "backend" OR task.type == "api" OR task.type == "database"
72
- → Assign to Furnace
73
-
74
- IF task.type == "test" OR task.type == "qa" OR task.type == "bugfix"
75
- → Assign to Crucible
76
-
77
- IF task.type == "docs" OR task.type == "readme" OR task.type == "api-docs"
78
- → Assign to Scribe
79
-
80
- IF task.type == "release" OR task.type == "deploy" OR task.type == "changelog"
81
- → Assign to Herald
82
-
83
- IF task.type == "review"
84
- → Assign to Sentinel (automatic for all completed work)
85
-
86
- IF task.type == "devops" OR task.type == "infra" OR task.type == "ci-cd"
87
- → Assign to Ember
88
-
89
- IF task.type == "security" OR task.type == "audit"
90
- → Assign to Aegis
91
- ```
92
-
93
- ### Priority Levels
94
-
95
- | Priority | Meaning | SLA |
96
- |----------|---------|-----|
97
- | `critical` | Blocking other work | Immediate |
98
- | `high` | Sprint commitment | Today |
99
- | `medium` | Sprint goal | This sprint |
100
- | `low` | Nice to have | When available |
101
-
102
- ---
103
-
104
- ## Integration Points
105
-
106
- ### Inputs (Forge Master Receives)
107
- - Epic files from Planning Hub (`/specs/epics/*.md`)
108
- - Completion signals from Workers (`/tasks/completed/*.md`)
109
- - Review results from Sentinel (`/tasks/approved/*.md` or `/tasks/needs-changes/*.md`)
110
- - Blocker escalations from Workers
111
- - Priority changes from Quartermaster
112
-
113
- ### Outputs (Forge Master Produces)
114
- - Task files for Workers (`/tasks/pending/*.md`)
115
- - Status reports for Planning Hub
116
- - Notifications to specific agents
117
- - Progress updates to Dashboard
118
-
119
- ---
120
-
121
- ## State Management
122
-
123
- ### Forge Master Maintains
124
-
125
- ```yaml
126
- # /context/forge-state.yaml
127
- current_epic: epic-003
128
- tasks_pending: 5
129
- tasks_in_progress: 3
130
- tasks_blocked: 1
131
- tasks_in_review: 2
132
- tasks_completed_today: 7
133
- agents_active:
134
- - anvil
135
- - furnace
136
- - crucible
137
- last_updated: 2026-01-11T14:30:00Z
138
- ```
139
-
140
- ### Does NOT Maintain
141
- - Code state (that's git)
142
- - Test results (that's Crucible)
143
- - Release state (that's Herald)
144
- - Architecture decisions (that's Sage)
@@ -1,128 +0,0 @@
1
- # Forge Master Session Context
2
-
3
- You are the **Forge Master** - chief orchestrator of Vibe Forge.
4
-
5
- ## Your Identity
6
-
7
- Load and embody: `/_vibe-forge/agents/forge-master/personality.md`
8
-
9
- ## Your Capabilities
10
-
11
- Reference: `/_vibe-forge/agents/forge-master/capabilities.md`
12
-
13
- ---
14
-
15
- ## Current Project Context
16
-
17
- Load project context from: `/_vibe-forge/context/project-context.md`
18
-
19
- This file contains:
20
- - Project name and description
21
- - Tech stack and patterns
22
- - Coding standards
23
- - Key architectural decisions
24
- - File structure conventions
25
-
26
- **This is your bible. All task instructions must align with project context.**
27
-
28
- ---
29
-
30
- ## Current State
31
-
32
- On session start, read:
33
-
34
- - `/_vibe-forge/context/forge-state.yaml` - Current task counts and active agents
35
- - `/_vibe-forge/tasks/in-progress/*.md` - What's currently being worked on
36
- - `/_vibe-forge/tasks/pending/*.md` - What's in the queue
37
- - `/_vibe-forge/tasks/review/*.md` - What's awaiting Sentinel
38
-
39
- ---
40
-
41
- ## Agent Roster
42
-
43
- | Agent | Specialization | Terminal |
44
- |-------|---------------|----------|
45
- | **Anvil** | Frontend Dev | Tab 2 |
46
- | **Furnace** | Backend Dev | Tab 3 |
47
- | **Crucible** | Tester/QA | Tab 4 |
48
- | **Sentinel** | Code Reviewer | Tab 5 |
49
- | **Scribe** | Documentation | On-demand |
50
- | **Herald** | Release Manager | On-demand |
51
- | **Ember** | DevOps/Infra | On-demand |
52
- | **Aegis** | Security | On-demand |
53
-
54
- Planning Hub agents (Sage, Oracle, Quartermaster) operate in Adam's main terminal.
55
-
56
- ---
57
-
58
- ## Communication Protocol
59
-
60
- ### To Workers (via task files)
61
- - Write task to `/tasks/pending/task-{id}.md`
62
- - Worker picks up automatically via file watcher
63
- - **Do NOT send conversational messages** - task file is the interface
64
-
65
- ### To Planning Hub (via stdout)
66
- - Report status updates directly in conversation
67
- - Escalate blockers that require decisions
68
- - Request clarification on requirements
69
-
70
- ### To Dashboard (via state file)
71
- - Update `/context/forge-state.yaml` after state changes
72
- - Dashboard polls this file for display
73
-
74
- ---
75
-
76
- ## Session Startup Checklist
77
-
78
- 1. Read `forge-state.yaml` to understand current state
79
- 2. Scan `/tasks/in-progress/` for active work
80
- 3. Check `/tasks/completed/` for anything needing routing to review
81
- 4. Check `/tasks/needs-changes/` for rejected work needing re-assignment
82
- 5. Report status summary to Adam
83
- 6. Await instructions
84
-
85
- ---
86
-
87
- ## Token Efficiency Rules
88
-
89
- 1. **Never restate project context** - it's in the file
90
- 2. **Reference file paths** - don't paste file contents into conversation
91
- 3. **Batch status updates** - one message per reporting cycle, not per task
92
- 4. **Assume workers read task files** - don't duplicate instructions verbally
93
- 5. **Exception-based reporting** - only surface problems, not smooth operations
94
-
95
- ---
96
-
97
- ## Example Session Start
98
-
99
- ```
100
- ⚒️ The Forge Master awakens.
101
-
102
- Current State:
103
- - Epic: epic-003 (User Authentication)
104
- - Progress: 7/12 tasks complete
105
- - Active: Anvil (task-019), Furnace (task-020)
106
- - Blocked: task-022 (awaiting API spec)
107
- - Review Queue: 2 tasks pending Sentinel
108
-
109
- The forge is operational. What are your orders?
110
- ```
111
-
112
- ---
113
-
114
- ## Slash Commands Reference
115
-
116
- All commands prefixed with `/forge`:
117
-
118
- ```
119
- /forge status - Full dashboard
120
- /forge task:create - New task
121
- /forge task:assign - Assign to agent
122
- /forge task:status - Task details
123
- /forge agents - Agent status
124
- /forge blockers - Current blockers
125
- /forge progress - Epic progress
126
- ```
127
-
128
- See `capabilities.md` for full command reference.