@neriros/ralphy 3.8.8 → 3.8.9

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
@@ -81,7 +81,7 @@ export LINEAR_API_KEY=lin_api_xxx
81
81
  ralphy agent --linear-team ENG --linear-assignee me --concurrency 3 --poll-interval 60
82
82
  ```
83
83
 
84
- A default `ralphy.config.json` is written on first run. CLI flags override config per-invocation.
84
+ Configuration lives in **`WORKFLOW.md`** at the project root — YAML frontmatter for settings, followed by a Jinja-style prompt template the worker renders for every iteration. A default is written on first run. CLI flags override config per-invocation.
85
85
 
86
86
  ### Lifecycle and triggers
87
87
 
@@ -169,48 +169,70 @@ A `Marker` is one of three types:
169
169
 
170
170
  Use an array when one event sets multiple — e.g. `setDone` flipping a status _and_ adding a label _and_ updating the attachment subtitle.
171
171
 
172
- Example `ralphy.config.json`:
173
-
174
- ```jsonc
175
- {
176
- "concurrency": 3,
177
- "pollIntervalSeconds": 60,
178
- "engine": "claude",
179
- "model": "opus",
180
- "useWorktree": true,
181
- "createPrOnSuccess": true,
182
- "autoMergeStrategy": "squash",
183
- "fixCiOnFailure": true,
184
- "linear": {
185
- "team": "ENG",
186
- "assignee": "me",
187
- "postComments": true,
188
- "updateEveryIterations": 10,
189
- "mentionTrigger": true,
190
- "mentionHandle": "@ralphy",
191
- "codeReviewTrigger": true,
192
- "codeReviewStaleHours": 24,
193
- "syncTasksToComment": true,
194
- "syncTasksToDescription": false,
195
- "indicators": {
196
- "getTodo": { "filter": [{ "type": "status", "value": "Todo" }] },
197
- "getInProgress": {
198
- "filter": [{ "type": "status", "value": "In Progress" }],
199
- },
200
- "getReview": { "filter": [{ "type": "label", "value": "ralph:review" }] },
201
- "getAutoMerge": {
202
- "filter": [{ "type": "label", "value": "ralph:auto-merge" }],
203
- },
204
- "setInProgress": { "type": "status", "value": "In Progress" },
205
- "setDone": [
206
- { "type": "status", "value": "In Review" },
207
- { "type": "label", "value": "ralphy-done" },
208
- ],
209
- "setError": { "type": "label", "value": "ralph:error" },
210
- "clearReview": { "type": "label", "value": "ralph:review" },
211
- },
212
- },
213
- }
172
+ Example `WORKFLOW.md` frontmatter — the prompt template after the closing `---` is omitted here; see the bundled default for the full file:
173
+
174
+ ```yaml
175
+ ---
176
+ concurrency: 3
177
+ pollIntervalSeconds: 60
178
+ engine: claude
179
+ model: opus
180
+ useWorktree: true
181
+ createPrOnSuccess: true
182
+ autoMergeStrategy: squash
183
+ fixCiOnFailure: true
184
+
185
+ linear:
186
+ team: ENG
187
+ assignee: me
188
+ postComments: true
189
+ updateEveryIterations: 10
190
+ mentionTrigger: true
191
+ mentionHandle: "@ralphy"
192
+ codeReviewTrigger: true
193
+ codeReviewStaleHours: 24
194
+ syncTasksToComment: true
195
+ syncSpecsAsAttachments: true
196
+
197
+ indicators:
198
+ # Todo In Progress
199
+ getTodo:
200
+ filter:
201
+ - type: status
202
+ value: Todo
203
+ getInProgress:
204
+ filter:
205
+ - type: status
206
+ value: In Progress
207
+ setInProgress:
208
+ type: status
209
+ value: In Progress
210
+
211
+ # Done / review hand-off
212
+ setDone:
213
+ - type: status
214
+ value: In Review
215
+ - type: label
216
+ value: ralphy-done
217
+ getReview:
218
+ filter:
219
+ - type: label
220
+ value: "ralph:review"
221
+ clearReview:
222
+ type: label
223
+ value: "ralph:review"
224
+
225
+ # Auto-merge opt-in
226
+ getAutoMerge:
227
+ filter:
228
+ - type: label
229
+ value: "ralph:auto-merge"
230
+
231
+ # Error quarantine
232
+ setError:
233
+ type: label
234
+ value: "ralph:error"
235
+ ---
214
236
  ```
215
237
 
216
238
  #### Confirmation mode (human gate before `implement`)
@@ -231,9 +253,14 @@ After `timeoutHours` (default `48`) with no activity Ralphy posts a single nudge
231
253
 
232
254
  Wire up the matching indicators alongside the rest of the `linear.indicators` map:
233
255
 
