Skip to content

Instantly share code, notes, and snippets.

@acmerfight
Last active September 3, 2026 14:34
Show Gist options
  • Select an option

  • Save acmerfight/5ae93bf79ae6739e556f1a56005c5772 to your computer and use it in GitHub Desktop.

Select an option

Save acmerfight/5ae93bf79ae6739e556f1a56005c5772 to your computer and use it in GitHub Desktop.
Reproduction for earendil-works/pi#9073

JsonlSessionRepo cwd-encoding collision reproduction

Reproduction for earendil-works/pi#9073, verified against commit e44d75c20a51142abc056c243b13c1d7bb4be687.

The patch adds one regression test to packages/agent/test/harness/jsonl-session-repo.test.ts. It fixes the clock, creates the same explicit ID in two distinct cwd values whose encoded directory names collide, and requires distinct physical paths and cwd-scoped discovery.

Run

From the repository root, with the patch file in that directory:

git apply jsonl-session-repo-cwd-collision.patch
cd packages/agent
node "$(git rev-parse --show-toplevel)/node_modules/vitest/dist/cli.js" --run test/harness/jsonl-session-repo.test.ts --reporter verbose

Current result

Against the commit above, the seven existing cases pass and the added regression fails during the second create():

Session already exists: same

The error originates in JsonlSessionRepo.assertSessionIdAvailable(). See failure.txt for the failure summary.

RUN v4.1.9 packages/agent
PASS persists metadata and filters discovery by cwd
PASS atomically publishes a branchless session header
PASS keeps an explicit Session mutation through commit until end
PASS rejects unsupported storage versions without repairing a torn tail
PASS keeps fork destinations claimed until close and rejects deleting open sessions
PASS rejects concurrent creates for the same working-directory id
PASS allows the same id to be active in different working directories
FAIL allows the same id when working-directory encodings collide
Error: Session already exists: same
at JsonlSessionRepo.assertSessionIdAvailable (src/harness/session/jsonl/repo.ts:297:23)
at JsonlSessionRepo.resolveNewSessionPath (src/harness/session/jsonl/repo.ts:275:3)
at JsonlSessionRepo.create (src/harness/session/jsonl/repo.ts:77:11)
at test/harness/jsonl-session-repo.test.ts:211:18
Test Files 1 failed (1)
Tests 1 failed | 7 passed (8)
diff --git a/packages/agent/test/harness/jsonl-session-repo.test.ts b/packages/agent/test/harness/jsonl-session-repo.test.ts
index 33cf05887..595dee704 100644
--- a/packages/agent/test/harness/jsonl-session-repo.test.ts
+++ b/packages/agent/test/harness/jsonl-session-repo.test.ts
@@ -1,3 +1,4 @@
+import { join } from "node:path";
import { describe, expect, it } from "vitest";
import { BACKGROUND_CONTEXT, type Context } from "../../src/harness/context.ts";
import { NodeExecutionEnv } from "../../src/harness/env/nodejs.ts";
@@ -196,4 +197,28 @@ describe("JsonlSessionRepo cwd-scoped lifecycle", () => {
await Promise.all(reopened.map((session) => session.close(BACKGROUND_CONTEXT)));
await repo.close(BACKGROUND_CONTEXT);
});
+
+ // Regression for #9073.
+ it("allows the same id when working-directory encodings collide", async () => {
+ const root = createTempDir();
+ const fileSystem = new NodeExecutionEnv({ cwd: root });
+ const repo = new JsonlSessionRepo({ fileSystem, sessionsRoot: "sessions", now: () => NOW });
+ const firstCwd = join(root, "tenant-a", "project");
+ const secondCwd = join(root, "tenant", "a-project");
+
+ const first = await repo.create({ id: "same", cwd: firstCwd }, BACKGROUND_CONTEXT);
+ await first.close(BACKGROUND_CONTEXT);
+ const second = await repo.create({ id: "same", cwd: secondCwd }, BACKGROUND_CONTEXT);
+
+ expect(first.metadata.path).not.toBe(second.metadata.path);
+ expect(await repo.list({ cwd: firstCwd }, BACKGROUND_CONTEXT)).toMatchObject([
+ { id: "same", cwd: firstCwd, path: first.metadata.path },
+ ]);
+ expect(await repo.list({ cwd: secondCwd }, BACKGROUND_CONTEXT)).toMatchObject([
+ { id: "same", cwd: secondCwd, path: second.metadata.path },
+ ]);
+
+ await second.close(BACKGROUND_CONTEXT);
+ await repo.close(BACKGROUND_CONTEXT);
+ });
});
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment