@spoolway/win32-x64 0.1.0 → 0.3.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 CHANGED
@@ -5,7 +5,13 @@
5
5
  </picture>
6
6
  </p>
7
7
 
8
- Minimalistic command line state machine for turning coding agents into a pipeline you can actually reason about. No dependencies, terminal native. Runs headless or controls supported multiplexers. Worktree management and built-in support for GitHub's stacked pull requests.
8
+ <p align="center">
9
+ <a href="LICENSE"><img alt="license" src="https://img.shields.io/github/license/marvingygas/spoolway?style=flat-square&label=license&labelColor=3f3f46&color=18181b"></a>
10
+ <a href="https://github.com/marvingygas/spoolway/actions/workflows/ci.yml"><img alt="ci" src="https://img.shields.io/github/actions/workflow/status/marvingygas/spoolway/ci.yml?branch=main&style=flat-square&label=ci&labelColor=3f3f46"></a>
11
+ <a href="https://github.com/marvingygas/spoolway/releases/latest"><img alt="release" src="https://img.shields.io/github/v/release/marvingygas/spoolway?style=flat-square&label=release&labelColor=3f3f46&color=18181b"></a>
12
+ </p>
13
+
14
+ Minimalistic command line state machine for turning coding agents into a pipeline you can actually reason about. No dependencies, terminal native. Runs headless or in a supported multiplexer. Manages worktrees and opens GitHub stacked pull requests.
9
15
 
10
16
  Supported providers:
11
17
 
@@ -20,34 +26,33 @@ Supported multiplexers:
20
26
 
21
27
  ## Why
22
28
 
23
- Running one coding agent is easy. Running five is tab-juggling: which one is done, which
24
- one is stuck, and which one is quietly rewriting a file another one needs. The order lives
25
- in your head, and it stops the moment you look away.
29
+ Running one coding agent is easy. Running five is hard: which one is done, which one is
30
+ stuck, and which one is rewriting a file another one needs. The order lives in your head.
26
31
 
27
- It replaces the orchestrating agent that is supposed to keep everything together — and
28
- sometimes does. spoolway won't surprise you with a bill or an opinion.
32
+ spoolway replaces the orchestrating agent that keeps everything together. It has no model
33
+ inside, so it never surprises you with a bill or an opinion.
29
34
 
30
35
  ## Features
31
36
 
32
- - **A dispatcher with no model in it.** Every scheduling decision is mechanical a
33
- counter, a timestamp, a position in the pipeline file. It never drifts, costs nothing,
34
- and is safe to interrupt at any point.
37
+ - **A dispatcher with no model in it.** Every scheduling decision is a counter, a
38
+ timestamp, or a position in the pipeline file. It costs nothing and is safe to interrupt.
35
39
  - **Any mix of agents.** Each step names its own agent and model: a local model for
36
- implementation, a cloud model for review, a shell command for the test suite.
37
- - **A worktree per task.** Every task builds on its own branch in its own checkout, so
38
- parallel tasks never step on each other.
40
+ implementation, a cloud model for review, a shell command for the tests.
41
+ - **A worktree per task.** Every task works on its own branch in its own checkout.
42
+ Parallel tasks never touch each other's files.
39
43
  - **Stacked pull requests.** A dependent task's branch is cut from its dependency's
40
- branch, so a chain of tasks arrives as one ordered stack of PRs. Nothing merges itself;
41
- you land the stack. Optional, and driven by **`spoolway stack`**.
42
- - **Session reuse.** A step can resume its prompt's earlier conversation instead of
43
- paying to rebuild context, bounded by how full the model's window already is.
44
- - **Unattended runs.** Overnight, nothing parks for a person: blocked work is resumed by
45
- an unblocker prompt, with an output-token ceiling as the brake.
46
- - **Trials.** Fork one task into an arm per pipeline and queue them together, then read the
47
- arms side by side in eval.
48
- - **Routines.** Keep the tasks you run over and over in `.spoolway/routines/`.
49
- - **Eval built in.** Every lane's spend and outcome land in a ledger, so you can see what
50
- your last pipeline edit did to pass rate and price.
44
+ branch. A chain of tasks arrives as one ordered stack of PRs. You land the stack.
45
+ Optional, driven by **`spoolway stack`**.
46
+ - **Session reuse.** A step can resume its prompt's earlier conversation. It stops
47
+ reusing when the model's window is too full.
48
+ - **Unattended runs.** Overnight, an unblocker prompt resumes blocked work. A token or
49
+ dollar ceiling stops the run.
50
+ - **Trials.** Fork a group into one arm per task, each on its own pipeline, and compare
51
+ the arms in eval.
52
+ - **Routines.** Keep the tasks you run more than once in `.spoolway/routines/`.
53
+ - **Jobs.** Run a routine on a cron schedule. A running dispatcher fires it.
54
+ - **Eval built in.** Every lane's spend and outcome go into a ledger. You see what your
55
+ last pipeline edit did to pass rate and price.
51
56
 
52
57
  ## Install
53
58
 
@@ -55,8 +60,9 @@ sometimes does. spoolway won't surprise you with a bill or an opinion.
55
60
  npm install -g spoolway
56
61
  ```
57
62
 
58
- A prebuilt binary, not a Node program the package is a thin wrapper that runs it. Linux
59
- (x64, arm64, musl), macOS (Apple Silicon, Intel) and Windows (x64, experimental).
63
+ The package is a small wrapper around a prebuilt binary. It runs on Linux (x64, arm64,
64
+ musl), macOS (Apple Silicon, Intel) and Windows (x64, experimental). `spoolway update` shows
65
+ what changed, and `spoolway whats-new` prints the release notes offline.
60
66
 
61
67
  From source instead, in a clone of this repository:
62
68
 
@@ -74,24 +80,20 @@ Platform notes and requirements in full: **[Installation and setup](docs/install
74
80
  spoolway init
75
81
  ```
76
82
 
77
- `spoolway doctor` checks that everything the configured pipeline needs is actually
78
- present, any time you want to confirm the project would run.
83
+ `spoolway doctor` checks that everything the configured pipeline needs is present.
79
84
 
80
85
  ### 2. Plan, or create queueable spoolway tasks directly
81
86
 
82
- Tell the `/spoolway-plan` skill what you want built. It argues the shape with you until
83
- every question is settled, and writes the result as one plan page. Approve the page and it
84
- cuts the plan into tasks.
87
+ Tell the `/spoolway-plan` skill what you want built. It talks the shape through with you
88
+ and writes one plan page. Approve the page and it cuts the plan into tasks.
85
89
 
86
90
  <img src="docs/screenshots/plan.png" alt="a plan page written by /spoolway-plan">
87
91
 
88
- Already know the shape you want? `/spoolway-tasks` skips the argument and cuts the task
89
- documents straight away.
92
+ If you already know the shape, `/spoolway-tasks` cuts the task documents straight away.
90
93
 
91
- **Both skills are optional.** A task is only a Markdown file in
92
- `~/.spoolway/<project>/pending/`, so anything that writes Markdown can produce one an
93
- issue exporter, a script, or a model you already talk to. The following command prints
94
- the frontmatter a task document must carry:
94
+ **Both skills are optional.** A task is a Markdown file in `~/.spoolway/<project>/pending/`.
95
+ An issue exporter, a script, or any model can write one. This command prints the
96
+ frontmatter a task document must carry:
95
97
 
96
98
  ```
97
99
  spoolway task contract
@@ -105,10 +107,10 @@ spoolway queue
105
107
 
106
108
  <img src="docs/screenshots/queue.png" alt="the queue screen">
107
109
 
108
- *The queue screen lists the groups on the left and previews the selected group's tasks on the
109
- right `enter` queues what is checked and offers to start dispatching on the spot. `g` gates
110
- a task on the fly, `p` forks one across several pipelines as a trial, and `r` opens the
111
- repeatable tasks you keep in `.spoolway/routines/`.*
110
+ *The queue screen lists groups on the left and the selected group's tasks on the right.
111
+ Each task names its own pipeline. `enter` queues what is checked and offers to start
112
+ dispatching. `g` gates a task, `p` forks a group into a trial, `s` saves a group as a
113
+ routine, and `r` opens the routines in `.spoolway/routines/`.*
112
114
 
113
115
  ### 4. Dispatch
114
116
 
@@ -118,32 +120,30 @@ spoolway dispatch # watch the board, and step in only where you are needed
118
120
 
119
121
  <img src="docs/screenshots/dispatch.png" alt="the dispatcher board">
120
122
 
121
- *One row per task, grouped by `group:`. The board says what each lane is spending as it
122
- spends it, what every queued task is waiting on, and which tasks are waiting on you the
123
- paused one above passed a gated step. Tasks can be paused and resumed from the board.*
123
+ *One row per task, grouped by `group:`. The board shows what each lane is spending, what
124
+ every queued task waits on, and which tasks are paused for you. NEXT tells a lane holding a
125
+ question apart from a task waiting at a gate. The bottom line shows the slots in use and
126
+ every scheduled job with its next firing.*
124
127
 
125
128
  Every task on the board is in one of a few states:
126
129
 
127
130
  | State | Meaning |
128
131
  |---|---|
129
132
  | `queued` | Waiting for its dependencies and a free slot. |
130
- | `running` | An agent is working the task's current step right now. |
131
- | `waiting on you` | A lane ended its turn on a question; answering it is what moves the task. |
132
- | `paused` | Passed a gated step; you decide whether it goes on. |
133
- | `blocked` | Something needs a person. |
133
+ | `running` | An agent is working the task's current step, or it has just moved there and a lane is starting. |
134
+ | `paused` | Waiting for you on purpose: a gate, a question in its pane, or a park. `r` on the board resumes it. |
135
+ | `blocked` | A step reported a block, or ran out of loops. Read the task's `## Blocker`, then `spoolway resume`. An unattended run hands it to the unblocker prompt instead. |
134
136
  | `unreachable` | A task it depends on is blocked, so it cannot start until you clear that one. |
