import { beforeEach, describe, expect, mock, test } from "bun:test"; import { fakeD1 } from "../metering/fake-d1.test-helper"; import { scopedTestState } from "../sites/scoped.test-helper"; let d1 = fakeD1(); mock.module("cloudflare:workers", () => ({ env: { get DB() { return d1.binding; }, }, waitUntil: () => undefined, })); const scoped = scopedTestState(); scoped.install(); const { linkForkObjects, linkObjects, purgeRepoLfs, rebillRepoLfs } = await import("./objects"); const { billableBytes, lfsUsage } = await import("./quota"); const refs = (oid: string) => (d1.db.query("SELECT refs FROM lfs_blobs WHERE oid = ?").get(oid) as { refs: number } | null)?.refs; beforeEach(() => { d1 = fakeD1(); scoped.reset(); d1.db.run(`CREATE TABLE lfs_blobs (oid TEXT PRIMARY KEY, size INTEGER NOT NULL, r2_key TEXT NOT NULL, refs INTEGER NOT NULL DEFAULT 0, orphaned_at INTEGER, created_at INTEGER NOT NULL)`); d1.db.run( "INSERT INTO lfs_blobs VALUES ('o1', 10, 'k1', 1, NULL, 0), ('o2', 20, 'k2', 1, NULL, 0), ('o3', 5, 'k3', 0, 1, 0)", ); }); describe("LFS links across scopes", () => { test("bills an owner once per oid however many of its repositories link it", async () => { await linkObjects({ id: "r1", owner_id: "u1" }, [ { oid: "o1", size: 10 }, { oid: "o2", size: 20 }, ]); await linkObjects({ id: "r2", owner_id: "u1" }, [{ oid: "o1", size: 10 }]); expect((await lfsUsage("u1")).storageBytes).toBe(30); expect(refs("o1")).toBe(3); expect( await billableBytes("u1", [ { oid: "o1", size: 10 }, { oid: "o9", size: 7 }, ]), ).toBe(7); }); test("never links an unreferenced copy or a size mismatch", async () => { await linkObjects({ id: "r1", owner_id: "u1" }, [ { oid: "o3", size: 5 }, { oid: "o1", size: 11 }, ]); expect((await lfsUsage("u1")).storageBytes).toBe(0); expect(scoped.repo("r1").query("SELECT COUNT(*) AS n FROM lfs_objects").get()).toEqual({ n: 0 }); }); test("a fork shares its parent's objects and purge releases them", async () => { await linkObjects({ id: "r1", owner_id: "u1" }, [{ oid: "o1", size: 10 }]); await linkForkObjects({ id: "f1", owner_id: "u2" }, "r1"); expect((await lfsUsage("u2")).storageBytes).toBe(10); await purgeRepoLfs({ id: "f1" }); expect((await lfsUsage("u2")).storageBytes).toBe(0); expect(refs("o1")).toBe(2); await purgeRepoLfs({ id: "r1" }); expect(refs("o1")).toBe(1); }); test("a transfer moves the bill to the new owner", async () => { await linkObjects({ id: "r1", owner_id: "u1" }, [{ oid: "o2", size: 20 }]); await rebillRepoLfs("r1", "u2"); expect((await lfsUsage("u1")).storageBytes).toBe(0); expect((await lfsUsage("u2")).storageBytes).toBe(20); }); });