pi-jar 0.1.8 → 0.1.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 +12 -9
- package/docs/DISCUSSION_BROKER_PLAN.md +333 -0
- package/docs/INTEGRATIONS.md +1 -1
- package/docs/LONG_SESSION_PERFORMANCE_PLAN.md +731 -0
- package/docs/SUBAGENT-TOOLS.md +2 -0
- package/extensions/index.ts +153 -63
- package/package.json +1 -1
- package/src/activity-view.ts +10 -6
- package/src/delegate.ts +727 -422
- package/src/democracy.ts +6 -4
- package/src/discussion-hub.ts +418 -0
- package/src/discussion.ts +419 -187
- package/src/footer-settings.ts +3 -29
- package/src/perf.ts +419 -0
- package/src/quota.ts +65 -25
- package/src/settings.ts +2 -12
- package/src/shells.ts +134 -28
package/README.md
CHANGED
|
@@ -61,6 +61,7 @@ Pi only delivers mouse events in its **fullscreen** TUI mode. In regular mode th
|
|
|
61
61
|
| `/jar commit [note]` | Draft a commit message for the staged changes with the `commit` role, edit it, and commit. Offers `git add -A` when nothing is staged. |
|
|
62
62
|
| `/jar` · `/jar settings` | Visual and workflow preferences. |
|
|
63
63
|
| `/jar status` | One-line status summary. |
|
|
64
|
+
| `/jar perf` | Long-session diagnostics on demand: branch entries, context sampling, parent and child RSS, retained/hibernated subagents and recovery worktrees, render requests vs. frames, shell output, discussion and quota cache. |
|
|
64
65
|
| `/jar tasks [list\|add\|done\|open\|edit\|delete]` | Human view/editor for the agent's checklist. |
|
|
65
66
|
| `/jar history` | Read-only conversation timeline for the active branch. |
|
|
66
67
|
| `/diff` | Review, accept or revert the files the agent changed. |
|
|
@@ -71,7 +72,7 @@ Pi only delivers mouse events in its **fullscreen** TUI mode. In regular mode th
|
|
|
71
72
|
| `/jar ask [question]` | Answer a question in a dialog and insert the answer into the editor. |
|
|
72
73
|
| `/jar accent [preset]` · `/jar footer` · `/jar icons [unicode\|nerd\|ascii]` | Switch a loaded accent theme; toggle footer fields; pick the icon set. |
|
|
73
74
|
| `/jar composer on\|off` · `/jar animations on\|off` · `/jar ui on\|off` | Toggle the composer, motion, or all pi-jar UI. |
|
|
74
|
-
| `/jar quota on\|off` | Session-only, read-only quota lookups for supported OAuth providers. |
|
|
75
|
+
| `/jar quota on\|off` | Session-only, read-only quota lookups for supported OAuth providers. Lookups start on session boundaries (startup, prompts, model changes), never from a render: at most one per provider every 5 minutes, and failures back off up to 30 minutes. |
|
|
75
76
|
| `/jar hub` | Open an installed task or subagent manager command. |
|
|
76
77
|
| `/jar demo` · `/jar reset` | Labeled sample roles in the footer / back to live data. |
|
|
77
78
|
|
|
@@ -255,16 +256,16 @@ This is a pi-jar enhancement: [pi-advisor](https://github.com/philipbrembeck/pi-
|
|
|
255
256
|
Use `parent` with `append` to add a genuinely new subtask to active work; `start`, `done`, `open`, `edit`, `list`, `add` and `delete` remain available.
|
|
256
257
|
- **`jar_ask`** — structured questions: numbered options with descriptions, single or multi-select, *Type your own answer* (multi-line, paste-friendly) and *Chat about this* to discuss before choosing.
|
|
257
258
|
- **`/diff`** — review what the agent (and its editing subagents) changed since the first edit to each file: files with `+/−` counts on the left, a full-path header and numbered, colored diff on the right. Changed lines get a colored rail and tinted background, replaced lines highlight the changed words, code is syntax-highlighted for known languages, and collapsed regions are labeled `┄ N unchanged lines ┄`. `/` filters files; `t` switches unified and aligned side-by-side views (unified below 70 columns), `←`/`→` (or `[`/`]`) change the context from 0 lines to the whole file, `w` wraps long lines, and `n`/`p`, `Home`/`End` navigate. Large changes offer summary or explicit windowed review (`v`), with clearly labeled coarse fallback and existing safety limits—not arbitrary-file streaming. See [diff review](docs/DIFF-REVIEW.md). `a` accept (keep, stop tracking), `r` then `y` revert (restore the original, or remove a file it created), `A`/`R` for all. The footer shows `± N files · /diff` while anything is unreviewed; each file counts once no matter who edited it. Only `edit`/`write` changes inside the project are tracked; shell-made changes are not.
|
|
258
|
-
- **`jar_shell`** — `start` (
|
|
259
|
-
- **`jar_delegate`** — spawns
|
|
260
|
-
- **`jar_subagent`** —
|
|
259
|
+
- **`jar_shell`** — `start` (optional `name`, `watch` regex, `notify`, task/service `purpose`), `list`, `peek`, bounded `wait`, `output`, `kill`. ANSI-stripped logs have per-job caps and a 4 MiB aggregate budget; surfaced finished jobs compact to a 32 KiB tail. Live jobs retain useful tails and are never killed to reclaim logs. Watch/exit notifications are compact and coalesced; reads acknowledge observed events. Each running shell gets a footer row and an activity view (`/jar shells`) with `x` kill and `f` follow. All shells stop when the session ends.
|
|
260
|
+
- **`jar_delegate`** — spawns retained, session-scoped subagents up to **Max subagents** in `/jar settings` (2, 4, 6, 8 or 16; default 4). Idle, paused and hibernated agents count toward this pool; over-cap batches are rejected. `scout` is fresh/read-only, `fork` inherits conversation read-only, and `worktree` forks context into a path-guarded Git worktree. Settled retained agents close their Pi process after 30 seconds of quiet while keeping their private session and workspace; `resume`/`ask` relaunch that same session. Launch returns before startup or the first turn completes, including legacy one-shot `write: true` mode.
|
|
261
|
+
- **`jar_subagent`** — `peek` reports progress, including the workspace path and changed files for recovery records; `steer` redirects a running worker; `resume` relaunches an idle/paused/hibernated agent. `ask`, `pause` and `stop` return accepted receipts immediately; answers and final handoffs arrive as `pi-jar.subagent` events. `stop` reconciles safe worktree changes; conflicts remain private and can be retried with `stop` after resolving parent drift. `discard` removes an unresolved recovery worktree without applying it. At most four active/recovery worktrees are admitted; resolve or discard one before starting another. Session shutdown reports paths of any preserved worktrees. Controls do not poll the child.
|
|
261
262
|
- **Subagent capabilities** — each task can set `tools` or `inheritTools: true`; known-tool mode filters and child guards remain in force. See [tool capabilities](docs/SUBAGENT-TOOLS.md).
|
|
262
|
-
- **Worktree finalization** —
|
|
263
|
-
- **`jar_democracy`** — **exceptional only**, for a persistent
|
|
264
|
-
- **`jar_discuss`** —
|
|
263
|
+
- **Worktree finalization** — edits do not touch the parent merely because a worker settles or hibernates. On `jar_subagent stop`, pi-jar checks parent drift and reviewability, applies safe changes and adds them to `/diff`; conflicts remain isolated for retry or explicit discard. Failed worktree transcripts are compacted independently of finished history. Process closure is awaited before finalization, and failed multi-file application rolls back rather than leaving a partial result.
|
|
264
|
+
- **`jar_democracy`** — **exceptional only**, for a persistent super-complex issue with several evidence-backed options after at least two distinct failed approaches. The moderator opens 2–8 options, resumes relevant idle/paused/hibernated fresh-context read-only scouts or spawns new scouts within the pool, and collects one private ballot per voter. A strict majority of invited voters wins; ties, plurality or missing/invalid ballots require user choice. Voting never implements its recommendation. A round has a 10-minute deadline and bounded rationales.
|
|
265
|
+
- **`jar_discuss`** — session-local, parent-owned discussion broker over authenticated local IPC; no shared paper, lock or polling. `ask`/`answer` return stable IDs without echoing your text. `list` reads only relevant unread questions/answers and advances your cursor; `thread` (or `list` with `questionId`) reads one thread; `pending` shows counts without message bodies. `since: "d0"` rereads relevant mail. At most 128 messages, 1600 characters each and 128 KiB are retained; unread/unanswered questions block new posts instead of being silently lost. Messages do not wake idle agents; the next natural turn gets an unread notice.
|
|
265
266
|
- **Activity view** — one split view (<kbd>Ctrl</kbd>+<kbd>Alt</kbd>+<kbd>A</kbd>, `/jar activity`, or a click on a footer row) for subagents, background shells and other extensions' teammates: list on the left, live details on the right (auto-follows; scroll up to pause, `f` to follow again). For a subagent the details show its task, its own checklist with subtasks, and a transcript like omp's: each tool call and message is one collapsed line that expands on demand (`Tab` into it, `↑↓`, `Enter`, or click) to show arguments and output, while streaming text shows live. `s` opens a steering input: type a message and press `Enter` to redirect the running subagent. `x` stops just that one. Finished runs stay listed for review.
|
|
266
267
|
- **`/jar history`** — separate, read-only timeline of the active branch (paging, search, expandable details). Pi's native transcript is untouched.
|
|
267
|
-
- Pi's built-in read/shell/edit/write tool cards render compactly: collapsed, each is one padded, state-colored card with its call line and a one-line summary (edit included), and partially streamed arguments never flicker to a fallback; the full output or diff stays one click or <kbd>Ctrl</kbd>+<kbd>O</kbd> away.
|
|
268
|
+
- Pi's built-in read/shell/edit/write tool cards render compactly: collapsed, each is one padded, state-colored card with its call line and a one-line summary (edit included), and partially streamed arguments never flicker to a fallback; the full output or diff stays one click or <kbd>Ctrl</kbd>+<kbd>O</kbd> away. Every requested frame re-renders the whole transcript, so background sources (subagent streams, shell changes, context and cost updates) share one adaptive repaint budget: at most every 250 ms below 300 branch entries, 500 ms below 800, 1 s below 2,000, and only on visible state changes beyond that; a frame Pi draws on its own satisfies pending updates. User actions and state changes (a subagent or shell starting, settling or failing) still repaint at once. The open activity view repaints live updates every 100 ms, slowing to 500 ms in very large sessions. Context usage is cached: session start, tree navigation, compaction, model changes, renames and the end of a run refresh it at once, while message ends recompute it at most every 750 ms. `/jar perf` shows the counters. The sliding bar some terminals show in the tab while the agent works is Pi's own `OSC 9;4` progress (`terminal.showTerminalProgress` in Pi settings), not pi-jar.
|
|
268
269
|
|
|
269
270
|
## Settings
|
|
270
271
|
|
|
@@ -304,9 +305,11 @@ pi-jar/
|
|
|
304
305
|
│ ├── delegate.ts retained subagents, moderator controls and RPC lifecycle
|
|
305
306
|
│ ├── delegate-worktree.ts isolated Git worktrees, path guard and safe reconciliation
|
|
306
307
|
│ ├── async-process.ts cancellable async subprocess runner with deadlines and tree cleanup
|
|
307
|
-
│ ├── discussion.ts
|
|
308
|
+
│ ├── discussion.ts session-local discussion broker and tool
|
|
309
|
+
│ ├── discussion-hub.ts bounded in-memory discussion mailboxes
|
|
308
310
|
│ ├── democracy.ts exceptional scout ballots, strict majority and user tie-break
|
|
309
311
|
│ ├── activity-view.ts subagent/shell details view
|
|
312
|
+
│ ├── perf.ts long-session render budget, context sampling and /jar perf
|
|
310
313
|
│ ├── icons.ts unicode / nerd / ascii glyph sets
|
|
311
314
|
│ ├── attachments.ts image chips; prompt-search.ts is prompt history
|
|
312
315
|
│ ├── session-gallery.ts recent sessions for the welcome
|
|
@@ -0,0 +1,333 @@
|
|
|
1
|
+
# Discussion Broker Improvement Plan
|
|
2
|
+
|
|
3
|
+
This is the detailed design for item 6 of the broader [Long-Session Stability and Performance Plan](./LONG_SESSION_PERFORMANCE_PLAN.md).
|
|
4
|
+
|
|
5
|
+
## Status
|
|
6
|
+
|
|
7
|
+
Implemented in v0.1.9. This document preserves the design and acceptance criteria for the parent-owned in-memory broker and authenticated session-local IPC that replaced the file-backed paper. The “current” paper behavior and imperative implementation phases describe the pre-0.1.9 baseline and original proposal.
|
|
8
|
+
|
|
9
|
+
## Problem
|
|
10
|
+
|
|
11
|
+
`jar_discuss` currently coordinates independent Pi processes through a shared temporary JSON paper. Every mutation must:
|
|
12
|
+
|
|
13
|
+
1. acquire a filesystem lock directory,
|
|
14
|
+
2. read and parse the whole paper,
|
|
15
|
+
3. validate against that snapshot,
|
|
16
|
+
4. mutate the in-memory copy,
|
|
17
|
+
5. serialize and rewrite the whole paper,
|
|
18
|
+
6. atomically rename the replacement, and
|
|
19
|
+
7. release the lock.
|
|
20
|
+
|
|
21
|
+
The paper is bounded, so this is not an unbounded-data bug, but it is the wrong synchronization primitive for a parent process that already owns the subagent lifecycle. Concurrent agents can spend time retrying the same lock, stale-lock recovery adds failure modes, every write performs filesystem work, and the file cannot efficiently provide targeted delivery.
|
|
22
|
+
|
|
23
|
+
The desired model is agent coordination, not durable shared storage.
|
|
24
|
+
|
|
25
|
+
## Goals
|
|
26
|
+
|
|
27
|
+
- Remove lock contention and filesystem polling from normal cross-agent communication.
|
|
28
|
+
- Keep the moderator as the authority for agent identity, lifecycle and routing.
|
|
29
|
+
- Preserve the useful `jar_discuss ask|answer|list` interaction model where practical.
|
|
30
|
+
- Deliver only relevant unread communication to each agent.
|
|
31
|
+
- Keep discussion state strictly bounded in memory.
|
|
32
|
+
- Avoid automatically waking LLM agents for ordinary messages.
|
|
33
|
+
- Make pending communication visible to the moderator and activity UI.
|
|
34
|
+
- Make cleanup deterministic on session replacement and shutdown.
|
|
35
|
+
- Keep protocol and transport simple enough to test without running model calls.
|
|
36
|
+
|
|
37
|
+
## Non-goals
|
|
38
|
+
|
|
39
|
+
- A durable chat history.
|
|
40
|
+
- A general message queue.
|
|
41
|
+
- Direct child-to-child sockets.
|
|
42
|
+
- Automatic agent debates or unbounded LLM ping-pong.
|
|
43
|
+
- Persisting discussion across parent-process crashes.
|
|
44
|
+
- Replacing Pi RPC used for normal subagent lifecycle/control.
|
|
45
|
+
|
|
46
|
+
## Proposed architecture
|
|
47
|
+
|
|
48
|
+
Pi Jar's parent process owns a session-local `DiscussionHub`. Child agents never mutate shared storage directly.
|
|
49
|
+
|
|
50
|
+
```text
|
|
51
|
+
Pi Jar parent
|
|
52
|
+
┌─────────────────┐
|
|
53
|
+
│ DiscussionHub │
|
|
54
|
+
│ │
|
|
55
|
+
│ bounded state │
|
|
56
|
+
│ routing │
|
|
57
|
+
│ sequence IDs │
|
|
58
|
+
│ unread cursors │
|
|
59
|
+
└───────┬─────────┘
|
|
60
|
+
│
|
|
61
|
+
┌───────────┼───────────┐
|
|
62
|
+
│ │ │
|
|
63
|
+
scout-1 worker-2 reviewer-3
|
|
64
|
+
```
|
|
65
|
+
|
|
66
|
+
The hub is owned beside `DelegateRegistry`, because the registry already knows which retained agents exist and when they start, settle, pause, resume, stop or disappear.
|
|
67
|
+
|
|
68
|
+
Suggested ownership:
|
|
69
|
+
|
|
70
|
+
```ts
|
|
71
|
+
const subagents = new DelegateRegistry();
|
|
72
|
+
const discussions = new DiscussionHub();
|
|
73
|
+
```
|
|
74
|
+
|
|
75
|
+
Lifecycle integration:
|
|
76
|
+
|
|
77
|
+
```ts
|
|
78
|
+
discussions.register(record.key);
|
|
79
|
+
discussions.retire(record.key);
|
|
80
|
+
discussions.clear();
|
|
81
|
+
```
|
|
82
|
+
|
|
83
|
+
## Transport
|
|
84
|
+
|
|
85
|
+
Use a session-local IPC endpoint:
|
|
86
|
+
|
|
87
|
+
- Unix domain socket on macOS/Linux.
|
|
88
|
+
- Named pipe on Windows.
|
|
89
|
+
- Newline-delimited JSON request/response protocol.
|
|
90
|
+
- Children connect only when `jar_discuss` is invoked; no permanently open connection is required.
|
|
91
|
+
- No polling loop.
|
|
92
|
+
- No shared writable file.
|
|
93
|
+
- No lock file or lock directory.
|
|
94
|
+
|
|
95
|
+
The parent passes endpoint metadata to child processes through environment variables:
|
|
96
|
+
|
|
97
|
+
```text
|
|
98
|
+
PI_JAR_DISCUSSION_ENDPOINT=...
|
|
99
|
+
PI_JAR_DISCUSSION_TOKEN=...
|
|
100
|
+
PI_JAR_SUBAGENT_KEY=delegate-2-1
|
|
101
|
+
```
|
|
102
|
+
|
|
103
|
+
The child must not be allowed to choose an arbitrary sender identity. The parent authenticates the session token and maps the connection/request to a known subagent key.
|
|
104
|
+
|
|
105
|
+
On Unix, create the containing temporary directory with owner-only permissions. Treat the token as session-local capability data and never print it in tool output or logs.
|
|
106
|
+
|
|
107
|
+
## Message model
|
|
108
|
+
|
|
109
|
+
Use monotonic numeric sequence IDs owned by the parent.
|
|
110
|
+
|
|
111
|
+
```ts
|
|
112
|
+
interface DiscussionMessage {
|
|
113
|
+
id: number;
|
|
114
|
+
kind: "question" | "answer";
|
|
115
|
+
from: string;
|
|
116
|
+
to?: string;
|
|
117
|
+
replyTo?: number;
|
|
118
|
+
text: string;
|
|
119
|
+
createdAt: number;
|
|
120
|
+
}
|
|
121
|
+
```
|
|
122
|
+
|
|
123
|
+
The parent is the only component allowed to:
|
|
124
|
+
|
|
125
|
+
- allocate IDs,
|
|
126
|
+
- validate `from`,
|
|
127
|
+
- validate target agent keys,
|
|
128
|
+
- validate answer references,
|
|
129
|
+
- mutate retention state, and
|
|
130
|
+
- advance per-agent read cursors.
|
|
131
|
+
|
|
132
|
+
This gives deterministic ordering without a filesystem lock.
|
|
133
|
+
|
|
134
|
+
## Mailboxes instead of a shared transcript
|
|
135
|
+
|
|
136
|
+
Treat the discussion as bounded per-agent mailboxes over one shared message store.
|
|
137
|
+
|
|
138
|
+
Each agent keeps a logical `lastSeenId`. A normal unread query returns only messages after that cursor that are relevant to the caller:
|
|
139
|
+
|
|
140
|
+
- questions addressed to that agent,
|
|
141
|
+
- broadcast questions when broadcasts are supported,
|
|
142
|
+
- answers to questions created by that agent.
|
|
143
|
+
|
|
144
|
+
Do not make every agent ingest the full discussion history.
|
|
145
|
+
|
|
146
|
+
Tool behavior:
|
|
147
|
+
|
|
148
|
+
- `jar_discuss ask`: append one question and return its ID.
|
|
149
|
+
- `jar_discuss answer`: append one answer to a known question and return its ID.
|
|
150
|
+
- `jar_discuss list`: return unread relevant messages and advance the caller cursor.
|
|
151
|
+
- `jar_discuss thread <id>`: return one question and its bounded answers without advancing unrelated unread state.
|
|
152
|
+
- `jar_discuss pending`: compact unanswered/unread summary for moderator diagnostics.
|
|
153
|
+
|
|
154
|
+
The existing `since` compatibility behavior can remain during migration, but the normal path should be cursor-based.
|
|
155
|
+
|
|
156
|
+
## Delivery policy
|
|
157
|
+
|
|
158
|
+
Communication should be event-driven but not model-trigger-happy.
|
|
159
|
+
|
|
160
|
+
When a new message is routed:
|
|
161
|
+
|
|
162
|
+
1. update the target mailbox state,
|
|
163
|
+
2. update a cheap pending-count signal in the parent,
|
|
164
|
+
3. request only the necessary Pi Jar UI/status update, and
|
|
165
|
+
4. do not automatically wake an idle model.
|
|
166
|
+
|
|
167
|
+
At the target agent's next natural turn, Pi Jar may inject a tiny notice such as:
|
|
168
|
+
|
|
169
|
+
```text
|
|
170
|
+
You have 1 unread discussion message. Use jar_discuss list when relevant.
|
|
171
|
+
```
|
|
172
|
+
|
|
173
|
+
The moderator can explicitly resume/steer a retained agent when a question is urgent. Ordinary agent-generated messages must not be able to create an automatic wake/answer/wake loop.
|
|
174
|
+
|
|
175
|
+
## Retention
|
|
176
|
+
|
|
177
|
+
Discussion state remains bounded.
|
|
178
|
+
|
|
179
|
+
Initial limits:
|
|
180
|
+
|
|
181
|
+
- at most 128 messages,
|
|
182
|
+
- at most 1,600 characters per message,
|
|
183
|
+
- at most 128 KiB total encoded message text/metadata,
|
|
184
|
+
- at most a small fixed mailbox/cursor record per registered agent.
|
|
185
|
+
|
|
186
|
+
Eviction priority:
|
|
187
|
+
|
|
188
|
+
1. answered question/answer groups already acknowledged by relevant agents,
|
|
189
|
+
2. acknowledged broadcast messages,
|
|
190
|
+
3. oldest acknowledged messages,
|
|
191
|
+
4. never silently evict an unanswered targeted question while disposable acknowledged entries exist.
|
|
192
|
+
|
|
193
|
+
If the hard bound cannot be maintained without removing an unresolved question, surface a compact capacity error and require progress rather than growing memory indefinitely.
|
|
194
|
+
|
|
195
|
+
## Context discipline
|
|
196
|
+
|
|
197
|
+
The broker stores coordination state. The model receives only the slice it needs.
|
|
198
|
+
|
|
199
|
+
Normal tool results should not echo:
|
|
200
|
+
|
|
201
|
+
- the caller's own submitted text,
|
|
202
|
+
- old acknowledged messages,
|
|
203
|
+
- unrelated agent chatter,
|
|
204
|
+
- the full mailbox,
|
|
205
|
+
- the full discussion graph.
|
|
206
|
+
|
|
207
|
+
This protects both response latency and model context in long sessions.
|
|
208
|
+
|
|
209
|
+
## Failure behavior
|
|
210
|
+
|
|
211
|
+
The broker is ephemeral by design.
|
|
212
|
+
|
|
213
|
+
If the parent process exits, discussion state is lost. That is acceptable because:
|
|
214
|
+
|
|
215
|
+
- the parent owns the child processes,
|
|
216
|
+
- discussion is coordination state rather than user-authored durable data,
|
|
217
|
+
- durable task/plan/session artifacts already live elsewhere.
|
|
218
|
+
|
|
219
|
+
Do not add per-message snapshots merely to reconstruct transient chatter after a crash. If later evidence shows recovery is valuable, add an optional atomic snapshot at coarse lifecycle boundaries, not a lock-based primary transport.
|
|
220
|
+
|
|
221
|
+
If the IPC endpoint is unavailable, `jar_discuss` should return a clear broker-unavailable error. Do not silently fall back to the old shared-file implementation, because maintaining two synchronization models would preserve the complexity this change is intended to remove.
|
|
222
|
+
|
|
223
|
+
## Observability
|
|
224
|
+
|
|
225
|
+
Expose lightweight broker information to Pi Jar diagnostics/activity state:
|
|
226
|
+
|
|
227
|
+
- registered agents,
|
|
228
|
+
- unread count per agent,
|
|
229
|
+
- unanswered question count,
|
|
230
|
+
- retained message count/bytes,
|
|
231
|
+
- oldest/newest sequence ID,
|
|
232
|
+
- IPC endpoint status,
|
|
233
|
+
- request/error counters.
|
|
234
|
+
|
|
235
|
+
Do not expose message bodies in generic telemetry.
|
|
236
|
+
|
|
237
|
+
## Implementation phases
|
|
238
|
+
|
|
239
|
+
### Phase 1: DiscussionHub
|
|
240
|
+
|
|
241
|
+
Add a pure in-memory `DiscussionHub` with no sockets and unit-test:
|
|
242
|
+
|
|
243
|
+
- registration/retirement,
|
|
244
|
+
- monotonic IDs,
|
|
245
|
+
- ask/answer validation,
|
|
246
|
+
- targeted routing,
|
|
247
|
+
- cursor semantics,
|
|
248
|
+
- thread reads,
|
|
249
|
+
- retention/eviction,
|
|
250
|
+
- cleanup.
|
|
251
|
+
|
|
252
|
+
### Phase 2: local IPC
|
|
253
|
+
|
|
254
|
+
Add the local server/client transport and authenticate children using session-local capability data.
|
|
255
|
+
|
|
256
|
+
Test:
|
|
257
|
+
|
|
258
|
+
- concurrent asks receive unique ordered IDs,
|
|
259
|
+
- concurrent answers do not require retries,
|
|
260
|
+
- invalid sender/target/reply IDs are rejected,
|
|
261
|
+
- malformed requests cannot crash the parent,
|
|
262
|
+
- endpoint cleanup happens on shutdown.
|
|
263
|
+
|
|
264
|
+
### Phase 3: jar_discuss adapter
|
|
265
|
+
|
|
266
|
+
Keep the public tool concise while switching its storage implementation to the broker.
|
|
267
|
+
|
|
268
|
+
Preserve useful response limits from the current implementation, but remove:
|
|
269
|
+
|
|
270
|
+
- `paper.json`,
|
|
271
|
+
- `paper.json.lock/`,
|
|
272
|
+
- lock retries,
|
|
273
|
+
- stale lock recovery,
|
|
274
|
+
- whole-paper reads and rewrites.
|
|
275
|
+
|
|
276
|
+
### Phase 4: DelegateRegistry/activity integration
|
|
277
|
+
|
|
278
|
+
Show pending counts in moderator/activity state and add a small unread notice at natural agent boundaries.
|
|
279
|
+
|
|
280
|
+
Do not auto-resume agents for normal messages.
|
|
281
|
+
|
|
282
|
+
### Phase 5: delete compatibility code
|
|
283
|
+
|
|
284
|
+
After the broker tests cover existing semantics:
|
|
285
|
+
|
|
286
|
+
- remove `createDiscussionPaper`,
|
|
287
|
+
- remove `disposeDiscussionPaper`,
|
|
288
|
+
- remove file-path environment variables,
|
|
289
|
+
- remove filesystem discussion tests,
|
|
290
|
+
- remove lock-specific code and stale-lock handling.
|
|
291
|
+
|
|
292
|
+
## Acceptance criteria
|
|
293
|
+
|
|
294
|
+
The implementation is complete when:
|
|
295
|
+
|
|
296
|
+
- two or more child agents can ask/answer concurrently with no filesystem lock,
|
|
297
|
+
- discussion operations perform no shared-paper read/write in the steady state,
|
|
298
|
+
- no polling timer is required for message delivery,
|
|
299
|
+
- ordering is deterministic,
|
|
300
|
+
- each agent sees only relevant unread messages by default,
|
|
301
|
+
- memory remains bounded under a stress test,
|
|
302
|
+
- idle agents are not automatically woken by normal discussion traffic,
|
|
303
|
+
- session replacement/shutdown removes IPC resources and in-memory state,
|
|
304
|
+
- existing subagent pause/resume/stop behavior remains unchanged,
|
|
305
|
+
- tests cover concurrency and lifecycle cleanup.
|
|
306
|
+
|
|
307
|
+
## Performance validation
|
|
308
|
+
|
|
309
|
+
Add a synthetic test/benchmark that compares the current file-backed design with the broker for concurrent local operations. The target is not an arbitrary microbenchmark trophy; it is removal of contention and variance.
|
|
310
|
+
|
|
311
|
+
Measure:
|
|
312
|
+
|
|
313
|
+
- median and p95 ask/answer latency,
|
|
314
|
+
- number of filesystem operations,
|
|
315
|
+
- number of retry waits,
|
|
316
|
+
- parent CPU time,
|
|
317
|
+
- retained heap after a fixed message workload.
|
|
318
|
+
|
|
319
|
+
Expected steady-state broker behavior is zero discussion filesystem operations and zero lock retries.
|
|
320
|
+
|
|
321
|
+
## Related cleanup: legacy footer settings
|
|
322
|
+
|
|
323
|
+
Pi Jar previously supported `$AGENT_DIR/pi-jar-footer.json` and migrated it into `pi-jar-settings.json`.
|
|
324
|
+
|
|
325
|
+
That compatibility path is retired alongside this plan PR:
|
|
326
|
+
|
|
327
|
+
- `pi-jar-settings.json` is the sole visual/footer settings source,
|
|
328
|
+
- Pi Jar no longer reads, writes or migrates `pi-jar-footer.json`,
|
|
329
|
+
- an existing legacy file is ignored and left untouched,
|
|
330
|
+
- footer field definitions remain reusable code, but have no independent persistence layer,
|
|
331
|
+
- regression tests verify the legacy file cannot influence current settings.
|
|
332
|
+
|
|
333
|
+
This keeps configuration ownership singular before more parent-owned coordination state is introduced.
|
package/docs/INTEGRATIONS.md
CHANGED
|
@@ -39,7 +39,7 @@ ctx.ui.setStatus("pi-jar.quota.openai-codex", JSON.stringify({
|
|
|
39
39
|
- `used` is a percentage from 0 to 100. Either window may be omitted, and each can carry an optional `resetsAt` (epoch milliseconds).
|
|
40
40
|
- `expiresAt` is required and may be at most five minutes ahead. A valid published status always wins.
|
|
41
41
|
- `/jar quota on` (the default each session) lets pi-jar resolve the current Anthropic or OpenAI Codex OAuth credentials through Pi's model registry and make a **read-only** request to the provider's quota endpoint when nothing is published.
|
|
42
|
-
- Requests have a 5 s timeout
|
|
42
|
+
- Requests have a 5 s timeout; successful results are cached for 5 minutes, while consecutive failures back off for 5, 10, 20, then 30 minutes. `/jar quota off` cancels pending requests and clears the cache. Renders only read cached values.
|
|
43
43
|
- These provider endpoints are not stable public APIs.
|
|
44
44
|
|
|
45
45
|
## Session entries owned by pi-jar
|