@cat-factory/worker 0.86.0 → 0.86.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.
@@ -0,0 +1,17 @@
1
+ import type { WorkspaceMemberRecord, WorkspaceMemberRepository, WorkspaceRole } from '@cat-factory/kernel';
2
+ import type { D1Database } from '@cloudflare/workers-types';
3
+ /** D1-backed store of workspace memberships (workspace RBAC; migration 0052). */
4
+ export declare class D1WorkspaceMemberRepository implements WorkspaceMemberRepository {
5
+ private readonly db;
6
+ constructor({ db }: {
7
+ db: D1Database;
8
+ });
9
+ get(workspaceId: string, userId: string): Promise<WorkspaceMemberRecord | null>;
10
+ listByWorkspace(workspaceId: string): Promise<WorkspaceMemberRecord[]>;
11
+ listWorkspaceIdsForUser(userId: string): Promise<string[]>;
12
+ getRolesForUserInWorkspaces(userId: string, workspaceIds: string[]): Promise<Map<string, WorkspaceRole>>;
13
+ upsert(member: WorkspaceMemberRecord): Promise<void>;
14
+ remove(workspaceId: string, userId: string): Promise<void>;
15
+ removeByAccountMembership(accountId: string, userId: string): Promise<number>;
16
+ }
17
+ //# sourceMappingURL=D1WorkspaceMemberRepository.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"D1WorkspaceMemberRepository.d.ts","sourceRoot":"","sources":["../../../src/infrastructure/repositories/D1WorkspaceMemberRepository.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EACV,qBAAqB,EACrB,yBAAyB,EACzB,aAAa,EACd,MAAM,qBAAqB,CAAA;AAC5B,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,2BAA2B,CAAA;AA0B3D,iFAAiF;AACjF,qBAAa,2BAA4B,YAAW,yBAAyB;IAC3E,OAAO,CAAC,QAAQ,CAAC,EAAE,CAAY;IAE/B,YAAY,EAAE,EAAE,EAAE,EAAE;QAAE,EAAE,EAAE,UAAU,CAAA;KAAE,EAErC;IAEK,GAAG,CAAC,WAAW,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,qBAAqB,GAAG,IAAI,CAAC,CAMpF;IAEK,eAAe,CAAC,WAAW,EAAE,MAAM,GAAG,OAAO,CAAC,qBAAqB,EAAE,CAAC,CAM3E;IAEK,uBAAuB,CAAC,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC,CAM/D;IAEK,2BAA2B,CAC/B,MAAM,EAAE,MAAM,EACd,YAAY,EAAE,MAAM,EAAE,GACrB,OAAO,CAAC,GAAG,CAAC,MAAM,EAAE,aAAa,CAAC,CAAC,CAkBrC;IAEK,MAAM,CAAC,MAAM,EAAE,qBAAqB,GAAG,OAAO,CAAC,IAAI,CAAC,CASzD;IAEK,MAAM,CAAC,WAAW,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAK/D;IAEK,yBAAyB,CAAC,SAAS,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC,CAYlF;CACF"}
@@ -0,0 +1,87 @@
1
+ import { chunkForIn } from './chunk';
2
+ /** Coerce a stored role string to a valid {@link WorkspaceRole}, defaulting to viewer. */
3
+ function parseRole(role) {
4
+ return role === 'admin' || role === 'member' || role === 'viewer' ? role : 'viewer';
5
+ }
6
+ function rowToMember(row) {
7
+ return {
8
+ workspaceId: row.workspace_id,
9
+ userId: row.user_id,
10
+ role: parseRole(row.role),
11
+ createdAt: row.created_at,
12
+ addedByUserId: row.added_by_user_id,
13
+ };
14
+ }
15
+ /** D1-backed store of workspace memberships (workspace RBAC; migration 0052). */
16
+ export class D1WorkspaceMemberRepository {
17
+ db;
18
+ constructor({ db }) {
19
+ this.db = db;
20
+ }
21
+ async get(workspaceId, userId) {
22
+ const row = await this.db
23
+ .prepare('SELECT * FROM workspace_members WHERE workspace_id = ? AND user_id = ?')
24
+ .bind(workspaceId, userId)
25
+ .first();
26
+ return row ? rowToMember(row) : null;
27
+ }
28
+ async listByWorkspace(workspaceId) {
29
+ const { results } = await this.db
30
+ .prepare('SELECT * FROM workspace_members WHERE workspace_id = ? ORDER BY created_at ASC')
31
+ .bind(workspaceId)
32
+ .all();
33
+ return results.map(rowToMember);
34
+ }
35
+ async listWorkspaceIdsForUser(userId) {
36
+ const { results } = await this.db
37
+ .prepare('SELECT workspace_id FROM workspace_members WHERE user_id = ?')
38
+ .bind(userId)
39
+ .all();
40
+ return results.map((r) => r.workspace_id);
41
+ }
42
+ async getRolesForUserInWorkspaces(userId, workspaceIds) {
43
+ const out = new Map();
44
+ if (workspaceIds.length === 0)
45
+ return out;
46
+ // ONE chunked-IN read per chunk (never a per-board point-read loop). Chunk via the
47
+ // shared helper so each statement stays under D1's 100 bound-parameter ceiling — the
48
+ // leading `user_id = ?` is the reason the helper leaves headroom below 100.
49
+ for (const chunk of chunkForIn(workspaceIds)) {
50
+ const placeholders = chunk.map(() => '?').join(', ');
51
+ const { results } = await this.db
52
+ .prepare(`SELECT workspace_id, role FROM workspace_members
53
+ WHERE user_id = ? AND workspace_id IN (${placeholders})`)
54
+ .bind(userId, ...chunk)
55
+ .all();
56
+ for (const r of results)
57
+ out.set(r.workspace_id, parseRole(r.role));
58
+ }
59
+ return out;
60
+ }
61
+ async upsert(member) {
62
+ await this.db
63
+ .prepare(`INSERT INTO workspace_members (workspace_id, user_id, role, created_at, added_by_user_id)
64
+ VALUES (?, ?, ?, ?, ?)
65
+ ON CONFLICT (workspace_id, user_id) DO UPDATE SET role = excluded.role`)
66
+ .bind(member.workspaceId, member.userId, member.role, member.createdAt, member.addedByUserId)
67
+ .run();
68
+ }
69
+ async remove(workspaceId, userId) {
70
+ await this.db
71
+ .prepare('DELETE FROM workspace_members WHERE workspace_id = ? AND user_id = ?')
72
+ .bind(workspaceId, userId)
73
+ .run();
74
+ }
75
+ async removeByAccountMembership(accountId, userId) {
76
+ // One DELETE joined on the owning account — drop every membership this user holds in
77
+ // boards of `accountId`. D1 has no `DELETE ... USING`, so scope by subquery.
78
+ const result = await this.db
79
+ .prepare(`DELETE FROM workspace_members
80
+ WHERE user_id = ?
81
+ AND workspace_id IN (SELECT id FROM workspaces WHERE account_id = ?)`)
82
+ .bind(userId, accountId)
83
+ .run();
84
+ return result.meta.changes ?? 0;
85
+ }
86
+ }
87
+ //# sourceMappingURL=D1WorkspaceMemberRepository.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"D1WorkspaceMemberRepository.js","sourceRoot":"","sources":["../../../src/infrastructure/repositories/D1WorkspaceMemberRepository.ts"],"names":[],"mappings":"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"}
@@ -1,5 +1,5 @@
1
- import type { ServiceRehome, WorkspaceRepository, WorkspaceVisibility } from '@cat-factory/kernel';
2
- import type { Workspace } from '@cat-factory/contracts';
1
+ import type { ServiceRehome, WorkspaceAccessRow, WorkspaceRepository, WorkspaceVisibility } from '@cat-factory/kernel';
2
+ import type { Workspace, WorkspaceAccessMode } from '@cat-factory/contracts';
3
3
  import type { D1Database } from '@cloudflare/workers-types';