135
137
  | `done` | Finished: the branch is handed over, the worktree removed, the task archived. |
136
138
 
137
139
  ### 5. Calibrate
138
140
 
139
- The `/spoolway-calibrate` skill reads your archived tasks and the spend ledger over them, and
140
- works out what actually cost you loops and money a prompt that keeps sending work back, a
141
- step running on a model far bigger than it needs.
141
+ The `/spoolway-calibrate` skill reads your archived tasks, their step-level evaluation results
142
+ and the spend ledger. It compares them with the prompts, pipelines and settings that produced
143
+ them. The comparison explains review failures, blocked sessions and wasted loops.
142
144
 
143
- It walks each finding with you, with the arithmetic behind it. The ones you keep are cut
144
- into tasks of their own, so the fix to your pipeline goes through the same line as
145
- everything else. This is how a pipeline that blocks constantly turns into one that runs
146
- unattended.
145
+ It walks each finding with you, with the numbers behind it. It applies the prompt and pipeline
146
+ changes you pick.
147
147
 
148
148
  ## A task is what travels the line, and you define it
149
149
 
@@ -164,8 +164,8 @@ depends_on:
164
164
  ## References
165
165
  ```
166
166
 
167
- **The frontmatter is spoolway's, the body is yours.** spoolway never reads the body; it is
168
- what the agent works from, written from a skeleton you own.
167
+ **The frontmatter is spoolway's, the body is yours.** spoolway never reads the body. The
168
+ agent works from it, and you own the skeleton it is written from.
169
169
 
170
170
  ## The pipeline is a file
171
171
 
@@ -181,7 +181,7 @@ steps:
181
181
  description: Write the code to satisfy the task's acceptance criteria.
182
182
  agent: pi
183
183
  prompt: implementer
184
- model: qwen3-coder-30b
184
+ model: Ornith-1.5-35B-A3B
185
185
  session: true
186
186
  on_pass: review
187
187
  on_fail: blocked
@@ -202,7 +202,7 @@ steps:
202
202
  description: Bring the domain documents in line with what this task changed.
203
203
  agent: pi
204
204
  prompt: archivist
205
- model: qwen3-coder-30b
205
+ model: Ornith-1.5-35B-A3B
206
206
  on_pass: handover
207
207
  on_fail: blocked
208
208
 
@@ -221,75 +221,150 @@ steps:
221
221
  on_fail: blocked
222
222
  ```
223
223
 
224
- **You do not have to write one by hand.** The `/spoolway-pipeline` skill writes a pipeline
225
- for you, and edits the one you already have.
224
+ **You do not have to write one by hand.** The `/spoolway-config` skill writes and edits
225
+ pipelines for you.
226
226
 
227
- ## Configurable per project
227
+ ## Jobs
228
+
229
+ A job runs a routine on a schedule. It has three parts: a cron expression, a pipeline, and a
230
+ routine saved under `.spoolway/routines/`.
231
+
232
+ The dispatcher fires a due job at the start of its pass. While any job is enabled, the
233
+ dispatcher stays up on an empty queue. A `spoolway dispatch` left running overnight is all a
234
+ job needs.
235
+
236
+ ```
237
+ spoolway jobs # the screen: write, edit, pause, delete, or fire a job
238
+ spoolway jobs list # every job, its schedule, and when it fires next
239
+ spoolway jobs run <name> # fire one now, ignoring its schedule
240
+ ```
241
+
242
+ <img src="docs/screenshots/jobs.png" alt="the jobs screen">
228
243
 
