sessionpipe 0.5.0 → 0.6.1

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.
@@ -3,7 +3,8 @@ export declare function dataDir(env?: NodeJS.ProcessEnv): string;
3
3
  export declare const launcherPath: (env?: NodeJS.ProcessEnv) => string;
4
4
  export declare const usesLauncher: (platform?: NodeJS.Platform) => boolean;
5
5
  /** The launcher, in sh. No node at all prints what Antigravity needs and exits 0: the
6
- * hook must stay invisible to the harness whatever is missing. */
6
+ * hook must stay invisible to the harness whatever is missing (and a PreToolUse entry
7
+ * an older install left must not turn into a silent deny). */
7
8
  export declare function launcherScript(node: string, hook: string, version: string): string;
8
9
  /** Copy the hook and worker out of the npm install and (re)write the launcher. The
9
10
  * worker goes first, so a hook that starts mid-copy never spawns a missing one. */
@@ -1 +1 @@
1
- {"version":3,"file":"launcher.d.ts","sourceRoot":"","sources":["../src/launcher.ts"],"names":[],"mappings":"AAYA,eAAO,MAAM,QAAQ,qBAAqB,CAAC;AAG3C,wBAAgB,OAAO,CAAC,GAAG,GAAE,MAAM,CAAC,UAAwB,GAAG,MAAM,CAGpE;AACD,eAAO,MAAM,YAAY,GAAI,MAAK,MAAM,CAAC,UAAwB,KAAG,MAA2C,CAAC;AAChH,eAAO,MAAM,YAAY,GAAI,WAAU,MAAM,CAAC,QAA2B,KAAG,OAA+B,CAAC;AAI5G;mEACmE;AACnE,wBAAgB,cAAc,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,GAAG,MAAM,CASlF;AAkBD;oFACoF;AACpF,wBAAgB,eAAe,CAAC,CAAC,EAAE;IAAE,OAAO,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,MAAM,CAAC;IAAC,OAAO,EAAE,MAAM,CAAC;IAAC,GAAG,CAAC,EAAE,MAAM,CAAC,UAAU,CAAA;CAAE,GAAG;IAC/G,QAAQ,EAAE,MAAM,CAAC;IACjB,OAAO,EAAE,OAAO,CAAC;CAClB,CASA;AAED,wBAAgB,cAAc,CAAC,GAAG,GAAE,MAAM,CAAC,UAAwB,GAAG,IAAI,CAEzE;AAED,MAAM,WAAW,aAAa;IAC5B,IAAI,EAAE,MAAM,CAAC;IACb,OAAO,EAAE,OAAO,CAAC;IACjB,iEAAiE;IACjE,IAAI,EAAE,MAAM,GAAG,IAAI,CAAC;IACpB,MAAM,EAAE,OAAO,CAAC;IAChB,OAAO,EAAE,MAAM,GAAG,IAAI,CAAC;IACvB,QAAQ,EAAE,MAAM,EAAE,CAAC;CACpB;AAED,6CAA6C;AAC7C,wBAAgB,aAAa,CAAC,OAAO,EAAE,MAAM,EAAE,GAAG,GAAE,MAAM,CAAC,UAAwB,GAAG,aAAa,CAwClG"}
1
+ {"version":3,"file":"launcher.d.ts","sourceRoot":"","sources":["../src/launcher.ts"],"names":[],"mappings":"AAaA,eAAO,MAAM,QAAQ,qBAAqB,CAAC;AAG3C,wBAAgB,OAAO,CAAC,GAAG,GAAE,MAAM,CAAC,UAAwB,GAAG,MAAM,CAGpE;AACD,eAAO,MAAM,YAAY,GAAI,MAAK,MAAM,CAAC,UAAwB,KAAG,MAA2C,CAAC;AAChH,eAAO,MAAM,YAAY,GAAI,WAAU,MAAM,CAAC,QAA2B,KAAG,OAA+B,CAAC;AAI5G;;+DAE+D;AAC/D,wBAAgB,cAAc,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,GAAG,MAAM,CASlF;AAkBD;oFACoF;AACpF,wBAAgB,eAAe,CAAC,CAAC,EAAE;IAAE,OAAO,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,MAAM,CAAC;IAAC,OAAO,EAAE,MAAM,CAAC;IAAC,GAAG,CAAC,EAAE,MAAM,CAAC,UAAU,CAAA;CAAE,GAAG;IAC/G,QAAQ,EAAE,MAAM,CAAC;IACjB,OAAO,EAAE,OAAO,CAAC;CAClB,CASA;AAED,wBAAgB,cAAc,CAAC,GAAG,GAAE,MAAM,CAAC,UAAwB,GAAG,IAAI,CAEzE;AAED,MAAM,WAAW,aAAa;IAC5B,IAAI,EAAE,MAAM,CAAC;IACb,OAAO,EAAE,OAAO,CAAC;IACjB,iEAAiE;IACjE,IAAI,EAAE,MAAM,GAAG,IAAI,CAAC;IACpB,MAAM,EAAE,OAAO,CAAC;IAChB,OAAO,EAAE,MAAM,GAAG,IAAI,CAAC;IACvB,QAAQ,EAAE,MAAM,EAAE,CAAC;CACpB;AAED,6CAA6C;AAC7C,wBAAgB,aAAa,CAAC,OAAO,EAAE,MAAM,EAAE,GAAG,GAAE,MAAM,CAAC,UAAwB,GAAG,aAAa,CAwClG"}
@@ -0,0 +1,70 @@
1
+ export declare const REGISTRY_LATEST = "https://registry.npmjs.org/sessionpipe/latest";
2
+ /** Order two versions: <0, 0, >0, or null if either isn't one. A release sorts above
3
+ * its own prereleases; prereleases compare by their tag. */
4
+ export declare function compareVersions(a: string, b: string): number | null;
5
+ /** `a` is a release newer than `b`. A prerelease is never offered as an update: the
6
+ * `latest` dist-tag is a release, and anything else is someone's experiment. */
7
+ export declare function isNewer(a: string, b: string): boolean;
8
+ /** The registry's `latest` for sessionpipe: one GET, nothing sent but the request. */
9
+ export declare function latestVersion(f?: typeof fetch, timeoutMs?: number): Promise<string>;
10
+ /** The prefix a global npm install of sessionpipe lives under, from the running copy's
11
+ * dist folder (`<prefix>/lib/node_modules/sessionpipe/dist`, on Windows
12
+ * `<prefix>\node_modules\sessionpipe\dist`). */
13
+ export declare function prefixOf(distDir: string, platform?: NodeJS.Platform): string | null;
14
+ /** The npm prefix this copy was installed into with `npm install -g`, or null when it
15
+ * isn't a global npm install (the npx cache, a git checkout, a project's
16
+ * node_modules, a dev build). A global install always has its bin link in the prefix. */
17
+ export declare function globalPrefix(distDir: string, platform?: NodeJS.Platform): string | null;
18
+ /** Why npm can't write this prefix (installed with sudo, a read-only image), or null. */
19
+ export declare function unwritable(prefix: string, platform?: NodeJS.Platform): string | null;
20
+ /** npm, run by this very node: under launchd PATH is /usr/bin:/bin, so neither `npm`
21
+ * nor the `node` its shebang asks for is on it. Its npm-cli.js sits beside the node
22
+ * binary (nvm, Homebrew, the official builds, the node Docker images). */
23
+ export declare function npmArgv(node: string, platform?: NodeJS.Platform): string[];
24
+ export interface ExecResult {
25
+ code: number | null;
26
+ stdout: string;
27
+ stderr: string;
28
+ error?: string;
29
+ }
30
+ export type Exec = (argv: string[], o: {
31
+ env: NodeJS.ProcessEnv;
32
+ timeoutMs: number;
33
+ }) => Promise<ExecResult>;
34
+ /** Run a command to the end, keeping the tail of its output. */
35
+ export declare const execCapture: Exec;
36
+ export interface InstallOptions {
37
+ /** The node running this copy (process.execPath). */
38
+ node: string;
39
+ /** The running copy's dist folder: where the new one lands, under the same prefix. */
40
+ distDir: string;
41
+ /** Harnesses whose hooks to re-arm afterwards (config.harnesses that are enabled). */
42
+ harnesses: string[];
43
+ env?: NodeJS.ProcessEnv;
44
+ exec?: Exec;
45
+ platform?: NodeJS.Platform;
46
+ }
47
+ export type InstallResult = {
48
+ ok: true;
49
+ ms: number;
50
+ hooks: string;
51
+ } | {
52
+ ok: false;
53
+ ms: number;
54
+ error: string;
55
+ stage: "prefix" | "npm" | "verify";
56
+ };
57
+ /** The version of the copy on disk (which may not be the one running). */
58
+ export declare function installedVersion(o: {
59
+ node: string;
60
+ distDir: string;
61
+ env?: NodeJS.ProcessEnv;
62
+ exec?: Exec;
63
+ }): Promise<string | null>;
64
+ /** `npm install -g sessionpipe@<version>` into the prefix the running copy came from,
65
+ * check the copy on disk says that version, then re-copy the hook launcher's files
66
+ * (the hooks run copies in ~/.local/share/sessionpipe, which npm never touches) for
67
+ * the harnesses already set up here. Lifecycle scripts are off: sessionpipe has none,
68
+ * and an unattended install runs nothing it fetched. */
69
+ export declare function installVersion(version: string, o: InstallOptions): Promise<InstallResult>;
70
+ //# sourceMappingURL=update.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"update.d.ts","sourceRoot":"","sources":["../src/update.ts"],"names":[],"mappings":"AAaA,eAAO,MAAM,eAAe,kDAAkD,CAAC;AAc/E;6DAC6D;AAC7D,wBAAgB,eAAe,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CASnE;AAED;iFACiF;AACjF,wBAAgB,OAAO,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,MAAM,GAAG,OAAO,CAKrD;AAED,sFAAsF;AACtF,wBAAsB,aAAa,CAAC,CAAC,GAAE,OAAO,KAAa,EAAE,SAAS,SAAO,GAAG,OAAO,CAAC,MAAM,CAAC,CAS9F;AAED;;iDAEiD;AACjD,wBAAgB,QAAQ,CAAC,OAAO,EAAE,MAAM,EAAE,QAAQ,GAAE,MAAM,CAAC,QAA2B,GAAG,MAAM,GAAG,IAAI,CAIrG;AAED;;0FAE0F;AAC1F,wBAAgB,YAAY,CAAC,OAAO,EAAE,MAAM,EAAE,QAAQ,GAAE,MAAM,CAAC,QAA2B,GAAG,MAAM,GAAG,IAAI,CAMzG;AAED,yFAAyF;AACzF,wBAAgB,UAAU,CAAC,MAAM,EAAE,MAAM,EAAE,QAAQ,GAAE,MAAM,CAAC,QAA2B,GAAG,MAAM,GAAG,IAAI,CAQtG;AAED;;2EAE2E;AAC3E,wBAAgB,OAAO,CAAC,IAAI,EAAE,MAAM,EAAE,QAAQ,GAAE,MAAM,CAAC,QAA2B,GAAG,MAAM,EAAE,CAa5F;AAED,MAAM,WAAW,UAAU;IACzB,IAAI,EAAE,MAAM,GAAG,IAAI,CAAC;IACpB,MAAM,EAAE,MAAM,CAAC;IACf,MAAM,EAAE,MAAM,CAAC;IACf,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB;AACD,MAAM,MAAM,IAAI,GAAG,CAAC,IAAI,EAAE,MAAM,EAAE,EAAE,CAAC,EAAE;IAAE,GAAG,EAAE,MAAM,CAAC,UAAU,CAAC;IAAC,SAAS,EAAE,MAAM,CAAA;CAAE,KAAK,OAAO,CAAC,UAAU,CAAC,CAAC;AAE7G,gEAAgE;AAChE,eAAO,MAAM,WAAW,EAAE,IAiCtB,CAAC;AAEL,MAAM,WAAW,cAAc;IAC7B,qDAAqD;IACrD,IAAI,EAAE,MAAM,CAAC;IACb,sFAAsF;IACtF,OAAO,EAAE,MAAM,CAAC;IAChB,sFAAsF;IACtF,SAAS,EAAE,MAAM,EAAE,CAAC;IACpB,GAAG,CAAC,EAAE,MAAM,CAAC,UAAU,CAAC;IACxB,IAAI,CAAC,EAAE,IAAI,CAAC;IACZ,QAAQ,CAAC,EAAE,MAAM,CAAC,QAAQ,CAAC;CAC5B;AAED,MAAM,MAAM,aAAa,GACrB;IAAE,EAAE,EAAE,IAAI,CAAC;IAAC,EAAE,EAAE,MAAM,CAAC;IAAC,KAAK,EAAE,MAAM,CAAA;CAAE,GACvC;IAAE,EAAE,EAAE,KAAK,CAAC;IAAC,EAAE,EAAE,MAAM,CAAC;IAAC,KAAK,EAAE,MAAM,CAAC;IAAC,KAAK,EAAE,QAAQ,GAAG,KAAK,GAAG,QAAQ,CAAA;CAAE,CAAC;AAKjF,0EAA0E;AAC1E,wBAAsB,gBAAgB,CAAC,CAAC,EAAE;IACxC,IAAI,EAAE,MAAM,CAAC;IACb,OAAO,EAAE,MAAM,CAAC;IAChB,GAAG,CAAC,EAAE,MAAM,CAAC,UAAU,CAAC;IACxB,IAAI,CAAC,EAAE,IAAI,CAAC;CACb,GAAG,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC,CAOzB;AAED;;;;yDAIyD;AACzD,wBAAsB,cAAc,CAAC,OAAO,EAAE,MAAM,EAAE,CAAC,EAAE,cAAc,GAAG,OAAO,CAAC,aAAa,CAAC,CA8C/F"}
package/dist/worker.js CHANGED
@@ -1,5 +1,5 @@
1
1
  #!/usr/bin/env node
