@shardworks/guild-starter-kit 0.1.16 → 0.1.18

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.
@@ -40,14 +40,105 @@ Other roles may emerge as the guild evolves.
40
40
 
41
41
  ## Workshops
42
42
 
43
- A workshop is a repository where animas do their work. The patron assigns workshops (usually existing repos), and artificers work inside them on commissions. The patron judges results by the works produced, not by inspecting the workshop.
43
+ A workshop is a repository where animas do their work. Workshops are guild space the patron assigns them, but during normal operation the patron judges results by the works produced, not by inspecting the workshop directly.
44
44
 
45
- ### Workshop Lifecycle
45
+ Each workshop is registered in `guild.json` under the `workshops` key with its name, remote URL, and the timestamp it was added. On disk, the guild maintains a bare clone of each workshop at `.nexus/workshops/{name}.git`. Commission worktrees are created from these bare clones, giving each commission an isolated working directory.
46
46
 
47
- 1. A workshop is registered with the guild (`nsg workshop add <url>`)
48
- 2. The guild clones it and manages worktrees for concurrent commissions
49
- 3. Artificers work in isolated worktrees — one per commission
50
- 4. Completed work is delivered as branches or pull requests
47
+ ### Managing Workshops
48
+
49
+ Four commands manage the workshop lifecycle:
50
+
51
+ | Command | What it does |
52
+ |---------|-------------|
53
+ | `nsg workshop add <url>` | Clone a remote repo and register it as a workshop |
54
+ | `nsg workshop remove <name>` | Remove a workshop — deletes bare clone, worktrees, and guild.json entry |
55
+ | `nsg workshop list` | List all workshops with clone status and active worktree count |
56
+ | `nsg workshop create <org/name>` | Create a new GitHub repo and register it as a workshop |
57
+
58
+ ### Adding an Existing Repository
59
+
60
+ When the patron has an existing repository they want the guild to work on:
61
+
62
+ ```
63
+ nsg workshop add https://github.com/org/my-app.git
64
+ ```
65
+
66
+ This clones the repo as a bare clone into `.nexus/workshops/my-app.git` and adds it to `guild.json`. The workshop name is derived from the URL (the last path segment, minus `.git`). To use a custom name:
67
+
68
+ ```
69
+ nsg workshop add https://github.com/org/my-app.git --name frontend
70
+ ```
71
+
72
+ The repository must already exist and be accessible. SSH URLs work too:
73
+
74
+ ```
75
+ nsg workshop add git@github.com:org/my-app.git
76
+ ```
77
+
78
+ ### Creating a New Repository
79
+
80
+ For greenfield work where no repository exists yet:
81
+
82
+ ```
83
+ nsg workshop create myorg/new-project
84
+ ```
85
+
86
+ This requires the GitHub CLI (`gh`) to be installed and authenticated. The command:
87
+
88
+ 1. Creates the repository on GitHub (private by default)
89
+ 2. Clones it as a bare clone into `.nexus/workshops/`
90
+ 3. Registers it in `guild.json`
91
+
92
+ For a public repository:
93
+
94
+ ```
95
+ nsg workshop create myorg/new-project --public
96
+ ```
97
+
98
+ If `gh` is not installed or not authenticated, the command fails with a clear message explaining what's needed.
99
+
100
+ ### Workshop Status
101
+
102
+ `nsg workshop list` shows each workshop with:
103
+
104
+ - **✓ / ✗** — whether the bare clone exists on disk (it may be missing after a fresh guild clone before running `nsg guild restore`)
105
+ - **Active worktrees** — how many commissions currently have worktrees checked out
106
+ - **Remote URL** — where the repo lives
107
+
108
+ If a bare clone is missing, the output includes a hint to run `nsg guild restore`.
109
+
110
+ ### Removing a Workshop
111
+
112
+ ```
113
+ nsg workshop remove my-app
114
+ ```
115
+
116
+ This deletes the bare clone, any commission worktrees for that workshop, and removes the entry from `guild.json`. This is a destructive operation — the workshop's local state is gone. The remote repository is not affected.
117
+
118
+ ### How Workshops Are Used in Commissions
119
+
120
+ When a commission is dispatched to a workshop, the worktree-setup engine:
121
+
122
+ 1. Creates a commission-specific branch from `main` in the workshop's bare clone
123
+ 2. Checks out a git worktree at `.nexus/worktrees/{workshop}/commission-{id}/`
124
+ 3. The anima works in this isolated directory
125
+
126
+ This means multiple commissions can run concurrently in the same workshop without interfering with each other — each gets its own branch and working directory.
127
+
128
+ ### guild.json Shape
129
+
130
+ ```json
131
+ {
132
+ "workshops": {
133
+ "my-app": {
134
+ "remoteUrl": "https://github.com/org/my-app.git",
135
+ "addedAt": "2026-03-24T12:00:00.000Z"
136
+ }
137
+ }
138
+ }
139
+ ```
140
+
141
+ The `remoteUrl` is the source of truth. The bare clone on disk is ephemeral and can be reconstructed from this URL by `nsg guild restore`.
51
142
 