229
- - Unattended mode delegates **`blocked`** tasks to a prompt you define. It clears
230
- obstacles on its own and keeps your pipeline running while nobody is watching.
231
- - Set specific models for generating pipelines or pull request summaries.
244
+ *The jobs screen. `n` asks for three things: the routine, the cron expression, and the
245
+ pipeline. A job fires once per matching minute. It skips a window while its previous run is
246
+ still in the queue. A window that passes while no dispatcher runs is not caught up later.*
247
+
248
+ A job is a few lines of TOML in `~/.spoolway/<project>/jobs.toml`. Put one in
249
+ `.spoolway/jobs.toml` inside the checkout to share it with the team.
232
250
 
233
251
  ```toml
234
- skills = ["spoolway-plan"] # which skills `spoolway eval` gives a block of their own
252
+ [jobs.nightly-audit]
253
+ schedule = "0 3 * * 1-5" # weekdays at 03:00, local time
254
+ pipeline = "impl_fast"
255
+ routine = "nightly" # a folder or a single .md under .spoolway/routines/
256
+ ```
257
+
258
+ ### Routines
259
+
260
+ A routine is work you run more than once. It lives in `.spoolway/routines/`, tracked in git.
261
+ Press `s` on a group in the queue screen to save it there, and `r` to browse and queue what is
262
+ saved. Every queued copy gets a fresh id, so a routine can run again. The saved files are
263
+ never changed.
264
+
265
+ ### Trials
266
+
267
+ A trial answers one question: which pipeline does this task best? Press `p` on a group in the
268
+ queue screen, pick a pipeline per task, and tick any steps to skip. Every task becomes one arm
269
+ under its chosen pipeline, and all arms share one trial id. Compare them with
270
+ `spoolway eval --runs --trial <id>`. An arm never pushes a branch or opens a pull request. When
271
+ the last arm finishes, every arm's copy is removed. The source group and the ledger rows stay.
272
+
273
+ ## Issue tracker
274
+
275
+ Event hooks sync tasks with an issue tracker. Sample scripts for GitHub and Jira ship with `spoolway init`.
276
+
277
+ | Event | When it fires |
278
+ |---|---|
279
+ | `fetch` | `spoolway issue show <ref>` reads one issue out of the tracker |
280
+ | `open` | `spoolway queue add` opens a ticket per document |
281
+ | `queued` | A task arrives in the queue |
282
+ | `blocked` | A task comes to rest on `blocked` |
283
+ | `paused` | A task arrives on the persisted `paused` stage; a live-step row whose public state is `paused` does not fire it |
284
+ | `done` | A task finishes |
235
285
 