4
4
  export declare const D1_ONLY_WORKSPACE_SCOPED_TABLES: readonly ['live_containers'];
5
5
  export declare class D1WorkspaceRepository implements WorkspaceRepository {
@@ -11,6 +11,8 @@ export declare class D1WorkspaceRepository implements WorkspaceRepository {
11
11
  get(id: string): Promise<Workspace | null>;
12
12
  ownerOf(id: string): Promise<string | null | undefined>;
13
13
  accountOf(id: string): Promise<string | null | undefined>;
14
+ accessRowOf(id: string): Promise<WorkspaceAccessRow | undefined>;
15
+ setAccessMode(id: string, mode: WorkspaceAccessMode): Promise<void>;
14
16
  create(workspace: Workspace, ownerUserId: string | null, accountId: string | null): Promise<void>;
15
17
  rename(id: string, name: string): Promise<void>;
16
18
  setDescription(id: string, description: string | null): Promise<void>;
@@ -1 +1 @@
1
- {"version":3,"file":"D1WorkspaceRepository.d.ts","sourceRoot":"","sources":["../../../src/infrastructure/repositories/D1WorkspaceRepository.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,aAAa,EAAE,mBAAmB,EAAE,mBAAmB,EAAE,MAAM,qBAAqB,CAAA;AAElG,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,wBAAwB,CAAA;AACvD,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,2BAA2B,CAAA;AAS3D,eAAO,MAAM,+BAA+B,YAAI,iBAAiB,CAAU,CAAA;AAE3E,qBAAa,qBAAsB,YAAW,mBAAmB;IAC/D,OAAO,CAAC,QAAQ,CAAC,EAAE,CAAY;IAE/B,YAAY,EAAE,EAAE,EAAE,EAAE;QAAE,EAAE,EAAE,UAAU,CAAA;KAAE,EAErC;IAEK,WAAW,CAAC,KAAK,EAAE,mBAAmB,GAAG,OAAO,CAAC,SAAS,EAAE,CAAC,CAsBlE;IAEK,GAAG,CAAC,EAAE,EAAE,MAAM,GAAG,OAAO,CAAC,SAAS,GAAG,IAAI,CAAC,CAM/C;IAEK,OAAO,CAAC,EAAE,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,GAAG,IAAI,GAAG,SAAS,CAAC,CAO5D;IAEK,SAAS,CAAC,EAAE,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,GAAG,IAAI,GAAG,SAAS,CAAC,CAO9D;IAEK,MAAM,CACV,SAAS,EAAE,SAAS,EACpB,WAAW,EAAE,MAAM,GAAG,IAAI,EAC1B,SAAS,EAAE,MAAM,GAAG,IAAI,GACvB,OAAO,CAAC,IAAI,CAAC,CAcf;IAEK,MAAM,CAAC,EAAE,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAEpD;IAEK,cAAc,CAAC,EAAE,EAAE,MAAM,EAAE,WAAW,EAAE,MAAM,GAAG,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC,CAK1E;IAEK,MAAM,CAAC,EAAE,EAAE,MAAM,EAAE,MAAM,GAAE,aAAa,EAAO,GAAG,OAAO,CAAC,IAAI,CAAC,CAyDpE;CACF"}
1
+ {"version":3,"file":"D1WorkspaceRepository.d.ts","sourceRoot":"","sources":["../../../src/infrastructure/repositories/D1WorkspaceRepository.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EACV,aAAa,EACb,kBAAkB,EAClB,mBAAmB,EACnB,mBAAmB,EACpB,MAAM,qBAAqB,CAAA;AAE5B,OAAO,KAAK,EAAE,SAAS,EAAE,mBAAmB,EAAE,MAAM,wBAAwB,CAAA;AAC5E,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,2BAA2B,CAAA;AAS3D,eAAO,MAAM,+BAA+B,YAAI,iBAAiB,CAAU,CAAA;AAE3E,qBAAa,qBAAsB,YAAW,mBAAmB;IAC/D,OAAO,CAAC,QAAQ,CAAC,EAAE,CAAY;IAE/B,YAAY,EAAE,EAAE,EAAE,EAAE;QAAE,EAAE,EAAE,UAAU,CAAA;KAAE,EAErC;IAEK,WAAW,CAAC,KAAK,EAAE,mBAAmB,GAAG,OAAO,CAAC,SAAS,EAAE,CAAC,CAsBlE;IAEK,GAAG,CAAC,EAAE,EAAE,MAAM,GAAG,OAAO,CAAC,SAAS,GAAG,IAAI,CAAC,CAM/C;IAEK,OAAO,CAAC,EAAE,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,GAAG,IAAI,GAAG,SAAS,CAAC,CAO5D;IAEK,SAAS,CAAC,EAAE,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,GAAG,IAAI,GAAG,SAAS,CAAC,CAO9D;IAEK,WAAW,CAAC,EAAE,EAAE,MAAM,GAAG,OAAO,CAAC,kBAAkB,GAAG,SAAS,CAAC,CAerE;IAEK,aAAa,CAAC,EAAE,EAAE,MAAM,EAAE,IAAI,EAAE,mBAAmB,GAAG,OAAO,CAAC,IAAI,CAAC,CAExE;IAEK,MAAM,CACV,SAAS,EAAE,SAAS,EACpB,WAAW,EAAE,MAAM,GAAG,IAAI,EAC1B,SAAS,EAAE,MAAM,GAAG,IAAI,GACvB,OAAO,CAAC,IAAI,CAAC,CAcf;IAEK,MAAM,CAAC,EAAE,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAEpD;IAEK,cAAc,CAAC,EAAE,EAAE,MAAM,EAAE,WAAW,EAAE,MAAM,GAAG,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC,CAK1E;IAEK,MAAM,CAAC,EAAE,EAAE,MAAM,EAAE,MAAM,GAAE,aAAa,EAAO,GAAG,OAAO,CAAC,IAAI,CAAC,CAyDpE;CACF"}
@@ -56,6 +56,22 @@ export class D1WorkspaceRepository {
56
56
  // Row absent → undefined (missing); present → the (possibly null) account id.
57
57
  return row ? row.account_id : undefined;
58
58
  }
59
+ async accessRowOf(id) {
60
+ const row = await this.db
61
+ .prepare('SELECT account_id, owner_user_id, access_mode FROM workspaces WHERE id = ?')
62
+ .bind(id)
63
+ .first();
64
+ if (!row)
65
+ return undefined;
66
+ return {
67
+ accountId: row.account_id,
68
+ ownerUserId: row.owner_user_id,
69
+ accessMode: row.access_mode === 'restricted' ? 'restricted' : 'account',
70
+ };
71
+ }
72
+ async setAccessMode(id, mode) {
73
+ await this.db.prepare('UPDATE workspaces SET access_mode = ? WHERE id = ?').bind(mode, id).run();
74
+ }
59
75
  async create(workspace, ownerUserId, accountId) {
60
76
  await this.db
61
77
  .prepare('INSERT INTO workspaces (id, name, description, created_at, owner_user_id, account_id) VALUES (?, ?, ?, ?, ?, ?)')
@@ -1 +1 @@
1
- {"version":3,"file":"D1WorkspaceRepository.js","sourceRoot":"","sources":["../../../src/infrastructure/repositories/D1WorkspaceRepository.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"D1WorkspaceRepository.js","sourceRoot":"","sources":["../../../src/infrastructure/repositories/D1WorkspaceRepository.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,22 @@
1
+ -- Workspace-level RBAC & membership (see docs/initiatives/workspace-rbac.md). The tier BELOW
2
+ -- account tenancy: an account admin can restrict a board to an explicit member roster with
3
+ -- per-member workspace roles. Mirrors the Node/Drizzle `workspace_members` table + the
4
+ -- `workspaces.access_mode` column (migration 20260716150654_fast_dracula) — keep the runtimes
5
+ -- symmetric. D1 does not enforce foreign keys, so the workspace-delete cascade
6
+ -- (WORKSPACE_SCOPED_TABLES lists `workspace_members`) is what reclaims a deleted board's roster.
7
+
8
+ -- Access mode: 'account' (default — every account member sees the board, the legacy behaviour)
9
+ -- or 'restricted' (only the explicit member roster). The default means zero change to existing rows.
10
+ ALTER TABLE workspaces ADD COLUMN access_mode TEXT NOT NULL DEFAULT 'account';
11
+
12
+ CREATE TABLE workspace_members (
13
+ workspace_id TEXT NOT NULL, -- the board this membership scopes
14
+ user_id TEXT NOT NULL, -- the internal users(id)
15
+ role TEXT NOT NULL, -- single value: admin | member | viewer (strict hierarchy)
16
+ created_at INTEGER NOT NULL,
17
+ added_by_user_id TEXT, -- audit: who granted; null for system grants (creator auto-enroll)
18
+ PRIMARY KEY (workspace_id, user_id)
19
+ );
20
+
21
+ -- Drives listWorkspaceIdsForUser + the workspace-list visibility subquery.
22
+ CREATE INDEX idx_workspace_members_user ON workspace_members (user_id);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@cat-factory/worker",
3
- "version": "0.86.0",
3
+ "version": "0.86.1",
4
4
  "description": "Reusable Cloudflare Worker library (Hono + D1) exposing the Agent Architecture Board core: the `createApp()` Hono factory, the default fetch/scheduled/queue handler, and the Durable Object + Workflow classes. Deployments (see deploy/backend) supply the wrangler.toml + config and re-export these.",
5
5
  "repository": {
6
6
  "type": "git",
@@ -42,22 +42,22 @@
42
42
  "pino": "^10.3.1",
43
43
  "valibot": "^1.4.2",
44
44
  "workers-ai-provider": "^3.3.1",
45
- "@cat-factory/agents": "0.61.0",
46
- "@cat-factory/caching": "0.9.0",
47
- "@cat-factory/contracts": "0.137.0",
48
- "@cat-factory/eks": "0.1.85",
49
- "@cat-factory/consensus": "0.10.58",
50
- "@cat-factory/gates": "0.5.42",
51
- "@cat-factory/gitlab": "0.10.4",
52
- "@cat-factory/integrations": "0.84.7",
53
- "@cat-factory/kernel": "0.131.0",
54
- "@cat-factory/observability-langfuse": "0.7.212",
55
- "@cat-factory/orchestration": "0.115.0",
56
- "@cat-factory/observability-otel": "0.1.6",
57
- "@cat-factory/prompt-fragments": "0.13.26",
58
- "@cat-factory/provider-cloudflare": "0.7.229",
59
- "@cat-factory/server": "0.127.0",
60
- "@cat-factory/spend": "0.12.38"
45
+ "@cat-factory/agents": "0.61.1",
46
+ "@cat-factory/caching": "0.9.1",
47
+ "@cat-factory/consensus": "0.10.59",
48
+ "@cat-factory/contracts": "0.138.0",
49
+ "@cat-factory/eks": "0.1.86",
50
+ "@cat-factory/gates": "0.5.43",
51
+ "@cat-factory/gitlab": "0.10.5",
52
+ "@cat-factory/integrations": "0.84.8",
53
+ "@cat-factory/kernel": "0.132.0",
54
+ "@cat-factory/observability-langfuse": "0.7.213",
55
+ "@cat-factory/observability-otel": "0.1.7",
56
+ "@cat-factory/orchestration": "0.115.1",
57
+ "@cat-factory/prompt-fragments": "0.13.27",
58
+ "@cat-factory/provider-cloudflare": "0.7.230",
59
+ "@cat-factory/server": "0.127.1",
60
+ "@cat-factory/spend": "0.12.39"
61
61
  },
62
62
  "devDependencies": {
63
63
  "@cloudflare/vitest-pool-workers": "^0.18.0",
@@ -65,7 +65,7 @@
65
65
  "typescript": "7.0.2",
66
66
  "vitest": "^4.1.10",
67
67
  "wrangler": "^4.110.0",
68
- "@cat-factory/conformance": "0.11.1"
68
+ "@cat-factory/conformance": "0.11.2"
69
69
  },
70
70
  "scripts": {
71
71
  "build": "tsc -b tsconfig.build.json",