52
143
  ## Commissions
53
144
 
@@ -58,7 +149,7 @@ A commission is a unit of work posted by the patron and undertaken by the guild.
58
149
  3. **In progress** — the artificer works in a workshop worktree
59
150
  4. **Completed** or **Failed** — work is delivered or the commission is marked as failed
60
151
 
61
- Use `nsg dispatch` to post and dispatch commissions.
152
+ Use `nsg commission` to post commissions. The Clockworks handles the rest via standing orders.
62
153
 
63
154
  ## Tools
64
155
 
@@ -68,19 +159,27 @@ Tools that animas wield during work. Each tool ships with instructions delivered
68
159
 
69
160
  - **install-tool** — install new tools, engines, or bundles into the guild
70
161
  - **remove-tool** — remove installed tools
71
- - **dispatch** — post and dispatch commissions
162
+ - **commission** — post commissions to the guild
72
163
  - **instantiate** — create new animas with assigned training and roles
73
164
  - **nexus-version** — report the installed Nexus framework version
165
+ - **signal** — signal a custom guild event for the Clockworks
74
166
 
75
167
  ### Engines
76
168
 
77
- Automated mechanical processes with no AI involvement. Engines handle repeatable infrastructure work:
169
+ Automated mechanical processes with no AI involvement. Two kinds:
170
+
171
+ **Static engines** — bespoke APIs called by framework code. Not triggerable by standing orders.
78
172
 
79
173
  - **manifest** — composes anima instructions from codex, training, and tool instructions at session start
80
174
  - **mcp-server** — runs the MCP server that exposes tools to animas during sessions
81
175
  - **worktree-setup** — creates and manages git worktrees for commissions
82
176
  - **ledger-migrate** — applies database migrations to the Ledger
83
177
 
178
+ **Clockwork engines** — purpose-built to respond to events via standing orders. Use the `engine()` SDK factory from `@shardworks/nexus-core`. The Clockworks runner calls them automatically when matching events fire.
179
+
180
+ - **workshop-prepare** — creates a worktree when a commission is posted (`commission.posted` → `commission.ready`)
181
+ - **workshop-merge** — merges a commission branch after the session ends (`commission.session.ended` → `commission.completed` or `commission.failed`)
182
+
84
183
  ## The Codex
85
184
 
86
185
  The guild's institutional body of policy and procedure — the employee handbook. Lives in `codex/` in the guildhall. Every anima receives the codex when manifested. The codex defines how the guild operates: standards, procedures, policies, and environmental facts.
@@ -89,7 +188,139 @@ Role-specific codex entries live in `codex/roles/` and are delivered only to ani
89
188
 
90
189
  ## The Ledger
91
190
 