2
- // sessionpipe 0.5.0 · Apache-2.0 · https://sessionpipe.org
2
+ // sessionpipe 0.6.1 · Apache-2.0 · https://sessionpipe.org
3
3
 
4
4
  // src/worker.ts
5
5
  import { readFileSync as readFileSync9, unlinkSync as unlinkSync5 } from "node:fs";
@@ -372,20 +372,19 @@ function installedClaudeShaped(file, harness, events, cmd, o) {
372
372
  // ../core/src/adapters/antigravity.ts
373
373
  var NAME = "antigravity";
374
374
  var HOOK_NAME = "sessionpipe";
375
- var AG_EVENTS = ["PreInvocation", "PostInvocation", "PreToolUse", "PostToolUse", "Stop"];
375
+ var AG_EVENTS = ["PreInvocation", "PostInvocation", "PostToolUse", "Stop"];
376
+ var AG_STALE_PRETOOL = '{"decision":"ask","reason":"sessionpipe: an outdated PreToolUse hook is still loaded. Restart this conversation (or run sessionpipe install) to drop it."}\n';
377
+ var antigravityAnswer = (event) => event === "PreToolUse" ? AG_STALE_PRETOOL : "{}\n";
376
378
  var gemini = (env) => env.GEMINI_CLI_HOME || path4.join(HOME, ".gemini");
377
379
  var hooksFile = (env) => path4.join(gemini(env), "config", "hooks.json");
378
380
  var projectsDir = (env) => path4.join(gemini(env), "config", "projects");
379
381
  var dataDirs = (env) => ["antigravity", "antigravity-cli", "antigravity-ide"].map((d) => path4.join(gemini(env), d));
380
382
  var ID_RE = /^[A-Za-z0-9_-]{1,128}$/;
381
383
  var validTool = (n) => typeof n === "string" && /^[A-Za-z0-9_.:-]{1,120}$/.test(n);
382
- function entry(cmd, lean) {
384
+ function entry(cmd) {
383
385
  const handler = (e) => ({ type: "command", command: cmd([NAME, e]).command, timeout: 5 });
384
386
  const out = { enabled: true };
385
- for (const e of AG_EVENTS) {
386
- if (lean && e === "PreToolUse") continue;
387
- out[e] = /Tool/.test(e) ? [{ matcher: "*", hooks: [handler(e)] }] : [handler(e)];
388
- }
387
+ for (const e of AG_EVENTS) out[e] = /Tool/.test(e) ? [{ matcher: "*", hooks: [handler(e)] }] : [handler(e)];
389
388
  return out;
390
389
  }
391
390
  var antigravity = {
@@ -393,12 +392,12 @@ var antigravity = {
393
392
  events: AG_EVENTS,
394
393
  detect: (env = process.env) => existsSync2(path4.join(gemini(env), "config")) || dataDirs(env).some((d) => existsSync2(d)),
395
394
  configFiles: (env = process.env) => [hooksFile(env)],
396
- install(cmd, env = process.env, opts = {}) {
395
+ install(cmd, env = process.env) {
397
396
  const file = hooksFile(env);
398
397
  const f = readJsonFile(file);
399
398
  if (!f.ok) return [{ file, changed: false, skipped: true, note: `${f.reason}; not touched` }];
400
399
  const hooks = f.value;
401
- const e = entry(cmd, opts.lean);
400
+ const e = entry(cmd);
402
401
  if (JSON.stringify(hooks[HOOK_NAME]) === JSON.stringify(e)) return [{ file, changed: false }];
403
402
  hooks[HOOK_NAME] = e;
404
403
  mkdirSync2(path4.dirname(file), { recursive: true });
@@ -427,14 +426,14 @@ var antigravity = {
427
426
  writeFileSync2(file, formatJson(hooks, f));
428
427
  return [{ file, changed: true }];
429
428
  },
430
- installed(cmd, env = process.env, opts = {}) {
429
+ installed(cmd, env = process.env) {
431
430
  const file = hooksFile(env);
432
431
  const f = readJsonFile(file);
433
432
  const have = f.ok ? f.value[HOOK_NAME] : void 0;
434
433
  return [
435
434
  {
436
435
  file,
437
- state: !have ? "missing" : JSON.stringify(have) === JSON.stringify(entry(cmd, opts.lean)) ? "current" : "stale"
436
+ state: !have ? "missing" : JSON.stringify(have) === JSON.stringify(entry(cmd)) ? "current" : "stale"
438
437
  }
439
438
  ];
440
439
  },
@@ -446,7 +445,8 @@ var antigravity = {
446
445
  } catch {
447
446
  }
448
447
  const id = s.conversationId ?? s.session_id ?? s.sessionId;
449
- if (!id) return { session: { id: "" }, events: [], stdout: "{}\n" };
448
+ const stdout = antigravityAnswer(event);
449
+ if (!id) return { session: { id: "" }, events: [], stdout };
450
450
  const workspaces = agWorkspaces(s.workspacePaths);
451
451
  const session = { id: String(id), cwd: workspaces[0] ?? input.cwd };
452
452
  if (typeof s.modelName === "string" && s.modelName !== "auto") session.model = s.modelName;
@@ -467,7 +467,8 @@ var antigravity = {
467
467
  if (tool) events.push(ev("tool.started", { tool, input: toolCall?.args }));
468
468
  break;
469
469
  case "PostToolUse":
470
- if (tool)
470
+ if (!tool) events.push(ev("session.heartbeat", {}));
471
+ else
471
472
  events.push(
472
473
  ev("tool.ended", {
473
474
  tool,
@@ -481,9 +482,9 @@ var antigravity = {
481
482
  events.push(ev("turn.ended", { reason: s.error ? "error" : "stop" }));
482
483
  break;
483
484
  default:
484
- return { session, events: [], stdout: "{}\n" };
485
+ return { session, events: [], stdout };
485
486
  }
486
- const r = { session, events, stdout: "{}\n", hints: { workspaces } };
487
+ const r = { session, events, stdout, hints: { workspaces } };
487
488
  if (typeof s.transcriptPath === "string") r.transcript = s.transcriptPath;
488
489
  return r;
489
490
  },