sessionpipe 0.11.0 → 0.13.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 +48 -6
- package/dist/ask.d.ts +40 -0
- package/dist/ask.d.ts.map +1 -0
- package/dist/cli.d.ts.map +1 -1
- package/dist/cli.js +3193 -1220
- package/dist/cli.js.map +4 -4
- package/dist/control/channel.d.ts +43 -0
- package/dist/control/channel.d.ts.map +1 -0
- package/dist/control/cli.d.ts +13 -1
- package/dist/control/cli.d.ts.map +1 -1
- package/dist/control/daemon.d.ts +189 -2
- package/dist/control/daemon.d.ts.map +1 -1
- package/dist/control/inbox.d.ts +119 -0
- package/dist/control/inbox.d.ts.map +1 -0
- package/dist/control/local.d.ts +69 -4
- package/dist/control/local.d.ts.map +1 -1
- package/dist/control/pair.d.ts.map +1 -1
- package/dist/control/reply.d.ts +25 -1
- package/dist/control/reply.d.ts.map +1 -1
- package/dist/control/route.d.ts +50 -2
- package/dist/control/route.d.ts.map +1 -1
- package/dist/control/sdk.d.ts.map +1 -1
- package/dist/control/store.d.ts +49 -4
- package/dist/control/store.d.ts.map +1 -1
- package/dist/help.d.ts.map +1 -1
- package/dist/hook.d.ts.map +1 -1
- package/dist/hook.js +15 -5
- package/dist/hook.js.map +2 -2
- package/dist/index.js +865 -155
- package/dist/index.js.map +4 -4
- package/dist/run.d.ts +1 -0
- package/dist/run.d.ts.map +1 -1
- package/dist/worker.js +874 -164
- package/dist/worker.js.map +4 -4
- package/package.json +1 -1
package/dist/control/local.d.ts
CHANGED
|
@@ -1,15 +1,20 @@
|
|
|
1
1
|
export type LocalRequest =
|
|
2
|
-
/** A waiter parks until a message for its session arrives.
|
|
2
|
+
/** A waiter parks until a message for its session arrives. `channel`: the waiter is
|
|
3
|
+
* `sessionpipe channel`, which pushes the message into the session rather than handing
|
|
4
|
+
* it to a turn that asked for it (CONTROL.md §8). */
|
|
3
5
|
{
|
|
4
6
|
op: "wait";
|
|
5
7
|
session: string;
|
|
6
8
|
pid?: number;
|
|
9
|
+
channel?: boolean;
|
|
7
10
|
}
|
|
8
|
-
/** A Stop hook asks for a queued message (turn mode).
|
|
11
|
+
/** A Stop hook asks for a queued message (turn mode). `mode` is the session's own
|
|
12
|
+
* permission mode, as its payload reports it (CONTROL.md §6, The session's mode). */
|
|
9
13
|
| {
|
|
10
14
|
op: "stop";
|
|
11
15
|
session: string;
|
|
12
16
|
active: boolean;
|
|
17
|
+
mode?: string;
|
|
13
18
|
}
|
|
14
19
|
/** A PermissionRequest hook parks until a verified answer, or until it's released. */
|
|
15
20
|
| {
|
|
@@ -18,13 +23,15 @@ export type LocalRequest =
|
|
|
18
23
|
attention: string;
|
|
19
24
|
tool?: string;
|
|
20
25
|
}
|
|
21
|
-
/** The worker reports a hook event: turn state
|
|
26
|
+
/** The worker reports a hook event: turn state, attention closure, and the session's
|
|
27
|
+
* own permission mode where its payload named one. */
|
|
22
28
|
| {
|
|
23
29
|
op: "event";
|
|
24
30
|
session: string;
|
|
25
31
|
event: string;
|
|
26
32
|
transcript?: string;
|
|
27
33
|
cwd?: string;
|
|
34
|
+
mode?: string;
|
|
28
35
|
}
|
|
29
36
|
/** `sessionpipe control status`. */
|
|
30
37
|
| {
|
|
@@ -44,8 +51,30 @@ export type LocalRequest =
|
|
|
44
51
|
account?: string;
|
|
45
52
|
order?: string[];
|
|
46
53
|
code?: string;
|
|
47
|
-
}
|
|
54
|
+
}
|
|
55
|
+
/** `sessionpipe ask` (CONTROL.md §13): a session here hands a task to another agent on
|
|
56
|
+
* this machine and gets the answer back on this connection. */
|
|
57
|
+
| AskRequest;
|
|
48
58
|
export type PoolOp = "status" | "on" | "off" | "enable" | "disable" | "remove" | "order" | "refresh" | "login.begin" | "login.complete" | "import";
|
|
59
|
+
export interface AskRequest {
|
|
60
|
+
op: "ask";
|
|
61
|
+
/** `<harness>:<id>` of the asking session, when known: the events go on it. */
|
|
62
|
+
from?: string;
|
|
63
|
+
/** The agent to ask. */
|
|
64
|
+
harness: string;
|
|
65
|
+
/** An existing `<harness>:<id>` to continue instead of a new session. */
|
|
66
|
+
session?: string;
|
|
67
|
+
/** 1–20 000 characters, not all whitespace. */
|
|
68
|
+
text: string;
|
|
69
|
+
/** Absolute; the caller's folder by default. */
|
|
70
|
+
cwd: string;
|
|
71
|
+
/** Every ancestor ref, outermost first (from env SESSIONPIPE_ASK_CHAIN). */
|
|
72
|
+
chain: string[];
|
|
73
|
+
/** Narrower than the machine's mode, never wider. */
|
|
74
|
+
permission?: "read" | "safe";
|
|
75
|
+
model?: string;
|
|
76
|
+
pid?: number;
|
|
77
|
+
}
|
|
49
78
|
export type LocalReply = {
|
|
50
79
|
op: "message";
|
|
51
80
|
text: string;
|
|
@@ -82,10 +111,46 @@ export type LocalReply = {
|
|
|
82
111
|
status?: unknown;
|
|
83
112
|
/** `import`: what was added and what was left out (control/pool.ts Imported). */
|
|
84
113
|
imported?: unknown;
|
|
114
|
+
}
|
|
115
|
+
/** The run began; `session` once it is known. */
|
|
116
|
+
| {
|
|
117
|
+
op: "asked";
|
|
118
|
+
ask_id: string;
|
|
119
|
+
session?: string;
|
|
120
|
+
}
|
|
121
|
+
/** The answer so far, whole, with a rising seq. */
|
|
122
|
+
| {
|
|
123
|
+
op: "progress";
|
|
124
|
+
text: string;
|
|
125
|
+
seq: number;
|
|
126
|
+
} | {
|
|
127
|
+
op: "answer";
|
|
128
|
+
ask_id: string;
|
|
129
|
+
session: string;
|
|
130
|
+
text: string;
|
|
131
|
+
ms: number;
|
|
132
|
+
}
|
|
133
|
+
/** ask_off · harness · folder · depth · loop · start_limit · bad_fields */
|
|
134
|
+
| {
|
|
135
|
+
op: "refused";
|
|
136
|
+
code: string;
|
|
137
|
+
detail: string;
|
|
138
|
+
} | {
|
|
139
|
+
op: "failed";
|
|
140
|
+
detail: string;
|
|
85
141
|
};
|
|
142
|
+
/** The replies that end an ask. */
|
|
143
|
+
export type AskEnd = Extract<LocalReply, {
|
|
144
|
+
op: "answer" | "refused" | "failed";
|
|
145
|
+
}>;
|
|
86
146
|
/** Where the daemon listens. `SESSIONPIPE_SOCKET` overrides (tests). */
|
|
87
147
|
export declare function socketPath(state: string, env?: NodeJS.ProcessEnv): string;
|
|
88
148
|
/** One request, one reply. `timeoutMs` bounds the whole exchange; null on any
|
|
89
149
|
* failure (no daemon, a timeout, a garbled reply) — callers treat that as "none". */
|
|
90
150
|
export declare function ask(sock: string, req: LocalRequest, timeoutMs: number): Promise<LocalReply | null>;
|
|
151
|
+
/** One request, several replies on the same connection (an ask): `onReply` sees each one
|
|
152
|
+
* in order, the promise settles with the one that ends the exchange. `timeoutMs` bounds
|
|
153
|
+
* the whole exchange; null when it ends without an end — no daemon, a timeout, a garbled
|
|
154
|
+
* line, a connection that closed mid-run. */
|
|
155
|
+
export declare function askMany(sock: string, req: LocalRequest, onReply: (r: LocalReply) => void, timeoutMs: number): Promise<AskEnd | null>;
|
|
91
156
|
//# sourceMappingURL=local.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"local.d.ts","sourceRoot":"","sources":["../../src/control/local.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"local.d.ts","sourceRoot":"","sources":["../../src/control/local.ts"],"names":[],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"pair.d.ts","sourceRoot":"","sources":["../../src/control/pair.ts"],"names":[],"mappings":"AASA,OAAO,EAKL,KAAK,cAAc,EAEpB,MAAM,mBAAmB,CAAC;AAE3B,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,2BAA2B,CAAC;AACtD,OAAO,KAAK,IAAI,MAAM,2BAA2B,CAAC;AAClD,OAAO,
|
|
1
|
+
{"version":3,"file":"pair.d.ts","sourceRoot":"","sources":["../../src/control/pair.ts"],"names":[],"mappings":"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"}
|
package/dist/control/reply.d.ts
CHANGED
|
@@ -1,8 +1,32 @@
|
|
|
1
1
|
/** The transcript's size now: where its answer will start. */
|
|
2
2
|
export declare function transcriptEnd(file: string): number;
|
|
3
|
+
/** Who asked for the first turn the transcript gained after a delivery: `ours` — the
|
|
4
|
+
* message this daemon handed the session in place, recognised by its own mark in the row
|
|
5
|
+
* the session wrote for it: a peer row for the inbox (the mark is in the text it was
|
|
6
|
+
* written with), a channel row for `sessionpipe channel` (the tag names the message's
|
|
7
|
+
* id); `other` — any other turn, the person typing in the same second above all, or
|
|
8
|
+
* another local process's message. Null while nothing has been written yet.
|
|
9
|
+
*
|
|
10
|
+
* This is the second half of a delivery's proof. The hook's own `UserPromptSubmit` says
|
|
11
|
+
* a turn began and carries no text, so on its own it cannot tell this message's turn
|
|
12
|
+
* from the person's: confirming on it alone acked a delivery that was really a hold,
|
|
13
|
+
* and then sent the answer to THEIR prompt back to the receiver as the answer to this
|
|
14
|
+
* message. */
|
|
15
|
+
export declare function firstAsk(file: string, from: number, mark: string): "ours" | "other" | null;
|
|
16
|
+
/** The permission mode the rows written after `from` record — what the turn a relaunch
|
|
17
|
+
* just ran ACTUALLY ran in, rather than what was asked for (spec/CONTROL.md §6
|
|
18
|
+
* `prompt`). The last word wins; null when no row says. */
|
|
19
|
+
export declare function ranInMode(file: string, from: number): string | null;
|
|
3
20
|
/** Claude Code records after the delivery → the turn's answer once the turn ended
|
|
4
21
|
* (an assistant record with `stop_reason: "end_turn"`), else null. The answer is the
|
|
5
|
-
* turn's assistant text, in order; sidechains (subagents) are not the session's words.
|
|
22
|
+
* turn's assistant text, in order; sidechains (subagents) are not the session's words.
|
|
23
|
+
*
|
|
24
|
+
* One model message can be written as several records, and every one carries the
|
|
25
|
+
* message's stop reason: when the model thinks before it answers, Claude Code 2.1.314
|
|
26
|
+
* writes a thinking record and then the text, both `end_turn`. A record with no text is
|
|
27
|
+
* not where the answer ends — taking it for the end acked every such answer with no
|
|
28
|
+
* reply. The turn is over at the `end_turn` record that has text, or at whatever follows
|
|
29
|
+
* a textless one (a turn that ended with nothing said). */
|
|
6
30
|
export declare function answerIn(lines: string[]): {
|
|
7
31
|
done: boolean;
|
|
8
32
|
text: string;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"reply.d.ts","sourceRoot":"","sources":["../../src/control/reply.ts"],"names":[],"mappings":"AASA,8DAA8D;AAC9D,wBAAgB,aAAa,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAMlD;AAED;;
|
|
1
|
+
{"version":3,"file":"reply.d.ts","sourceRoot":"","sources":["../../src/control/reply.ts"],"names":[],"mappings":"AASA,8DAA8D;AAC9D,wBAAgB,aAAa,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAMlD;AAED;;;;;;;;;;;eAWe;AACf,wBAAgB,QAAQ,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,GAAG,MAAM,GAAG,OAAO,GAAG,IAAI,CAmC1F;AAED;;4DAE4D;AAC5D,wBAAgB,SAAS,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAyBnE;AAUD;;;;;;;;;4DAS4D;AAC5D,wBAAgB,QAAQ,CAAC,KAAK,EAAE,MAAM,EAAE,GAAG;IAAE,IAAI,EAAE,OAAO,CAAC;IAAC,IAAI,EAAE,MAAM,CAAA;CAAE,CAgCzE;AAED;;iFAEiF;AACjF,wBAAsB,WAAW,CAC/B,IAAI,EAAE,MAAM,EACZ,IAAI,EAAE,MAAM,EACZ,CAAC,EAAE;IACD,SAAS,EAAE,MAAM,CAAC;IAClB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,GAAG,CAAC,EAAE,MAAM,MAAM,CAAC;IACnB,KAAK,CAAC,EAAE,CAAC,EAAE,EAAE,MAAM,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;IACtC,yEAAyE;IACzE,MAAM,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,CAAC;CACjC,GACA,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC,CA8BxB"}
|
package/dist/control/route.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import type { ControlKind } from "@sessionpipe/core/control";
|
|
2
|
-
export type DeliveryMode = "sdk" | "waiter" | "turn" | "api" | "resume" | "fork";
|
|
2
|
+
export type DeliveryMode = "sdk" | "waiter" | "turn" | "inbox" | "api" | "resume" | "fork";
|
|
3
3
|
export interface SessionView {
|
|
4
4
|
harness: string;
|
|
5
5
|
/** The daemon holds this session through the Agent SDK right now. */
|
|
@@ -8,12 +8,18 @@ export interface SessionView {
|
|
|
8
8
|
waiter: boolean;
|
|
9
9
|
/** Between a turn's start and its Stop (the Stop hook will ask). */
|
|
10
10
|
midTurn: boolean;
|
|
11
|
+
/** A live, idle, vetted session whose own permission class is this machine's: its own
|
|
12
|
+
* local inbox takes the message (§6.3). */
|
|
13
|
+
inbox: boolean;
|
|
11
14
|
/** A live process holds the session (registry entry or a fresh transcript write). */
|
|
12
15
|
live: boolean;
|
|
13
16
|
/** The transcript exists on this machine (Codex, Antigravity: the session was placed). */
|
|
14
17
|
known: boolean;
|
|
15
18
|
/** This Claude Code can copy a session (`--fork-session`); no other harness can. */
|
|
16
19
|
canFork: boolean;
|
|
20
|
+
/** It already has a copy, which is where its messages go: a copy is a leaf and is
|
|
21
|
+
* never itself copied (§6 `prompt`). */
|
|
22
|
+
copied: boolean;
|
|
17
23
|
/** The harness has an input API (OpenCode, Codex app-server) — none is wired yet. */
|
|
18
24
|
api: boolean;
|
|
19
25
|
}
|
|
@@ -27,8 +33,18 @@ export type Route = {
|
|
|
27
33
|
/** The harnesses the daemon can run a turn of by itself: resume an idle session, start a
|
|
28
34
|
* new one (`claude -p`, `codex exec`, `agy -p`, or any ACP agent as its client). */
|
|
29
35
|
export declare const HEADLESS: Set<string>;
|
|
36
|
+
/** The ladder in one place, so its order is a fact and not a shape of the code: the
|
|
37
|
+
* first rung that fits wins (spec/CONTROL.md §6). The in-place rungs come first,
|
|
38
|
+
* because the session answers in the person's own window or thread, in its own
|
|
39
|
+
* permission mode, with nothing started and nothing replayed. Among those, the ones
|
|
40
|
+
* the session itself opened — a parked waiter, a running turn — come before the one
|
|
41
|
+
* where the daemon writes to it unasked. */
|
|
42
|
+
export declare const DELIVERY_LADDER: readonly ["sdk", "waiter", "turn", "inbox", "api", "resume", "fork"];
|
|
43
|
+
/** Does `a` sit above `b` on the ladder? The rungs above `inbox` are all free to test,
|
|
44
|
+
* so a message that takes one of them never pays for the inbox's own look. */
|
|
45
|
+
export declare const earlier: (a: DeliveryMode, b: DeliveryMode) => boolean;
|
|
30
46
|
/** Where a prompt (or a start) goes. Never two writers on one transcript: a live
|
|
31
|
-
* session gets a fork, never a resume. */
|
|
47
|
+
* session gets an in-place lane or a fork, never a resume. */
|
|
32
48
|
export declare function routePrompt(s: SessionView): Route;
|
|
33
49
|
/** How each kind is delivered, before the session's state is looked at. */
|
|
34
50
|
export declare function kindPath(kind: ControlKind, harness: string): "prompt" | "permission" | "cancel" | "start" | "pool" | {
|
|
@@ -41,10 +57,42 @@ export declare function kindPath(kind: ControlKind, harness: string): "prompt" |
|
|
|
41
57
|
* command to reply with (a real session tried \`sessionpipe send\`, 2026-10-01). */
|
|
42
58
|
export declare const IN_PLACE_ANSWER = "Answer it right here, as you would answer the person at the keyboard: your reply is sent back to them automatically. Don't run a command or call a tool just to send it.";
|
|
43
59
|
export declare function frame(text: string, receiver: string): string;
|
|
60
|
+
/** frame() undone: the person's words, and the host they were sent from. A channel shows
|
|
61
|
+
* the words as the message and says where they came from beside it. Text that frame()
|
|
62
|
+
* didn't make comes back whole, from nowhere. */
|
|
63
|
+
export declare function unframe(text: string): {
|
|
64
|
+
text: string;
|
|
65
|
+
via: string | null;
|
|
66
|
+
};
|
|
67
|
+
/** What the daemon looks for in the row the session writes for the turn this message
|
|
68
|
+
* caused (§6.3): a turn is only proof of delivery when it is THIS message's turn. */
|
|
69
|
+
export declare const inboxMark: (id: string) => string;
|
|
70
|
+
/** The same for a channel's message (§8): `sessionpipe channel` names the message's id on
|
|
71
|
+
* its `<channel>` tag, and Claude Code writes the tag into the row of the turn it causes. */
|
|
72
|
+
export declare const channelMark: (id: string) => string;
|
|
73
|
+
/** The framed text for the `inbox` lane: `frame()` with that mark in it, since the
|
|
74
|
+
* message becomes a prompt of the session's own and the daemon has to recognise it
|
|
75
|
+
* again in the transcript. */
|
|
76
|
+
export declare function frameInbox(text: string, receiver: string, id: string): string;
|
|
77
|
+
/** Said with a message a copy of a session is answering, so the model knows the person
|
|
78
|
+
* is not reading this conversation: a copy is not the thread they are looking at. */
|
|
79
|
+
export declare const COPY_NOTE = "You are a copy of that session, started to answer this message: the conversation above is a replay, the original session is somewhere else, and nothing you do here appears in it. Answer the message and stop; don't carry on the original's work.";
|
|
44
80
|
/** A new session's first message: the person's words first, where they come from after.
|
|
45
81
|
* Claude Code names a session from the start of its first message, so a header in front
|
|
46
82
|
* named every started session "Message via spacesheep.dev (sessionpipe control, s…"
|
|
47
83
|
* (2026-10-02). In a new session there is no one else's conversation to tell it apart
|
|
48
84
|
* from, so the source line can follow the ask. */
|
|
49
85
|
export declare function frameStart(text: string, receiver: string): string;
|
|
86
|
+
/** What a session another session asked receives (CONTROL.md §13), new or not: the task
|
|
87
|
+
* first, as frameStart puts it, then who asked and that the answer travels by itself. */
|
|
88
|
+
export declare function frameAsk(text: string, from: string | undefined): string;
|
|
89
|
+
/** A handoff's answer as it lands in `reply_to` (CONTROL.md §6): who answered, in the
|
|
90
|
+
* short form the receivers label sessions by, and which receiver the person asked through. */
|
|
91
|
+
export declare function frameHandoff(from: {
|
|
92
|
+
harness: string;
|
|
93
|
+
id: string;
|
|
94
|
+
}, receiver: string, reply: string): string;
|
|
95
|
+
/** The receiver's own host, for a line a person reads; the whole string when it is not
|
|
96
|
+
* a URL. */
|
|
97
|
+
export declare function hostOf(receiver: string): string;
|
|
50
98
|
//# sourceMappingURL=route.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"route.d.ts","sourceRoot":"","sources":["../../src/control/route.ts"],"names":[],"mappings":"AAIA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,2BAA2B,CAAC;AAE7D,MAAM,MAAM,YAAY,GAAG,KAAK,GAAG,QAAQ,GAAG,MAAM,GAAG,KAAK,GAAG,QAAQ,GAAG,MAAM,CAAC;
|
|
1
|
+
{"version":3,"file":"route.d.ts","sourceRoot":"","sources":["../../src/control/route.ts"],"names":[],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"sdk.d.ts","sourceRoot":"","sources":["../../src/control/sdk.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"sdk.d.ts","sourceRoot":"","sources":["../../src/control/sdk.ts"],"names":[],"mappings":"AAaA,OAAO,KAAK,EAAE,OAAO,EAAc,MAAM,aAAa,CAAC;AAmBvD,wBAAsB,OAAO,CAAC,CAAC,EAAE;IAC/B,SAAS,EAAE,MAAM,GAAG,IAAI,CAAC;IACzB,GAAG,CAAC,EAAE,MAAM,CAAC,UAAU,CAAC;IACxB,GAAG,EAAE,CAAC,CAAC,EAAE,MAAM,KAAK,IAAI,CAAC;CAC1B,GAAG,OAAO,CAAC,OAAO,GAAG,IAAI,CAAC,CAkG1B"}
|
package/dist/control/store.d.ts
CHANGED
|
@@ -31,13 +31,19 @@ export interface ControlConfig {
|
|
|
31
31
|
receivers: PairedReceiver[];
|
|
32
32
|
/** Caps this machine keeps whatever a receiver sends (defaults in daemon.ts,
|
|
33
33
|
* LIMITS): new sessions running at once and per hour, headless Claude Code runs
|
|
34
|
-
* at once. */
|
|
34
|
+
* at once, copies of sessions made in a day. */
|
|
35
35
|
limits?: {
|
|
36
36
|
start_concurrent?: number;
|
|
37
37
|
start_per_hour?: number;
|
|
38
38
|
headless?: number;
|
|
39
|
+
copies_per_day?: number;
|
|
39
40
|
};
|
|
41
|
+
/** Whether a session here may ask another agent through the daemon (CONTROL.md §13).
|
|
42
|
+
* On unless `sessionpipe ask off` set it false; the daemon says which in its hello. */
|
|
43
|
+
ask?: boolean;
|
|
40
44
|
}
|
|
45
|
+
/** `ask` as the config means it: on when unsaid. */
|
|
46
|
+
export declare const askOn: (c: Pick<ControlConfig, "ask">) => boolean;
|
|
41
47
|
export declare const controlFile: (env?: NodeJS.ProcessEnv) => string;
|
|
42
48
|
export declare const controlState: (env?: NodeJS.ProcessEnv) => string;
|
|
43
49
|
export declare function writePrivate(file: string, value: unknown): void;
|
|
@@ -83,6 +89,10 @@ export interface Ack {
|
|
|
83
89
|
reply?: string;
|
|
84
90
|
/** A start's taken and delivered: what it ran with (CONTROL.md §6, Options). */
|
|
85
91
|
applied?: StartOptions;
|
|
92
|
+
/** This answer came from a COPY of the session the command named, not from it: the
|
|
93
|
+
* person's words went somewhere other than the conversation they were looking at,
|
|
94
|
+
* and they are owed that fact (CONTROL.md §6 `fork`). */
|
|
95
|
+
copy_of?: string;
|
|
86
96
|
}
|
|
87
97
|
/** What a session the daemon started runs with: its level and, when one was asked for,
|
|
88
98
|
* its model. Recorded at the start; every later run of the session reads it. */
|
|
@@ -103,13 +113,48 @@ export declare class AckOutbox {
|
|
|
103
113
|
add(a: Ack): void;
|
|
104
114
|
keep(left: Ack[]): void;
|
|
105
115
|
}
|
|
116
|
+
/** How long a message written into a live session's own inbox keeps that lane shut for
|
|
117
|
+
* it (CONTROL.md §6.3): Claude Code holds an unmatched message that long before
|
|
118
|
+
* dropping it, and a hold can be released, so a second write inside the window would
|
|
119
|
+
* mean the person's words arriving twice. It outlives the daemon that wrote it, so a
|
|
120
|
+
* restart — an update installs one — cannot turn a resend into a second frame. */
|
|
121
|
+
export declare const HOLD_TTL_MS = 300000;
|
|
122
|
+
/** A copy the daemon made because it could not reach the original (CONTROL.md §6
|
|
123
|
+
* `fork`), and what the person is owed about it: which session it is, when it was made
|
|
124
|
+
* and why there is one at all. Daemons up to 0.10.0 wrote the id alone. */
|
|
125
|
+
export interface Copy {
|
|
126
|
+
id: string;
|
|
127
|
+
at: string;
|
|
128
|
+
/** In the machine's own words, for the ack and the board: why a copy, not the session. */
|
|
129
|
+
reason: string;
|
|
130
|
+
}
|
|
131
|
+
/** A message written into a session's own inbox that it has not taken yet
|
|
132
|
+
* (CONTROL.md §6.3), by the session it was written to. */
|
|
133
|
+
export interface Parked {
|
|
134
|
+
/** When it was written, ISO-8601. Older than HOLD_TTL_MS is no longer a hold. */
|
|
135
|
+
at: string;
|
|
136
|
+
/** The message's id, so a log or a later ack can name the one that is waiting. */
|
|
137
|
+
id: string;
|
|
138
|
+
}
|
|
106
139
|
export interface DaemonState {
|
|
107
|
-
/** Original session → the
|
|
108
|
-
copies: Record<string,
|
|
140
|
+
/** Original session → the copy its messages go to. */
|
|
141
|
+
copies: Record<string, Copy>;
|
|
109
142
|
/** Claude Code sessions the daemon started → what they run with (Codex and
|
|
110
143
|
* Antigravity keep theirs in the alias entry, aliases.ts). */
|
|
111
144
|
started: Record<string, StartOptions>;
|
|
145
|
+
/** Session ref → the permission mode its own hooks last reported (CONTROL.md §6, The
|
|
146
|
+
* session's mode). The daemon's own record, in its own state: no Claude Code home is
|
|
147
|
+
* written to. Insertion order is the age order, which is how the oldest are dropped. */
|
|
148
|
+
modes: Record<string, string>;
|
|
149
|
+
/** Session ref → a message written into its own inbox that it has not taken. Read back
|
|
150
|
+
* pruned: only the ones still inside the hold window. */
|
|
151
|
+
parked: Record<string, Parked>;
|
|
112
152
|
}
|
|
113
|
-
export declare function readState(file: string): DaemonState;
|
|
153
|
+
export declare function readState(file: string, now?: number): DaemonState;
|
|
154
|
+
/** Both shapes of `copies`, every time. A daemon up to 0.10.0 reads `copies` as a map of
|
|
155
|
+
* plain session ids and uses what it finds there as a `--resume` target, so writing
|
|
156
|
+
* only the record would make every message to a session with a copy resume
|
|
157
|
+
* `[object Object]` after a rollback — and a fleet keeps the previous build precisely
|
|
158
|
+
* so it can roll back. */
|
|
114
159
|
export declare const writeState: (file: string, s: DaemonState) => void;
|
|
115
160
|
//# sourceMappingURL=store.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"store.d.ts","sourceRoot":"","sources":["../../src/control/store.ts"],"names":[],"mappings":"AAuBA,OAAO,EAAqC,KAAK,QAAQ,EAAE,KAAK,UAAU,EAAE,MAAM,2BAA2B,CAAC;AAC9G,OAAO,EAGL,KAAK,MAAM,EACX,KAAK,WAAW,EAChB,KAAK,SAAS,EAIf,MAAM,eAAe,CAAC;AAEvB,MAAM,WAAW,cAAc;IAC7B,qDAAqD;IACrD,GAAG,EAAE,MAAM,CAAC;IACZ,4DAA4D;IAC5D,OAAO,EAAE,MAAM,CAAC;IAChB,IAAI,EAAE,MAAM,CAAC;IACb,OAAO,EAAE,MAAM,CAAC;IAChB;sEACkE;IAClE,KAAK,EAAE,MAAM,CAAC;IACd,uEAAuE;IACvE,QAAQ,CAAC,EAAE,WAAW,CAAC;IACvB,IAAI,EAAE,CAAC,UAAU,GAAG;QAAE,IAAI,CAAC,EAAE,MAAM,CAAC;QAAC,QAAQ,EAAE,MAAM,CAAA;KAAE,CAAC,EAAE,CAAC;IAC3D,SAAS,EAAE,MAAM,CAAC;CACnB;AAED;wCACwC;AACxC,eAAO,MAAM,KAAK,YAAI,MAAM,EAAE,MAAM,EAAE,SAAS,CAAU,CAAC;AAC1D,MAAM,MAAM,WAAW,GAAG,CAAC,OAAO,KAAK,CAAC,CAAC,MAAM,CAAC,CAAC;AACjD,eAAO,MAAM,SAAS,MAAO,OAAO,KAAG,WAAW,GAAG,IACkB,CAAC;AAExE,MAAM,WAAW,aAAa;IAC5B,IAAI,EAAE,MAAM,CAAC;IACb,gFAAgF;IAChF,OAAO,EAAE,MAAM,EAAE,CAAC;IAClB,IAAI,EAAE,WAAW,CAAC;IAClB,SAAS,EAAE,cAAc,EAAE,CAAC;IAC5B;;
|
|
1
|
+
{"version":3,"file":"store.d.ts","sourceRoot":"","sources":["../../src/control/store.ts"],"names":[],"mappings":"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"}
|
package/dist/help.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"help.d.ts","sourceRoot":"","sources":["../src/help.ts"],"names":[],"mappings":"AAGA,wBAAgB,UAAU,CAAC,SAAS,EAAE,SAAS,MAAM,EAAE,GAAG,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,
|
|
1
|
+
{"version":3,"file":"help.d.ts","sourceRoot":"","sources":["../src/help.ts"],"names":[],"mappings":"AAGA,wBAAgB,UAAU,CAAC,SAAS,EAAE,SAAS,MAAM,EAAE,GAAG,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CA4D/E;AAED,wBAAgB,WAAW,CAAC,IAAI,EAAE,MAAM,EAAE,EAAE,SAAS,EAAE,SAAS,MAAM,EAAE,GAAG,MAAM,GAAG,SAAS,CAO5F"}
|
package/dist/hook.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"hook.d.ts","sourceRoot":"","sources":["../src/hook.ts"],"names":[],"mappings":";
|
|
1
|
+
{"version":3,"file":"hook.d.ts","sourceRoot":"","sources":["../src/hook.ts"],"names":[],"mappings":";AA0BA,iFAAiF;AACjF,MAAM,WAAW,MAAM;IACrB,KAAK,IAAI,MAAM,CAAC;IAChB,MAAM,CAAC,IAAI,EAAE,MAAM,GAAG,IAAI,CAAC;CAC5B;AAED;;0FAE0F;AAC1F,wBAAsB,QAAQ,CAAC,IAAI,EAAE,MAAM,EAAE,EAAE,GAAG,EAAE,MAAM,CAAC,UAAU,EAAE,EAAE,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAwRhG"}
|
package/dist/hook.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
// sessionpipe 0.
|
|
2
|
+
// sessionpipe 0.13.0 · Apache-2.0 · https://sessionpipe.org
|
|
3
3
|
|
|
4
4
|
// src/hook.ts
|
|
5
5
|
import { spawn } from "node:child_process";
|
|
@@ -50,6 +50,11 @@ function ask(sock, req, timeoutMs) {
|
|
|
50
50
|
|
|
51
51
|
// src/hook.ts
|
|
52
52
|
var UUID = /^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i;
|
|
53
|
+
var MODE_SHAPE = /^[A-Za-z]{1,40}$/;
|
|
54
|
+
var modeOf = (s) => {
|
|
55
|
+
const v = typeof s.permission_mode === "string" ? s.permission_mode : s.permissionMode;
|
|
56
|
+
return typeof v === "string" && MODE_SHAPE.test(v) ? v : void 0;
|
|
57
|
+
};
|
|
53
58
|
async function hookMain(argv, env, io) {
|
|
54
59
|
const t0 = process.hrtime.bigint();
|
|
55
60
|
let workMs = null;
|
|
@@ -126,6 +131,8 @@ async function hookMain(argv, env, io) {
|
|
|
126
131
|
// Devin's payload names no folder at all; this is the only thing that does.
|
|
127
132
|
"DEVIN_PROJECT_DIR",
|
|
128
133
|
"GEMINI_CLI_HOME",
|
|
134
|
+
// The session the control daemon ran this one for (PROTOCOL.md §3 delegated_by).
|
|
135
|
+
"SESSIONPIPE_ASKED_BY",
|
|
129
136
|
"SESSIONPIPE_CONTROL_JOB",
|
|
130
137
|
// The launcher a script named for a session it starts (PROTOCOL.md §3 launched_by).
|
|
131
138
|
"SESSIONPIPE_LAUNCHED_BY",
|
|
@@ -172,7 +179,7 @@ async function hookMain(argv, env, io) {
|
|
|
172
179
|
}
|
|
173
180
|
function controlAsk(stdin) {
|
|
174
181
|
if (harness !== "claude-code" || event !== "Stop" && event !== "PermissionRequest") return null;
|
|
175
|
-
if (env.SESSIONPIPE_CONTROL_JOB) return null;
|
|
182
|
+
if (env.SESSIONPIPE_CONTROL_JOB && event === "Stop") return null;
|
|
176
183
|
const sock = socketPath(state, env);
|
|
177
184
|
if (process.platform === "win32" ? !existsSync(path2.join(path2.dirname(configFile()), "control.json")) : !existsSync(sock))
|
|
178
185
|
return null;
|
|
@@ -186,10 +193,13 @@ async function hookMain(argv, env, io) {
|
|
|
186
193
|
if (!id) return null;
|
|
187
194
|
if (typeof s.transcript_path !== "string" && !UUID.test(id)) return null;
|
|
188
195
|
const session = `claude-code:${id}`;
|
|
196
|
+
const mode = modeOf(s);
|
|
189
197
|
if (event === "Stop")
|
|
190
|
-
return ask(
|
|
191
|
-
|
|
192
|
-
|
|
198
|
+
return ask(
|
|
199
|
+
sock,
|
|
200
|
+
{ op: "stop", session, active: s.stop_hook_active === true, ...mode ? { mode } : {} },
|
|
201
|
+
300
|
|
202
|
+
).then((r) => r?.op === "block" ? JSON.stringify({ decision: "block", reason: r.reason }) : null);
|
|
193
203
|
const tool = typeof s.tool_name === "string" && /^[A-Za-z0-9_.:-]{1,120}$/.test(s.tool_name) ? s.tool_name : void 0;
|
|
194
204
|
const turn = typeof s.prompt_id === "string" ? s.prompt_id : void 0;
|
|
195
205
|
const attention = `perm-${createHash("sha256").update(`${turn ?? ""}|${tool ?? ""}|${JSON.stringify(s.tool_input ?? null)}`).digest("hex").slice(0, 16)}`;
|