92
- The guild's operational database (SQLite). Holds anima records, roster, commission history, compositions, and the audit trail. Lives at `.nexus/nexus.db` in the guildhall. Managed by the ledger-migrate engine.
191
+ The guild's operational database (SQLite). Holds anima records, roster, commission history, compositions, events, and the audit trail. Lives at `.nexus/nexus.db` in the guildhall. Managed by the ledger-migrate engine.
192
+
193
+ ## The Clockworks
194
+
195
+ The Clockworks is the guild's event-driven nervous system — it connects things that happen to things that should happen in response. It turns the guild from a purely imperative system into a reactive one.
196
+
197
+ ### Events
198
+
199
+ An event is an immutable fact: *this happened*. Events are recorded in the Ledger and processed by the Clockworks runner.
200
+
201
+ Two kinds:
202
+
203
+ - **Framework events** — signaled automatically by the system (`commission.sealed`, `tool.installed`, `anima.instantiated`, etc.). Animas cannot signal these.
204
+ - **Custom events** — declared by the guild in `guild.json` under `clockworks.events`. Animas signal these using the `signal` tool.
205
+
206
+ ### Standing Orders
207
+
208
+ A standing order is a registered response to an event — guild policy that says "when X happens, do Y." Standing orders live in `guild.json` under `clockworks.standingOrders`.
209
+
210
+ Three verbs:
211
+
212
+ | Verb | What it does |
213
+ |------|-------------|
214
+ | **`run`** | Invokes a clockwork engine. No AI involved — deterministic automation. |
215
+ | **`summon`** | Manifests an anima (by role) and delivers the event as urgent context. The anima is expected to act. |
216
+ | **`brief`** | Manifests an anima (by role) and delivers the event as informational context. The anima decides whether to act. |
217
+
218
+ Standing orders target **roles**, not named animas — durable across anima turnover.
219
+
220
+ Example `guild.json` configuration:
221
+
222
+ ```json
223
+ {
224
+ "clockworks": {
225
+ "events": {
226
+ "code.reviewed": {
227
+ "description": "Signaled when an artificer completes a code review"
228
+ }
229
+ },
230
+ "standingOrders": [
231
+ { "on": "commission.sealed", "run": "cleanup-worktree" },
232
+ { "on": "commission.failed", "summon": "advisor" },
233
+ { "on": "code.reviewed", "brief": "guildmaster" }
234
+ ]
235
+ }
236
+ }
237
+ ```
238
+
239
+ ### Signaling Events
240
+
241
+ Use the **signal** tool to signal custom events:
242
+
243
+ ```
244
+ signal({ name: "code.reviewed", payload: { pr: 42, issues_found: 0 } })
245
+ ```
246
+
247
+ The event name must be declared in `guild.json clockworks.events`. Framework namespaces (`anima.*`, `commission.*`, `tool.*`, `migration.*`, `guild.*`, `standing-order.*`) are reserved.
248
+
249
+ ### Processing Events
250
+
251
+ Events are not processed automatically. The operator controls when the Clockworks runs:
252
+
253
+ | Command | What it does |
254
+ |---------|-------------|
255
+ | `nsg clock list` | Show all pending (unprocessed) events |
256
+ | `nsg clock tick [id]` | Process the next pending event, or a specific one by id |
257
+ | `nsg clock run` | Process all pending events until the queue is empty |
258
+
259
+ ### Error Handling
260
+
261
+ When a standing order fails, the system signals a `standing-order.failed` event. Guilds can respond to this with their own standing orders. A loop guard prevents cascading failures.
262
+
263
+ ### Hello World Walkthrough
264
+
265
+ To test the Clockworks from scratch:
266
+
267
+ **1. Declare a custom event** in `guild.json`:
268
+
269
+ ```json
270
+ {
271
+ "clockworks": {
272
+ "events": {
273
+ "hello.world": {
274
+ "description": "A test event for verifying the Clockworks"
275
+ }
276
+ },
277
+ "standingOrders": []
278
+ }
279
+ }
280
+ ```
281
+
282
+ **2. Signal the event:**
283
+
284
+ ```
285
+ nsg signal hello.world --payload '{"message": "greetings from the Clockworks"}'
286
+ ```
287
+
288
+ **3. Check the queue:**
289
+
290
+ ```
291
+ nsg clock list
292
+ ```
293
+
294
+ You should see the pending event with its id, name, payload, and timestamp.
295
+
296
+ **4. Process it:**
297
+
298
+ ```
299
+ nsg clock tick
300
+ ```
301
+
302
+ Since there are no standing orders, the event is marked as processed with no dispatches.
303
+
304
+ **5. Add a standing order** to `guild.json`:
305
+
306
+ ```json
307
+ {
308
+ "clockworks": {
309
+ "standingOrders": [
310
+ { "on": "hello.world", "brief": "advisor" }
311
+ ]
312
+ }
313
+ }
314
+ ```
315
+
316
+ **6. Signal again and process:**
317
+
318
+ ```
319
+ nsg signal hello.world
320
+ nsg clock tick
321
+ ```
322
+
323
+ The Clockworks matches the event to the standing order and dispatches it — the advisor is briefed.
93
324
 
94
325
  ## Training
95
326
 
@@ -103,6 +334,36 @@ Named, versioned, immutable personality templates. A temperament defines who an
103
334
 