286
+ **The two shipped scripts are samples.** `spoolway init` writes `github.sh` and `jira.sh` into
287
+ `.spoolway/hooks/`. A native Windows install gets the `.ps1` pair.
288
+
289
+ See **[Issue Tracking](docs/configuration.md#issue_tracking--a-hook-fired-on-four-task-events)**.
290
+
291
+ ## Configurable per project
292
+
293
+ - Unattended mode hands **`blocked`** tasks to a prompt you define, so the pipeline keeps
294
+ running while nobody is watching.
295
+ - Set a model for generating pipelines.
296
+
297
+ ```toml
236
298
  [dispatch]
237
299
  backend = "herdr" # herdr, tmux, or headless
238
300
  herdr_mode = "split" # "split": a workspace per task; "grouped": one shared tab, a pane per task
239
- interval = "10s"
301
+ tmux_mode = "grouped" # "grouped": one session for the run; "split": a session per task
302
+ worktree_root = "" # where a task's worktree is cut; blank is ~/.spoolway/<project>/worktrees
303
+ interval = "10s" # how long the dispatcher waits between passes
240
304
  lane_quiet = "15m" # silence before a lane is reminded to report
241
305
  default_pipeline = "default" # which pipeline a task runs when it names none
242
- auto_commit = true
306
+ auto_commit = true # commit a lane's leftover work when its step settles
243
307
 
244
308
  [unattended]
245
309
  enabled = true # the overnight switch
246
- max_output_tokens = 0 # spend ceiling for a run with nobody watching; 0 is none
310
+ max_output_tokens = 0 # output-token ceiling for a run with nobody watching; 0 is none
311
+ max_cost_usd = 0.0 # dollar ceiling for the same run; 0 is none
247
312
  skip_blocked_lane = true # a cleared block carries the task past the step it blocked on
248
313
  blocked_agent = "claude" # who staffs `blocked` when nobody is at the keyboard
249
314
  blocked_model = "claude-opus-5"
250
315
  blocked_effort = "medium"
316
+ blocked_session = true # the unblocker carries its own earlier session forward
251
317
  blocked_prompt = "unblocker"
252
318
 
253
319
  [pipeline_gen]
254
320
  pipeline_agent = "claude" # who `spoolway pipeline gen` opens its session as
255
321
  pipeline_model = "claude-opus-5"
256
322
  pipeline_effort = "medium"
257
- pipeline_auto = false # false asks before writing the pipeline
258
- pipeline_local_models = false
259
323
 
260
- [update]
261
- check = true # tell a person at a keyboard that a newer release is out
324
+ [housekeeping]
325
+ update_check = true # tell a person at a keyboard that a newer release is out
326
+ calibrate_window = "14d" # how far back `/spoolway-calibrate` reads
327
+ retention_days = 30 # how long run records and archived tasks are kept; 0 keeps everything
328
+ price_max_age_days = 30 # how old the price table may be before `spoolway doctor` says so
262
329
 
263
- [calibrate]
264
- window = "14d" # how far back `/spoolway-calibrate` reads
330
+ [agents.claude]
331
+ kind = "claude"
332
+ concurrency = 3 # most lanes of this profile at once
333
+ session_reuse_ctx = 50 # % of the window before a carried session restarts fresh
334
+ session_blocked_ctx = 0 # % of the window at which a running lane is stopped and blocked; 0 is off
335
+ permission_mode = "auto"
265
336
 
266
- [stack.summary]
267
- agent = "claude" # writes each PR's title and summary
268
- model = "claude-haiku-4-5" # blank: the task file itself is the PR body
269
- prompt = "summariser"
337
+ [agents.codex]
338
+ kind = "codex"
339
+ concurrency = 3
340
+ session_reuse_ctx = 50
341
+ session_blocked_ctx = 0
342
+ permission_mode = "never"
270
343
 
271
344
  [agents.pi]
272
345
  kind = "pi"
273
- session_reuse_ctx = 50 # % of the window before a carried session restarts fresh
274
-
275
- [agents.claude]
276
- kind = "claude"
277
- concurrency = 3
278
346
  session_reuse_ctx = 50
279
- permission_mode = "auto"
347
+ session_blocked_ctx = 0
280
348
 
281
- [models."*qwen3-coder-30b*"]
349
+ [models."Ornith-1.5-35B-A3B"] # a local model, served by llama.cpp
282
350
  context_window = 100096
283
- slots = 3 # parallel lanes the local server can actually hold
351
+ slots = 2 # parallel lanes the local server can actually hold
284
352
  exclusive = true # never alongside another exclusive model
353
+ local = true # runs on hardware you own
354
+
355
+ [issue_tracking]
356
+ hook = "" # a script in .spoolway/hooks/, e.g. "github.sh"; blank runs none
357
+ project_key = "" # handed to the hook verbatim, e.g. owner/repo
358
+ on_fail = "ignore" # what a failing hook does: ignore it, or pause the task
359
+ key_in_names = false # prefix branch and worktree names with the tracker's slug
285
360
  ```
286
361
 
287
362
  See **[Configuration](docs/configuration.md)**.
288
363
 
289
364
  ## Eval every run
290
365
 
291
- Every lane's transcript is read when it settles and banked to a ledger: tokens, cost, wall
292
- time, and what the lane reported. Every edit to your pipelines, prompts or config mints a
366
+ When a lane finishes, its transcript is read and written to a ledger: tokens, cost, wall
367
+ time, and what the lane reported. Every edit to your pipelines, prompts or config creates a
293
368
  new version, so you can see what your last change did to pass rate and price.
294
369
 
295
370
  ```
@@ -298,13 +373,13 @@ spoolway eval
298
373
 
299
374
  <img src="docs/screenshots/eval.png" alt="the eval screen">
300
375
 
301
- *The eval screen on its runs view, one row per attempt at a task `tab` cycles the four
302
- views: the version comparisons per pipeline and per step, this one, and what your skills
303
- came to. `f` filters, `e` exports CSV.*
376
+ *The eval screen on its runs view, one row per attempt at a task. `tab` cycles the views: per
377
+ pipeline, per step, runs, per watched directory, and per session outside the lanes. `f` filters,
378
+ `e` exports CSV.*
304
379
 
305
380
  ## Documentation
306
381
 
307
- See **[Documentation index](DOCS.md)**.
382
+ See **[Documentation index](DOCS.md)**.
308
383
 
309
384
  ## License
310
385
 
package/bin/spoolway.exe CHANGED
Binary file
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@spoolway/win32-x64",
3
- "version": "0.1.0",
3
+ "version": "0.3.0",
4
4
  "description": "spoolway binary for win32 x64",
5
5
  "license": "MIT",
6
6
  "author": "Marvin Gygas",