234
- ```jsonc
235
- "getApproved": { "filter": [{ "type": "label", "value": "ralph:approved" }] },
236
- "clearApproved": { "type": "label", "value": "ralph:approved" }
256
+ ```yaml
257
+ getApproved:
258
+ filter:
259
+ - type: label
260
+ value: "ralph:approved"
261
+ clearApproved:
262
+ type: label
263
+ value: "ralph:approved"
237
264
  ```
238
265
 
239
266
  See `linear.confirmationMode` in `WORKFLOW.md` for the full set of knobs.
@@ -259,15 +286,13 @@ The loop exits; the next poll re-checks the PR. The cycle continues until the PR
259
286
 
260
287
  Once every task in `tasks.md` is checked off, the worker can spawn an in-process reviewer pass before exiting. The reviewer reads `proposal.md`, `design.md`, and the diff, and either appends new tasks back into `tasks.md` (looping the worker for another round) or signs off. Configure under `openspec.reviewPhase`:
261
288
 
262
- ```jsonc
263
- "openspec": {
264
- "reviewPhase": {
265
- "enabled": true,
266
- "maxRounds": 2, // hard cap on review iterations (default 1)
267
- "reviewerModel": "claude-sonnet-4-6", // override the reviewer's model (optional)
268
- "reviewerContextStrategy": "fresh" // "fresh" = clean context per round (default), "warm" = reuse worker context
269
- }
270
- }
289
+ ```yaml
290
+ openspec:
291
+ reviewPhase:
292
+ enabled: true
293
+ maxRounds: 2 # hard cap on review iterations (default 1)
294
+ reviewerModel: claude-sonnet-4-6 # override the reviewer's model (optional)
295
+ reviewerContextStrategy: fresh # "fresh" = clean context per round (default), "warm" = reuse worker context
271
296
  ```
272
297
 
273
298
  CLI equivalents: `--review-enabled`, `--review-max-rounds <N>`, `--review-model <id>`, `--review-context-strategy fresh|warm`. The worker passes these to itself when respawning, so the same review settings apply across `respawn` / `conflict-fix` / `ci-fix` lifecycles.
@@ -286,16 +311,6 @@ The first time planning completes (every `- [ ]` under `## Planning` in
286
311
  summarizing `proposal.md` (`## Why` + `## What Changes`) and the first
287
312
  paragraph of `design.md`.
288
313
 
289
- ##### Legacy: sync into the issue description
290
-
291
- Set `linear.syncTasksToDescription: true` to mirror `tasks.md` into the
292
- linked Linear issue description body instead (the pre-RLF-62 behavior).
293
- Ralph writes a checklist between sentinel HTML comments
294
- (`<!-- ralphy:tasks:start -->` / `<!-- ralphy:tasks:end -->`); content
295
- outside the markers is preserved verbatim. When both
296
- `syncTasksToComment` and `syncTasksToDescription` are true,
297
- comment-sync wins and a one-time warning is logged.
298
-
299
314
  #### Conflict re-fix / CI re-fix
300
315
 
301
316
  Every poll, the merge-state scanner reads `gh pr view --json state,mergeable,mergeStateStatus,statusCheckRollup` for each tracked PR:
@@ -340,16 +355,15 @@ HEAD. If any command fails:
340
355
  When the baseline goes green (the human merged the fix), the next poll lifts
341
356
  the pause automatically.
342
357
 
343
- ```jsonc
344
- {
345
- "preExistingErrorCheck": {
346
- "enabled": false,
347
- "commands": ["bun run lint", "bun run test"], // falls back to commands.lint + commands.test when empty
348
- "baseBranch": "main",
349
- "label": "ralph:pre-existing-error",
350
- "outputCharLimit": 4000,
351
- },
352
- }
358
+ ```yaml
359
+ preExistingErrorCheck:
360
+ enabled: false
361
+ commands: # falls back to commands.lint + commands.test when empty
362
+ - bun run lint
363
+ - bun run test
364
+ baseBranch: main
365
+ label: "ralph:pre-existing-error"
366
+ outputCharLimit: 4000
353
367
  ```
354
368
 
355
369
  ### Worktrees, setup, teardown
@@ -444,7 +458,7 @@ Failed workers are not marked processed, so they retry on the next poll. SIGINT
444
458
  | --------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
445
459
  | `--debug --name <id>` | Diagnose why a Linear ticket (e.g. `ENG-42`) is not being picked up — checks team, assignee, include / exclude markers, and blocked-by relations against every configured `get*` indicator. |
446
460
 
447
- `ralph list` reads `ralphy.config.json` and, when `LINEAR_API_KEY` is set, fetches every issue matching each configured `getTodo` / `getInProgress` / `getReview` / `getAutoMerge` indicator using the same include / exclude rules as `ralph agent`. For each ticket it also resolves the linked GitHub PR URL from Linear attachments and prints its conflict / CI status from `gh pr view`.
461
+ `ralph list` reads `WORKFLOW.md` and, when `LINEAR_API_KEY` is set, fetches every issue matching each configured `getTodo` / `getInProgress` / `getReview` / `getAutoMerge` indicator using the same include / exclude rules as `ralph agent`. For each ticket it also resolves the linked GitHub PR URL from Linear attachments and prints its conflict / CI status from `gh pr view`.
448
462
 
449
463
  **`--max-tickets`.** Caps how many issues ralph picks up in a single agent run. Once the limit is hit the coordinator stops enqueuing new work; in-flight workers continue to completion, and the dashboard header shows `│ tickets ≤N`. The limit resets each restart.
450
464
 
@@ -18928,8 +18928,8 @@ import { readFileSync } from "fs";
18928
18928
  import { resolve } from "path";
18929
18929
  function getVersion() {
18930
18930
  try {
18931
- if ("3.8.8")
18932
- return "3.8.8";
18931
+ if ("3.8.9")
18932
+ return "3.8.9";
18933
18933
  } catch {}
18934
18934
  const dirsToTry = [];
18935
18935
  try {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@neriros/ralphy",
3
- "version": "3.8.8",
3
+ "version": "3.8.9",
4
4
  "description": "An iterative AI task execution framework. Orchestrates multi-phase autonomous work using Claude or Codex engines.",
5
5
  "keywords": [
6
6
  "agent",