104
335
  Training content lives in `training/curricula/` and `training/temperaments/` in the guildhall, organized as `{name}/{version}/`.
105
336
 
337
+ ## Guild Restore
338
+
339
+ When the guildhall repository is cloned fresh onto a new machine (or by a new developer), the `.nexus/` directory does not exist — it is gitignored. The guild's configuration and code are all tracked in git, but runtime state needs to be reconstructed.
340
+
341
+ ```
342
+ nsg guild restore
343
+ ```
344
+
345
+ This command reconstructs all ephemeral runtime state from the tracked guild configuration:
346
+
347
+ 1. **Workshops** — re-clones all workshop bare repos from their `remoteUrl` in `guild.json`. Skips any that are already present.
348
+ 2. **npm dependencies** — runs `npm install` to restore packages from `package.json`.
349
+ 3. **On-disk tools** — reinstalls tools that have full source tracked in the guildhall.
350
+ 4. **Reports linked tools** — lists any tools that were npm-linked and need manual re-linking (since symlinks don't survive a clone).
351
+
352
+ The command is idempotent — safe to run at any time. If everything is already in place, it reports "Nothing to restore."
353
+
354
+ ### When to Run Restore
355
+
356
+ - After cloning the guildhall repo for the first time
357
+ - After pulling changes that added new workshops
358
+ - If a bare clone is corrupted or accidentally deleted
359
+ - When `nsg workshop list` shows ✗ (missing bare clone) for any workshop
360
+
361
+ ### What Restore Does NOT Do
362
+
363
+ - It does not create the Ledger (that's done by `nsg init` and the ledger-migrate engine)
364
+ - It does not re-create animas or commissions — those live in the Ledger
365
+ - It does not push or pull workshop repos — it only clones them fresh if missing
366
+
106
367
  ## CLI Reference
107
368
 
108
369
  The primary interface is the `nsg` command:
@@ -110,10 +371,19 @@ The primary interface is the `nsg` command:
110
371
  | Command | Purpose |
111
372
  |---------|---------|
112
373
  | `nsg init` | Create a new guild |
113
- | `nsg dispatch <content>` | Post and dispatch a commission |
374
+ | `nsg commission <spec> --workshop <name>` | Post a commission |
114
375
  | `nsg tool install <source>` | Install a tool or bundle |
115
376
  | `nsg tool remove <name>` | Remove an installed tool |
377
+ | `nsg workshop add <url>` | Clone a remote repo and register it as a workshop |
378
+ | `nsg workshop remove <name>` | Remove a workshop |
379
+ | `nsg workshop list` | List workshops with status |
380
+ | `nsg workshop create <org/name>` | Create a new GitHub repo and register as a workshop |
381
+ | `nsg guild restore` | Restore runtime state after a fresh clone |
116
382
  | `nsg anima create` | Instantiate a new anima |
117
383
  | `nsg anima manifest <name>` | Generate an anima's full instructions |
118
384
  | `nsg status` | Show guild status |
119
385
  | `nsg consult <name>` | Consult a standing anima (e.g., the advisor) |
386
+ | `nsg signal <name>` | Signal a custom guild event |
387
+ | `nsg clock list` | Show pending events |
388
+ | `nsg clock tick [id]` | Process next pending event (or specific id) |
389
+ | `nsg clock run` | Process all pending events |
@@ -0,0 +1,24 @@
1
+ -- Clockworks tables: event log and dispatch tracking.
2
+ -- Part of Pillar 5 — the guild's event-driven nervous system.
3
+
4
+ CREATE TABLE events (
5
+ id INTEGER PRIMARY KEY,
6
+ name TEXT NOT NULL,
7
+ payload TEXT,
8
+ emitter TEXT NOT NULL,
9
+ fired_at TEXT NOT NULL DEFAULT (datetime('now')),
10
+ processed INTEGER NOT NULL DEFAULT 0
11
+ );
12
+
13
+ CREATE TABLE event_dispatches (
14
+ id INTEGER PRIMARY KEY,
15
+ event_id INTEGER NOT NULL REFERENCES events(id),
16
+ handler_type TEXT NOT NULL,
17
+ handler_name TEXT NOT NULL,
18
+ target_role TEXT,
19
+ notice_type TEXT,
20
+ started_at TEXT,
21
+ ended_at TEXT,
22
+ status TEXT,
23
+ error TEXT
24
+ );
@@ -0,0 +1,5 @@
1
+ -- Add status_reason to commissions for tracking why each state transition happened.
2
+ -- Every status change should include a reason: "posted by patron", "merged to main",
3
+ -- "merge conflict in src/foo.ts", etc.
4
+
5
+ ALTER TABLE commissions ADD COLUMN status_reason TEXT;
package/nexus-bundle.json CHANGED
@@ -3,7 +3,7 @@
3
3
  "tools": [
4
4
  { "package": "@shardworks/tool-install@0.x", "name": "install-tool" },
5
5
  { "package": "@shardworks/tool-remove@0.x", "name": "remove-tool" },
6
- { "package": "@shardworks/tool-dispatch@0.x", "name": "dispatch" },
6
+ { "package": "@shardworks/tool-commission@0.x", "name": "commission" },
7
7
  { "package": "@shardworks/tool-instantiate@0.x", "name": "instantiate" },
8
8
  { "package": "@shardworks/tool-nexus-version@0.x", "name": "nexus-version" }
9
9
  ],
@@ -11,15 +11,20 @@
11
11
  { "package": "@shardworks/engine-manifest@0.x", "name": "manifest" },
12
12
  { "package": "@shardworks/engine-mcp-server@0.x", "name": "mcp-server" },
13
13
  { "package": "@shardworks/engine-worktree-setup@0.x", "name": "worktree-setup" },
14
+ { "package": "@shardworks/engine-workshop-prepare@0.x", "name": "workshop-prepare" },
15
+ { "package": "@shardworks/engine-workshop-merge@0.x", "name": "workshop-merge" },
14
16
  { "package": "@shardworks/engine-ledger-migrate@0.x", "name": "ledger-migrate" }
15
17
  ],
16
18
  "temperaments": [
17
- { "path": "temperaments/guide" }
19
+ { "path": "temperaments/guide" },
20
+ { "path": "temperaments/artisan" }
18
21
  ],
19
22
  "curricula": [
20
23
  { "path": "curricula/guild-operations" }
21
24
  ],
22
25
  "migrations": [
23
- { "path": "migrations/001-initial-schema.sql" }
26
+ { "path": "migrations/001-initial-schema.sql" },
27
+ { "path": "migrations/002-clockworks.sql" },
28
+ { "path": "migrations/003-commission-status-reason.sql" }
24
29
  ]
25
30
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@shardworks/guild-starter-kit",
3
- "version": "0.1.16",
3
+ "version": "0.1.18",
4
4
  "description": "Default bundle for new Nexus guilds — tools, training, and migrations",
5
5
  "repository": {
6
6
  "type": "git",
@@ -0,0 +1,23 @@
1
+ # Artisan Temperament
2
+
3
+ You are an artisan — methodical, resourceful, and focused on delivering solid work. You take pride in craft, not in flash.
4
+
5
+ ## Disposition
6
+
7
+ - **Pragmatic.** Favor working solutions over elegant abstractions. Get something real running, then refine. Don't gold-plate.
8
+ - **Self-directed.** Once you have a clear brief, work independently. Make decisions within scope without asking permission for every detail. Use your judgment — that's why you were commissioned.
9
+ - **Thorough.** Test your work. Check edge cases. Read the error messages. Don't declare something done until you've verified it works, not just that it compiles.
10
+ - **Honest about problems.** If something isn't working, say so early. If the brief is unclear or contradictory, surface it rather than guessing. A well-timed question saves more time than a wrong assumption.
11
+
12
+ ## Communication Style
13
+
14
+ - Be concise. Commit messages and code comments are your primary output — make them clear and useful for the next anima who reads them.
15
+ - When reporting status, lead with what's done and what's blocked. Skip the preamble.
16
+ - If you encounter a design decision outside your brief, flag it and move on. Don't block on decisions that aren't yours to make.
17
+
18
+ ## Work Ethic
19
+
20
+ - Commit early and often. Small, atomic commits that tell a clear story.
21
+ - Leave the workshop cleaner than you found it. No dead code, no dangling TODOs, no mystery files.
22
+ - Respect the scope of your commission. Do the work you were asked to do. If you see adjacent improvements, note them — don't chase them.
23
+ - When sage advice is provided, follow it. The sage planned the work; you execute the plan. If you believe the plan has a flaw, record your concern, but do not contradict it unilaterally.
@@ -0,0 +1,4 @@
1
+ {
2
+ "version": "0.1.0",
3
+ "content": "content.md"
4
+ }