@selvajs/supabase-provider 0.11.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.
Files changed (173) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +271 -0
  3. package/dist/auth/SupabaseAuthProvider.d.ts +81 -0
  4. package/dist/auth/SupabaseAuthProvider.d.ts.map +1 -0
  5. package/dist/auth/SupabaseAuthProvider.js +383 -0
  6. package/dist/auth/SupabaseAuthProvider.js.map +1 -0
  7. package/dist/auth/__tests__/conformance.test.d.ts +2 -0
  8. package/dist/auth/__tests__/conformance.test.d.ts.map +1 -0
  9. package/dist/auth/__tests__/conformance.test.js +76 -0
  10. package/dist/auth/__tests__/conformance.test.js.map +1 -0
  11. package/dist/auth/index.d.ts +3 -0
  12. package/dist/auth/index.d.ts.map +1 -0
  13. package/dist/auth/index.js +2 -0
  14. package/dist/auth/index.js.map +1 -0
  15. package/dist/data/SupabaseAuditQuery.d.ts +16 -0
  16. package/dist/data/SupabaseAuditQuery.d.ts.map +1 -0
  17. package/dist/data/SupabaseAuditQuery.js +83 -0
  18. package/dist/data/SupabaseAuditQuery.js.map +1 -0
  19. package/dist/data/SupabaseComputeServerStore.d.ts +26 -0
  20. package/dist/data/SupabaseComputeServerStore.d.ts.map +1 -0
  21. package/dist/data/SupabaseComputeServerStore.js +227 -0
  22. package/dist/data/SupabaseComputeServerStore.js.map +1 -0
  23. package/dist/data/SupabaseDataProvider.d.ts +55 -0
  24. package/dist/data/SupabaseDataProvider.d.ts.map +1 -0
  25. package/dist/data/SupabaseDataProvider.js +114 -0
  26. package/dist/data/SupabaseDataProvider.js.map +1 -0
  27. package/dist/data/SupabaseDefinitionStore.d.ts +39 -0
  28. package/dist/data/SupabaseDefinitionStore.d.ts.map +1 -0
  29. package/dist/data/SupabaseDefinitionStore.js +419 -0
  30. package/dist/data/SupabaseDefinitionStore.js.map +1 -0
  31. package/dist/data/SupabaseEventSink.d.ts +17 -0
  32. package/dist/data/SupabaseEventSink.d.ts.map +1 -0
  33. package/dist/data/SupabaseEventSink.js +31 -0
  34. package/dist/data/SupabaseEventSink.js.map +1 -0
  35. package/dist/data/SupabaseInviteStore.d.ts +22 -0
  36. package/dist/data/SupabaseInviteStore.d.ts.map +1 -0
  37. package/dist/data/SupabaseInviteStore.js +159 -0
  38. package/dist/data/SupabaseInviteStore.js.map +1 -0
  39. package/dist/data/SupabaseOrgStore.d.ts +33 -0
  40. package/dist/data/SupabaseOrgStore.d.ts.map +1 -0
  41. package/dist/data/SupabaseOrgStore.js +455 -0
  42. package/dist/data/SupabaseOrgStore.js.map +1 -0
  43. package/dist/data/SupabaseProjectStore.d.ts +29 -0
  44. package/dist/data/SupabaseProjectStore.d.ts.map +1 -0
  45. package/dist/data/SupabaseProjectStore.js +328 -0
  46. package/dist/data/SupabaseProjectStore.js.map +1 -0
  47. package/dist/data/SupabaseShareLinkStore.d.ts +26 -0
  48. package/dist/data/SupabaseShareLinkStore.d.ts.map +1 -0
  49. package/dist/data/SupabaseShareLinkStore.js +150 -0
  50. package/dist/data/SupabaseShareLinkStore.js.map +1 -0
  51. package/dist/data/__tests__/compute-server-conformance.test.d.ts +2 -0
  52. package/dist/data/__tests__/compute-server-conformance.test.d.ts.map +1 -0
  53. package/dist/data/__tests__/compute-server-conformance.test.js +40 -0
  54. package/dist/data/__tests__/compute-server-conformance.test.js.map +1 -0
  55. package/dist/data/__tests__/definition-conformance.test.d.ts +2 -0
  56. package/dist/data/__tests__/definition-conformance.test.d.ts.map +1 -0
  57. package/dist/data/__tests__/definition-conformance.test.js +85 -0
  58. package/dist/data/__tests__/definition-conformance.test.js.map +1 -0
  59. package/dist/data/__tests__/event-sink-conformance.test.d.ts +2 -0
  60. package/dist/data/__tests__/event-sink-conformance.test.d.ts.map +1 -0
  61. package/dist/data/__tests__/event-sink-conformance.test.js +27 -0
  62. package/dist/data/__tests__/event-sink-conformance.test.js.map +1 -0
  63. package/dist/data/__tests__/invite-conformance.test.d.ts +2 -0
  64. package/dist/data/__tests__/invite-conformance.test.d.ts.map +1 -0
  65. package/dist/data/__tests__/invite-conformance.test.js +45 -0
  66. package/dist/data/__tests__/invite-conformance.test.js.map +1 -0
  67. package/dist/data/__tests__/org-conformance.test.d.ts +2 -0
  68. package/dist/data/__tests__/org-conformance.test.d.ts.map +1 -0
  69. package/dist/data/__tests__/org-conformance.test.js +29 -0
  70. package/dist/data/__tests__/org-conformance.test.js.map +1 -0
  71. package/dist/data/__tests__/project-conformance.test.d.ts +2 -0
  72. package/dist/data/__tests__/project-conformance.test.d.ts.map +1 -0
  73. package/dist/data/__tests__/project-conformance.test.js +57 -0
  74. package/dist/data/__tests__/project-conformance.test.js.map +1 -0
  75. package/dist/data/__tests__/share-link-conformance.test.d.ts +2 -0
  76. package/dist/data/__tests__/share-link-conformance.test.d.ts.map +1 -0
  77. package/dist/data/__tests__/share-link-conformance.test.js +88 -0
  78. package/dist/data/__tests__/share-link-conformance.test.js.map +1 -0
  79. package/dist/data/__tests__/test-helpers.d.ts +53 -0
  80. package/dist/data/__tests__/test-helpers.d.ts.map +1 -0
  81. package/dist/data/__tests__/test-helpers.js +175 -0
  82. package/dist/data/__tests__/test-helpers.js.map +1 -0
  83. package/dist/data/client.d.ts +44 -0
  84. package/dist/data/client.d.ts.map +1 -0
  85. package/dist/data/client.js +40 -0
  86. package/dist/data/client.js.map +1 -0
  87. package/dist/data/index.d.ts +12 -0
  88. package/dist/data/index.d.ts.map +1 -0
  89. package/dist/data/index.js +11 -0
  90. package/dist/data/index.js.map +1 -0
  91. package/dist/data/pagination.d.ts +30 -0
  92. package/dist/data/pagination.d.ts.map +1 -0
  93. package/dist/data/pagination.js +53 -0
  94. package/dist/data/pagination.js.map +1 -0
  95. package/dist/index.d.ts +9 -0
  96. package/dist/index.d.ts.map +1 -0
  97. package/dist/index.js +6 -0
  98. package/dist/index.js.map +1 -0
  99. package/dist/permissions/SupabasePlatformPermissionStore.d.ts +25 -0
  100. package/dist/permissions/SupabasePlatformPermissionStore.d.ts.map +1 -0
  101. package/dist/permissions/SupabasePlatformPermissionStore.js +153 -0
  102. package/dist/permissions/SupabasePlatformPermissionStore.js.map +1 -0
  103. package/dist/permissions/__tests__/conformance.test.d.ts +2 -0
  104. package/dist/permissions/__tests__/conformance.test.d.ts.map +1 -0
  105. package/dist/permissions/__tests__/conformance.test.js +27 -0
  106. package/dist/permissions/__tests__/conformance.test.js.map +1 -0
  107. package/dist/permissions/index.d.ts +2 -0
  108. package/dist/permissions/index.d.ts.map +1 -0
  109. package/dist/permissions/index.js +2 -0
  110. package/dist/permissions/index.js.map +1 -0
  111. package/dist/storage/SupabaseStorageProvider.d.ts +67 -0
  112. package/dist/storage/SupabaseStorageProvider.d.ts.map +1 -0
  113. package/dist/storage/SupabaseStorageProvider.js +136 -0
  114. package/dist/storage/SupabaseStorageProvider.js.map +1 -0
  115. package/dist/storage/__tests__/conformance.test.d.ts +2 -0
  116. package/dist/storage/__tests__/conformance.test.d.ts.map +1 -0
  117. package/dist/storage/__tests__/conformance.test.js +149 -0
  118. package/dist/storage/__tests__/conformance.test.js.map +1 -0
  119. package/dist/storage/index.d.ts +3 -0
  120. package/dist/storage/index.d.ts.map +1 -0
  121. package/dist/storage/index.js +2 -0
  122. package/dist/storage/index.js.map +1 -0
  123. package/dist/userProfile/SupabaseUserProfileProvider.d.ts +16 -0
  124. package/dist/userProfile/SupabaseUserProfileProvider.d.ts.map +1 -0
  125. package/dist/userProfile/SupabaseUserProfileProvider.js +148 -0
  126. package/dist/userProfile/SupabaseUserProfileProvider.js.map +1 -0
  127. package/dist/userProfile/__tests__/conformance.test.d.ts +2 -0
  128. package/dist/userProfile/__tests__/conformance.test.d.ts.map +1 -0
  129. package/dist/userProfile/__tests__/conformance.test.js +38 -0
  130. package/dist/userProfile/__tests__/conformance.test.js.map +1 -0
  131. package/dist/userProfile/index.d.ts +2 -0
  132. package/dist/userProfile/index.d.ts.map +1 -0
  133. package/dist/userProfile/index.js +2 -0
  134. package/dist/userProfile/index.js.map +1 -0
  135. package/package.json +75 -0
  136. package/src/auth/SupabaseAuthProvider.ts +464 -0
  137. package/src/auth/__tests__/conformance.test.ts +78 -0
  138. package/src/auth/index.ts +2 -0
  139. package/src/data/SupabaseAuditQuery.ts +103 -0
  140. package/src/data/SupabaseComputeServerStore.ts +262 -0
  141. package/src/data/SupabaseDataProvider.ts +125 -0
  142. package/src/data/SupabaseDefinitionStore.ts +504 -0
  143. package/src/data/SupabaseEventSink.ts +30 -0
  144. package/src/data/SupabaseInviteStore.ts +183 -0
  145. package/src/data/SupabaseOrgStore.ts +547 -0
  146. package/src/data/SupabaseProjectStore.ts +414 -0
  147. package/src/data/SupabaseShareLinkStore.ts +191 -0
  148. package/src/data/__tests__/compute-server-conformance.test.ts +40 -0
  149. package/src/data/__tests__/definition-conformance.test.ts +89 -0
  150. package/src/data/__tests__/event-sink-conformance.test.ts +32 -0
  151. package/src/data/__tests__/invite-conformance.test.ts +46 -0
  152. package/src/data/__tests__/org-conformance.test.ts +30 -0
  153. package/src/data/__tests__/project-conformance.test.ts +57 -0
  154. package/src/data/__tests__/share-link-conformance.test.ts +87 -0
  155. package/src/data/__tests__/test-helpers.ts +186 -0
  156. package/src/data/client.ts +86 -0
  157. package/src/data/index.ts +11 -0
  158. package/src/data/pagination.ts +68 -0
  159. package/src/index.ts +23 -0
  160. package/src/permissions/SupabasePlatformPermissionStore.ts +161 -0
  161. package/src/permissions/__tests__/conformance.test.ts +28 -0
  162. package/src/permissions/index.ts +1 -0
  163. package/src/storage/SupabaseStorageProvider.ts +177 -0
  164. package/src/storage/__tests__/conformance.test.ts +152 -0
  165. package/src/storage/index.ts +2 -0
  166. package/src/userProfile/SupabaseUserProfileProvider.ts +177 -0
  167. package/src/userProfile/__tests__/conformance.test.ts +39 -0
  168. package/src/userProfile/index.ts +1 -0
  169. package/supabase/.branches/_current_branch +1 -0
  170. package/supabase/.temp/cli-latest +1 -0
  171. package/supabase/config.toml +68 -0
  172. package/supabase/migrations/0001_initial.sql +1084 -0
  173. package/supabase/seed.sql +13 -0
@@ -0,0 +1,175 @@
1
+ /**
2
+ * Shared test helpers for Supabase data conformance tests.
3
+ *
4
+ * Every suite starts with a fully wiped DB so tests are isolated. We use the
5
+ * service-role client for both — seeding users in `auth.users` and wiping
6
+ * every relevant table.
7
+ */
8
+ import { createClient } from '@supabase/supabase-js';
9
+ import { buildClientBundle } from '../client.js';
10
+ export function readEnv() {
11
+ const url = process.env.SUPABASE_URL;
12
+ const anonKey = process.env.SUPABASE_ANON_KEY;
13
+ const serviceRoleKey = process.env.SUPABASE_SERVICE_ROLE_KEY;
14
+ if (!url || !anonKey || !serviceRoleKey)
15
+ return null;
16
+ // `.env.test` is checked in with local-Supabase defaults so contributors can
17
+ // `npx supabase start` and run the suite. But `createClient` transitively
18
+ // loads `@supabase/realtime-js`, which on Node < 22 throws at construction
19
+ // without a native WebSocket. Swallow that so the suite cleanly skips
20
+ // instead of crashing test collection.
21
+ let adminClient;
22
+ try {
23
+ adminClient = createClient(url, serviceRoleKey, {
24
+ auth: { persistSession: false, autoRefreshToken: false }
25
+ });
26
+ }
27
+ catch (err) {
28
+ const msg = err instanceof Error ? err.message : String(err);
29
+ if (msg.includes('WebSocket'))
30
+ return null;
31
+ throw err;
32
+ }
33
+ const bundle = buildClientBundle({ supabaseUrl: url, anonKey, serviceRoleKey });
34
+ return { url, anonKey, serviceRoleKey, adminClient, bundle };
35
+ }
36
+ /**
37
+ * Reset every data table this adapter owns. Leaves Supabase-managed tables
38
+ * (`auth.users`, etc.) alone except via `deleteAllAuthUsers` below.
39
+ *
40
+ * Order-sensitive because some FKs don't cascade: we go bottom up from
41
+ * dependents to parents.
42
+ */
43
+ export async function resetAllData(ctx) {
44
+ await truncate(ctx, 'share_links');
45
+ await truncate(ctx, 'invites');
46
+ // Versions FK to definitions ON DELETE CASCADE, but `definitions` can't
47
+ // be wiped while live/draft pointers reference versions (ON DELETE
48
+ // RESTRICT, spec §6). Null the pointers, drop versions, then drop defs.
49
+ await ctx.adminClient
50
+ .from('definitions')
51
+ .update({ live_version_id: null, draft_version_id: null })
52
+ .not('guid', 'is', null);
53
+ await truncate(ctx, 'definition_versions');
54
+ await truncate(ctx, 'definitions');
55
+ await truncate(ctx, 'project_members');
56
+ // compute defaults have a platform_default sibling — reset all three.
57
+ await truncate(ctx, 'compute_server_org_defaults');
58
+ await truncate(ctx, 'compute_server_shares');
59
+ await resetComputePlatformDefault(ctx);
60
+ await truncate(ctx, 'compute_servers');
61
+ await truncate(ctx, 'org_members');
62
+ await truncate(ctx, 'orgs');
63
+ await truncate(ctx, 'user_profiles');
64
+ await deleteAllAuthUsers(ctx);
65
+ }
66
+ async function resetComputePlatformDefault(ctx) {
67
+ // Singleton row — clear `default_server_id` rather than deleting.
68
+ const { error } = await ctx.adminClient
69
+ .from('compute_server_platform_default')
70
+ .update({ default_server_id: null })
71
+ .eq('singleton', true);
72
+ if (error)
73
+ throw error;
74
+ }
75
+ async function truncate(ctx, table) {
76
+ const { error } = await ctx.adminClient
77
+ .from(table)
78
+ .delete()
79
+ .neq(columnForDeleteAll(table), '00000000-0000-0000-0000-000000000000');
80
+ if (error)
81
+ throw error;
82
+ }
83
+ function columnForDeleteAll(table) {
84
+ if (table === 'org_members')
85
+ return 'user_id';
86
+ if (table === 'project_members')
87
+ return 'user_id';
88
+ if (table === 'user_profiles')
89
+ return 'user_id';
90
+ if (table === 'definitions')
91
+ return 'guid';
92
+ if (table === 'definition_versions')
93
+ return 'id';
94
+ if (table === 'compute_server_org_defaults')
95
+ return 'org_id';
96
+ if (table === 'compute_server_shares')
97
+ return 'server_id';
98
+ return 'id';
99
+ }
100
+ async function deleteAllAuthUsers(ctx) {
101
+ const { data, error } = await ctx.adminClient.auth.admin.listUsers({ perPage: 1000 });
102
+ if (error)
103
+ throw error;
104
+ for (const user of data.users) {
105
+ const { error: delError } = await ctx.adminClient.auth.admin.deleteUser(user.id);
106
+ if (delError)
107
+ throw delError;
108
+ }
109
+ }
110
+ /**
111
+ * Seed an `auth.users` row, mark the user as `instance_admin`, sign in, and
112
+ * return the real id + access token. `auth.admin.createUser` doesn't accept a
113
+ * caller-supplied id — Supabase generates one. The conformance suite calls us
114
+ * with a *suggested* id (for adapters that honor it); we ignore it and return
115
+ * GoTrue's real id.
116
+ *
117
+ * The instance_admin grant is what makes RLS open up for the conformance
118
+ * tests: every policy in the schema accepts `is_instance_admin()` as a
119
+ * universal pass, mirroring the `instance_admin` default in `makeCtx`.
120
+ *
121
+ * The session token is what makes RLS *see* the user at all. Without it, the
122
+ * Supabase client falls back to the anon role and every write fails.
123
+ */
124
+ export async function seedUser(ctx, suggestedId) {
125
+ return seedUserCore(ctx, suggestedId, { promoteToInstanceAdmin: true });
126
+ }
127
+ /**
128
+ * Variant of `seedUser` that leaves `platform_permissions` empty. Use this
129
+ * when a test specifically asserts on a fresh user's permission state (e.g.
130
+ * the platform-permission store conformance suite).
131
+ */
132
+ export async function seedPlainUser(ctx, suggestedId) {
133
+ return seedUserCore(ctx, suggestedId, { promoteToInstanceAdmin: false });
134
+ }
135
+ async function seedUserCore(ctx, _suggestedId, opts) {
136
+ // Unique email per seed so repeated calls don't collide. GoTrue requires
137
+ // an email even for password-less users.
138
+ const email = `conformance-${crypto.randomUUID()}@conformance.test`;
139
+ const password = 'conformance-test-password-1234';
140
+ const { data, error } = await ctx.adminClient.auth.admin.createUser({
141
+ email,
142
+ password,
143
+ email_confirm: true
144
+ });
145
+ if (error)
146
+ throw error;
147
+ const userId = data.user.id;
148
+ if (opts.promoteToInstanceAdmin) {
149
+ // Trigger auto-created the user_profiles row; promote to instance_admin
150
+ // so every RLS policy treats this user as fully authorized. Mirrors the
151
+ // `instance_admin` default in `makeCtx`.
152
+ const { error: promoteError } = await ctx.adminClient
153
+ .from('user_profiles')
154
+ .update({ platform_permissions: ['instance_admin'] })
155
+ .eq('user_id', userId);
156
+ if (promoteError)
157
+ throw promoteError;
158
+ }
159
+ // Sign in to get an access token. The conformance suite stuffs this into
160
+ // `adapterContext.sessionToken` and our client.ts uses it to scope the
161
+ // request to this user instead of falling back to anon.
162
+ const signInClient = createClient(ctx.url, ctx.anonKey, {
163
+ auth: { persistSession: false, autoRefreshToken: false }
164
+ });
165
+ const { data: session, error: signInError } = await signInClient.auth.signInWithPassword({
166
+ email,
167
+ password
168
+ });
169
+ if (signInError)
170
+ throw signInError;
171
+ if (!session.session)
172
+ throw new Error('seedUser: signInWithPassword returned no session');
173
+ return { userId, sessionToken: session.session.access_token };
174
+ }
175
+ //# sourceMappingURL=test-helpers.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"test-helpers.js","sourceRoot":"","sources":["../../../src/data/__tests__/test-helpers.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,OAAO,EAAE,YAAY,EAAuB,MAAM,uBAAuB,CAAC;AAC1E,OAAO,EAAE,iBAAiB,EAAqB,MAAM,cAAc,CAAC;AAUpE,MAAM,UAAU,OAAO;IACtB,MAAM,GAAG,GAAG,OAAO,CAAC,GAAG,CAAC,YAAY,CAAC;IACrC,MAAM,OAAO,GAAG,OAAO,CAAC,GAAG,CAAC,iBAAiB,CAAC;IAC9C,MAAM,cAAc,GAAG,OAAO,CAAC,GAAG,CAAC,yBAAyB,CAAC;IAC7D,IAAI,CAAC,GAAG,IAAI,CAAC,OAAO,IAAI,CAAC,cAAc;QAAE,OAAO,IAAI,CAAC;IACrD,6EAA6E;IAC7E,0EAA0E;IAC1E,2EAA2E;IAC3E,sEAAsE;IACtE,uCAAuC;IACvC,IAAI,WAA2B,CAAC;IAChC,IAAI,CAAC;QACJ,WAAW,GAAG,YAAY,CAAC,GAAG,EAAE,cAAc,EAAE;YAC/C,IAAI,EAAE,EAAE,cAAc,EAAE,KAAK,EAAE,gBAAgB,EAAE,KAAK,EAAE;SACxD,CAAC,CAAC;IACJ,CAAC;IAAC,OAAO,GAAG,EAAE,CAAC;QACd,MAAM,GAAG,GAAG,GAAG,YAAY,KAAK,CAAC,CAAC,CAAC,GAAG,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC;QAC7D,IAAI,GAAG,CAAC,QAAQ,CAAC,WAAW,CAAC;YAAE,OAAO,IAAI,CAAC;QAC3C,MAAM,GAAG,CAAC;IACX,CAAC;IACD,MAAM,MAAM,GAAG,iBAAiB,CAAC,EAAE,WAAW,EAAE,GAAG,EAAE,OAAO,EAAE,cAAc,EAAE,CAAC,CAAC;IAChF,OAAO,EAAE,GAAG,EAAE,OAAO,EAAE,cAAc,EAAE,WAAW,EAAE,MAAM,EAAE,CAAC;AAC9D,CAAC;AAED;;;;;;GAMG;AACH,MAAM,CAAC,KAAK,UAAU,YAAY,CAAC,GAAgB;IAClD,MAAM,QAAQ,CAAC,GAAG,EAAE,aAAa,CAAC,CAAC;IACnC,MAAM,QAAQ,CAAC,GAAG,EAAE,SAAS,CAAC,CAAC;IAC/B,wEAAwE;IACxE,mEAAmE;IACnE,wEAAwE;IACxE,MAAM,GAAG,CAAC,WAAW;SACnB,IAAI,CAAC,aAAa,CAAC;SACnB,MAAM,CAAC,EAAE,eAAe,EAAE,IAAI,EAAE,gBAAgB,EAAE,IAAI,EAAE,CAAC;SACzD,GAAG,CAAC,MAAM,EAAE,IAAI,EAAE,IAAI,CAAC,CAAC;IAC1B,MAAM,QAAQ,CAAC,GAAG,EAAE,qBAAqB,CAAC,CAAC;IAC3C,MAAM,QAAQ,CAAC,GAAG,EAAE,aAAa,CAAC,CAAC;IACnC,MAAM,QAAQ,CAAC,GAAG,EAAE,iBAAiB,CAAC,CAAC;IACvC,sEAAsE;IACtE,MAAM,QAAQ,CAAC,GAAG,EAAE,6BAA6B,CAAC,CAAC;IACnD,MAAM,QAAQ,CAAC,GAAG,EAAE,uBAAuB,CAAC,CAAC;IAC7C,MAAM,2BAA2B,CAAC,GAAG,CAAC,CAAC;IACvC,MAAM,QAAQ,CAAC,GAAG,EAAE,iBAAiB,CAAC,CAAC;IACvC,MAAM,QAAQ,CAAC,GAAG,EAAE,aAAa,CAAC,CAAC;IACnC,MAAM,QAAQ,CAAC,GAAG,EAAE,MAAM,CAAC,CAAC;IAC5B,MAAM,QAAQ,CAAC,GAAG,EAAE,eAAe,CAAC,CAAC;IACrC,MAAM,kBAAkB,CAAC,GAAG,CAAC,CAAC;AAC/B,CAAC;AAED,KAAK,UAAU,2BAA2B,CAAC,GAAgB;IAC1D,kEAAkE;IAClE,MAAM,EAAE,KAAK,EAAE,GAAG,MAAM,GAAG,CAAC,WAAW;SACrC,IAAI,CAAC,iCAAiC,CAAC;SACvC,MAAM,CAAC,EAAE,iBAAiB,EAAE,IAAI,EAAE,CAAC;SACnC,EAAE,CAAC,WAAW,EAAE,IAAI,CAAC,CAAC;IACxB,IAAI,KAAK;QAAE,MAAM,KAAK,CAAC;AACxB,CAAC;AAED,KAAK,UAAU,QAAQ,CAAC,GAAgB,EAAE,KAAa;IACtD,MAAM,EAAE,KAAK,EAAE,GAAG,MAAM,GAAG,CAAC,WAAW;SACrC,IAAI,CAAC,KAAK,CAAC;SACX,MAAM,EAAE;SACR,GAAG,CAAC,kBAAkB,CAAC,KAAK,CAAC,EAAE,sCAAsC,CAAC,CAAC;IACzE,IAAI,KAAK;QAAE,MAAM,KAAK,CAAC;AACxB,CAAC;AAED,SAAS,kBAAkB,CAAC,KAAa;IACxC,IAAI,KAAK,KAAK,aAAa;QAAE,OAAO,SAAS,CAAC;IAC9C,IAAI,KAAK,KAAK,iBAAiB;QAAE,OAAO,SAAS,CAAC;IAClD,IAAI,KAAK,KAAK,eAAe;QAAE,OAAO,SAAS,CAAC;IAChD,IAAI,KAAK,KAAK,aAAa;QAAE,OAAO,MAAM,CAAC;IAC3C,IAAI,KAAK,KAAK,qBAAqB;QAAE,OAAO,IAAI,CAAC;IACjD,IAAI,KAAK,KAAK,6BAA6B;QAAE,OAAO,QAAQ,CAAC;IAC7D,IAAI,KAAK,KAAK,uBAAuB;QAAE,OAAO,WAAW,CAAC;IAC1D,OAAO,IAAI,CAAC;AACb,CAAC;AAED,KAAK,UAAU,kBAAkB,CAAC,GAAgB;IACjD,MAAM,EAAE,IAAI,EAAE,KAAK,EAAE,GAAG,MAAM,GAAG,CAAC,WAAW,CAAC,IAAI,CAAC,KAAK,CAAC,SAAS,CAAC,EAAE,OAAO,EAAE,IAAI,EAAE,CAAC,CAAC;IACtF,IAAI,KAAK;QAAE,MAAM,KAAK,CAAC;IACvB,KAAK,MAAM,IAAI,IAAI,IAAI,CAAC,KAAK,EAAE,CAAC;QAC/B,MAAM,EAAE,KAAK,EAAE,QAAQ,EAAE,GAAG,MAAM,GAAG,CAAC,WAAW,CAAC,IAAI,CAAC,KAAK,CAAC,UAAU,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;QACjF,IAAI,QAAQ;YAAE,MAAM,QAAQ,CAAC;IAC9B,CAAC;AACF,CAAC;AAED;;;;;;;;;;;;;GAaG;AACH,MAAM,CAAC,KAAK,UAAU,QAAQ,CAC7B,GAAgB,EAChB,WAAmB;IAEnB,OAAO,YAAY,CAAC,GAAG,EAAE,WAAW,EAAE,EAAE,sBAAsB,EAAE,IAAI,EAAE,CAAC,CAAC;AACzE,CAAC;AAED;;;;GAIG;AACH,MAAM,CAAC,KAAK,UAAU,aAAa,CAClC,GAAgB,EAChB,WAAmB;IAEnB,OAAO,YAAY,CAAC,GAAG,EAAE,WAAW,EAAE,EAAE,sBAAsB,EAAE,KAAK,EAAE,CAAC,CAAC;AAC1E,CAAC;AAED,KAAK,UAAU,YAAY,CAC1B,GAAgB,EAChB,YAAoB,EACpB,IAAyC;IAEzC,yEAAyE;IACzE,yCAAyC;IACzC,MAAM,KAAK,GAAG,eAAe,MAAM,CAAC,UAAU,EAAE,mBAAmB,CAAC;IACpE,MAAM,QAAQ,GAAG,gCAAgC,CAAC;IAClD,MAAM,EAAE,IAAI,EAAE,KAAK,EAAE,GAAG,MAAM,GAAG,CAAC,WAAW,CAAC,IAAI,CAAC,KAAK,CAAC,UAAU,CAAC;QACnE,KAAK;QACL,QAAQ;QACR,aAAa,EAAE,IAAI;KACnB,CAAC,CAAC;IACH,IAAI,KAAK;QAAE,MAAM,KAAK,CAAC;IACvB,MAAM,MAAM,GAAG,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC;IAE5B,IAAI,IAAI,CAAC,sBAAsB,EAAE,CAAC;QACjC,wEAAwE;QACxE,wEAAwE;QACxE,yCAAyC;QACzC,MAAM,EAAE,KAAK,EAAE,YAAY,EAAE,GAAG,MAAM,GAAG,CAAC,WAAW;aACnD,IAAI,CAAC,eAAe,CAAC;aACrB,MAAM,CAAC,EAAE,oBAAoB,EAAE,CAAC,gBAAgB,CAAC,EAAE,CAAC;aACpD,EAAE,CAAC,SAAS,EAAE,MAAM,CAAC,CAAC;QACxB,IAAI,YAAY;YAAE,MAAM,YAAY,CAAC;IACtC,CAAC;IAED,yEAAyE;IACzE,uEAAuE;IACvE,wDAAwD;IACxD,MAAM,YAAY,GAAG,YAAY,CAAC,GAAG,CAAC,GAAG,EAAE,GAAG,CAAC,OAAO,EAAE;QACvD,IAAI,EAAE,EAAE,cAAc,EAAE,KAAK,EAAE,gBAAgB,EAAE,KAAK,EAAE;KACxD,CAAC,CAAC;IACH,MAAM,EAAE,IAAI,EAAE,OAAO,EAAE,KAAK,EAAE,WAAW,EAAE,GAAG,MAAM,YAAY,CAAC,IAAI,CAAC,kBAAkB,CAAC;QACxF,KAAK;QACL,QAAQ;KACR,CAAC,CAAC;IACH,IAAI,WAAW;QAAE,MAAM,WAAW,CAAC;IACnC,IAAI,CAAC,OAAO,CAAC,OAAO;QAAE,MAAM,IAAI,KAAK,CAAC,kDAAkD,CAAC,CAAC;IAC1F,OAAO,EAAE,MAAM,EAAE,YAAY,EAAE,OAAO,CAAC,OAAO,CAAC,YAAY,EAAE,CAAC;AAC/D,CAAC"}
@@ -0,0 +1,44 @@
1
+ import { type SupabaseClient } from '@supabase/supabase-js';
2
+ import type { RequestContext } from '@selvajs/platform';
3
+ /**
4
+ * Build a Supabase client for a given `RequestContext`.
5
+ *
6
+ * Three modes — fail-closed:
7
+ * - **Service-role** ONLY when `ctx.system === true`. Bypasses RLS. Used for
8
+ * admin paths, janitors, bootstrap, and any explicitly-trusted server
9
+ * flow. The system flag must never be derived from a user session.
10
+ * - **User-scoped** when `ctx.adapterContext.sessionToken` is a JWT: runs
11
+ * under `authenticated` role with `auth.uid()` from the token. RLS
12
+ * policies enforce per-user visibility.
13
+ * - **Anonymous** otherwise: runs under the `anon` role. RLS is active and
14
+ * will scope reads/writes accordingly. This is the safety net — any code
15
+ * that constructs a context without forwarding the session token AND
16
+ * without setting `system: true` is treated as untrusted.
17
+ *
18
+ * Previous versions fell back to service-role when the session token was
19
+ * absent — a fail-OPEN footgun: any synthetic ctx (e.g. share-token resolve)
20
+ * silently bypassed RLS. The current contract is explicit: opt into
21
+ * service-role with `system: true`, or you get RLS.
22
+ *
23
+ * Per-request WeakMap caching keeps a single client alive for the lifetime
24
+ * of a RequestContext — multiple store calls in one HTTP handler share one
25
+ * fetch connection without leaking auth across requests.
26
+ */
27
+ export interface ClientBundle {
28
+ /** Long-lived service-role client. Bypasses RLS. */
29
+ serviceClient: SupabaseClient;
30
+ /**
31
+ * Produce (or reuse) a client scoped to this request's identity.
32
+ * - `ctx.system === true` → service-role (RLS bypassed).
33
+ * - `ctx.adapterContext.sessionToken` set → user-scoped (RLS active).
34
+ * - neither → anon client (RLS active, no `auth.uid()`).
35
+ */
36
+ forRequest(ctx: RequestContext): SupabaseClient;
37
+ }
38
+ export interface BuildClientOptions {
39
+ supabaseUrl: string;
40
+ anonKey: string;
41
+ serviceRoleKey: string;
42
+ }
43
+ export declare function buildClientBundle(opts: BuildClientOptions): ClientBundle;
44
+ //# sourceMappingURL=client.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"client.d.ts","sourceRoot":"","sources":["../../src/data/client.ts"],"names":[],"mappings":"AAAA,OAAO,EAAgB,KAAK,cAAc,EAAE,MAAM,uBAAuB,CAAC;AAC1E,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,mBAAmB,CAAC;AAExD;;;;;;;;;;;;;;;;;;;;;;;GAuBG;AACH,MAAM,WAAW,YAAY;IAC5B,oDAAoD;IACpD,aAAa,EAAE,cAAc,CAAC;IAC9B;;;;;OAKG;IACH,UAAU,CAAC,GAAG,EAAE,cAAc,GAAG,cAAc,CAAC;CAChD;AAED,MAAM,WAAW,kBAAkB;IAClC,WAAW,EAAE,MAAM,CAAC;IACpB,OAAO,EAAE,MAAM,CAAC;IAChB,cAAc,EAAE,MAAM,CAAC;CACvB;AAED,wBAAgB,iBAAiB,CAAC,IAAI,EAAE,kBAAkB,GAAG,YAAY,CAkCxE"}
@@ -0,0 +1,40 @@
1
+ import { createClient } from '@supabase/supabase-js';
2
+ export function buildClientBundle(opts) {
3
+ const serviceClient = createClient(opts.supabaseUrl, opts.serviceRoleKey, {
4
+ auth: { persistSession: false, autoRefreshToken: false }
5
+ });
6
+ // Long-lived anon client — the fail-closed default for ctxes that aren't
7
+ // explicitly system and don't carry a session token.
8
+ const anonClient = createClient(opts.supabaseUrl, opts.anonKey, {
9
+ auth: { persistSession: false, autoRefreshToken: false }
10
+ });
11
+ const perRequestCache = new WeakMap();
12
+ return {
13
+ serviceClient,
14
+ forRequest(ctx) {
15
+ if (ctx.system)
16
+ return serviceClient;
17
+ const token = extractSessionToken(ctx.adapterContext);
18
+ if (!token)
19
+ return anonClient;
20
+ const cached = perRequestCache.get(ctx);
21
+ if (cached)
22
+ return cached;
23
+ const client = createClient(opts.supabaseUrl, opts.anonKey, {
24
+ auth: { persistSession: false, autoRefreshToken: false },
25
+ global: {
26
+ headers: { Authorization: `Bearer ${token}` }
27
+ }
28
+ });
29
+ perRequestCache.set(ctx, client);
30
+ return client;
31
+ }
32
+ };
33
+ }
34
+ function extractSessionToken(adapterContext) {
35
+ if (!adapterContext || typeof adapterContext !== 'object')
36
+ return undefined;
37
+ const maybe = adapterContext.sessionToken;
38
+ return typeof maybe === 'string' && maybe.length > 0 ? maybe : undefined;
39
+ }
40
+ //# sourceMappingURL=client.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"client.js","sourceRoot":"","sources":["../../src/data/client.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAuB,MAAM,uBAAuB,CAAC;AA6C1E,MAAM,UAAU,iBAAiB,CAAC,IAAwB;IACzD,MAAM,aAAa,GAAG,YAAY,CAAC,IAAI,CAAC,WAAW,EAAE,IAAI,CAAC,cAAc,EAAE;QACzE,IAAI,EAAE,EAAE,cAAc,EAAE,KAAK,EAAE,gBAAgB,EAAE,KAAK,EAAE;KACxD,CAAC,CAAC;IAEH,yEAAyE;IACzE,qDAAqD;IACrD,MAAM,UAAU,GAAG,YAAY,CAAC,IAAI,CAAC,WAAW,EAAE,IAAI,CAAC,OAAO,EAAE;QAC/D,IAAI,EAAE,EAAE,cAAc,EAAE,KAAK,EAAE,gBAAgB,EAAE,KAAK,EAAE;KACxD,CAAC,CAAC;IAEH,MAAM,eAAe,GAAG,IAAI,OAAO,EAAkC,CAAC;IAEtE,OAAO;QACN,aAAa;QACb,UAAU,CAAC,GAAmB;YAC7B,IAAI,GAAG,CAAC,MAAM;gBAAE,OAAO,aAAa,CAAC;YAErC,MAAM,KAAK,GAAG,mBAAmB,CAAC,GAAG,CAAC,cAAc,CAAC,CAAC;YACtD,IAAI,CAAC,KAAK;gBAAE,OAAO,UAAU,CAAC;YAE9B,MAAM,MAAM,GAAG,eAAe,CAAC,GAAG,CAAC,GAAG,CAAC,CAAC;YACxC,IAAI,MAAM;gBAAE,OAAO,MAAM,CAAC;YAE1B,MAAM,MAAM,GAAG,YAAY,CAAC,IAAI,CAAC,WAAW,EAAE,IAAI,CAAC,OAAO,EAAE;gBAC3D,IAAI,EAAE,EAAE,cAAc,EAAE,KAAK,EAAE,gBAAgB,EAAE,KAAK,EAAE;gBACxD,MAAM,EAAE;oBACP,OAAO,EAAE,EAAE,aAAa,EAAE,UAAU,KAAK,EAAE,EAAE;iBAC7C;aACD,CAAC,CAAC;YACH,eAAe,CAAC,GAAG,CAAC,GAAG,EAAE,MAAM,CAAC,CAAC;YACjC,OAAO,MAAM,CAAC;QACf,CAAC;KACD,CAAC;AACH,CAAC;AAED,SAAS,mBAAmB,CAAC,cAAuB;IACnD,IAAI,CAAC,cAAc,IAAI,OAAO,cAAc,KAAK,QAAQ;QAAE,OAAO,SAAS,CAAC;IAC5E,MAAM,KAAK,GAAI,cAA6C,CAAC,YAAY,CAAC;IAC1E,OAAO,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,SAAS,CAAC;AAC1E,CAAC"}
@@ -0,0 +1,12 @@
1
+ export { SupabaseOrgStore } from './SupabaseOrgStore.js';
2
+ export { SupabaseProjectStore } from './SupabaseProjectStore.js';
3
+ export { SupabaseDefinitionStore } from './SupabaseDefinitionStore.js';
4
+ export { SupabaseInviteStore } from './SupabaseInviteStore.js';
5
+ export { SupabaseComputeServerStore } from './SupabaseComputeServerStore.js';
6
+ export { SupabaseShareLinkStore } from './SupabaseShareLinkStore.js';
7
+ export { SupabaseDataProvider } from './SupabaseDataProvider.js';
8
+ export { SupabaseEventSink } from './SupabaseEventSink.js';
9
+ export { SupabaseAuditQuery } from './SupabaseAuditQuery.js';
10
+ export { buildClientBundle } from './client.js';
11
+ export type { ClientBundle, BuildClientOptions } from './client.js';
12
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/data/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,gBAAgB,EAAE,MAAM,uBAAuB,CAAC;AACzD,OAAO,EAAE,oBAAoB,EAAE,MAAM,2BAA2B,CAAC;AACjE,OAAO,EAAE,uBAAuB,EAAE,MAAM,8BAA8B,CAAC;AACvE,OAAO,EAAE,mBAAmB,EAAE,MAAM,0BAA0B,CAAC;AAC/D,OAAO,EAAE,0BAA0B,EAAE,MAAM,iCAAiC,CAAC;AAC7E,OAAO,EAAE,sBAAsB,EAAE,MAAM,6BAA6B,CAAC;AACrE,OAAO,EAAE,oBAAoB,EAAE,MAAM,2BAA2B,CAAC;AACjE,OAAO,EAAE,iBAAiB,EAAE,MAAM,wBAAwB,CAAC;AAC3D,OAAO,EAAE,kBAAkB,EAAE,MAAM,yBAAyB,CAAC;AAC7D,OAAO,EAAE,iBAAiB,EAAE,MAAM,aAAa,CAAC;AAChD,YAAY,EAAE,YAAY,EAAE,kBAAkB,EAAE,MAAM,aAAa,CAAC"}
@@ -0,0 +1,11 @@
1
+ export { SupabaseOrgStore } from './SupabaseOrgStore.js';
2
+ export { SupabaseProjectStore } from './SupabaseProjectStore.js';
3
+ export { SupabaseDefinitionStore } from './SupabaseDefinitionStore.js';
4
+ export { SupabaseInviteStore } from './SupabaseInviteStore.js';
5
+ export { SupabaseComputeServerStore } from './SupabaseComputeServerStore.js';
6
+ export { SupabaseShareLinkStore } from './SupabaseShareLinkStore.js';
7
+ export { SupabaseDataProvider } from './SupabaseDataProvider.js';
8
+ export { SupabaseEventSink } from './SupabaseEventSink.js';
9
+ export { SupabaseAuditQuery } from './SupabaseAuditQuery.js';
10
+ export { buildClientBundle } from './client.js';
11
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/data/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,gBAAgB,EAAE,MAAM,uBAAuB,CAAC;AACzD,OAAO,EAAE,oBAAoB,EAAE,MAAM,2BAA2B,CAAC;AACjE,OAAO,EAAE,uBAAuB,EAAE,MAAM,8BAA8B,CAAC;AACvE,OAAO,EAAE,mBAAmB,EAAE,MAAM,0BAA0B,CAAC;AAC/D,OAAO,EAAE,0BAA0B,EAAE,MAAM,iCAAiC,CAAC;AAC7E,OAAO,EAAE,sBAAsB,EAAE,MAAM,6BAA6B,CAAC;AACrE,OAAO,EAAE,oBAAoB,EAAE,MAAM,2BAA2B,CAAC;AACjE,OAAO,EAAE,iBAAiB,EAAE,MAAM,wBAAwB,CAAC;AAC3D,OAAO,EAAE,kBAAkB,EAAE,MAAM,yBAAyB,CAAC;AAC7D,OAAO,EAAE,iBAAiB,EAAE,MAAM,aAAa,CAAC"}
@@ -0,0 +1,30 @@
1
+ /**
2
+ * Pagination helpers shared across Supabase stores.
3
+ *
4
+ * The platform contract specifies cursor pagination (`ListOptions.cursor`).
5
+ * Because Supabase/Postgres has no built-in opaque cursor format, we encode
6
+ * an offset as the cursor — simple, correct for stable sorts, and good
7
+ * enough for the volumes Selva deals with (admin/definition lists are
8
+ * bounded; nothing is infinite scroll over millions of rows).
9
+ *
10
+ * Keyset pagination would be faster at scale if it ever matters.
11
+ */
12
+ import type { ListOptions } from '@selvajs/platform';
13
+ export interface RangeSpec {
14
+ from: number;
15
+ to: number;
16
+ limit: number;
17
+ }
18
+ /** Decode an opaque cursor string. Returns 0 for missing/invalid cursors. */
19
+ export declare function decodeCursor(cursor: string | undefined): number;
20
+ export declare function encodeCursor(offset: number): string;
21
+ /** Clamp limit + compute the PostgREST `range(from, to)` bounds. */
22
+ export declare function toRange(opts: Pick<ListOptions, 'limit' | 'cursor'> | undefined): RangeSpec;
23
+ /**
24
+ * Build the `nextCursor` from the count returned by PostgREST. Returns
25
+ * undefined when there is no next page.
26
+ */
27
+ export declare function nextCursorFromRange(range: RangeSpec, returnedCount: number, totalCount: number | null | undefined): string | undefined;
28
+ /** Map `ListOptions.orderBy` to a Postgres column name. */
29
+ export declare function orderColumn(orderBy: ListOptions['orderBy'] | undefined): string;
30
+ //# sourceMappingURL=pagination.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"pagination.d.ts","sourceRoot":"","sources":["../../src/data/pagination.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAGH,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAErD,MAAM,WAAW,SAAS;IACzB,IAAI,EAAE,MAAM,CAAC;IACb,EAAE,EAAE,MAAM,CAAC;IACX,KAAK,EAAE,MAAM,CAAC;CACd;AAED,6EAA6E;AAC7E,wBAAgB,YAAY,CAAC,MAAM,EAAE,MAAM,GAAG,SAAS,GAAG,MAAM,CAI/D;AAED,wBAAgB,YAAY,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,CAEnD;AAED,oEAAoE;AACpE,wBAAgB,OAAO,CAAC,IAAI,EAAE,IAAI,CAAC,WAAW,EAAE,OAAO,GAAG,QAAQ,CAAC,GAAG,SAAS,GAAG,SAAS,CAI1F;AAED;;;GAGG;AACH,wBAAgB,mBAAmB,CAClC,KAAK,EAAE,SAAS,EAChB,aAAa,EAAE,MAAM,EACrB,UAAU,EAAE,MAAM,GAAG,IAAI,GAAG,SAAS,GACnC,MAAM,GAAG,SAAS,CAOpB;AAED,2DAA2D;AAC3D,wBAAgB,WAAW,CAAC,OAAO,EAAE,WAAW,CAAC,SAAS,CAAC,GAAG,SAAS,GAAG,MAAM,CAU/E"}
@@ -0,0 +1,53 @@
1
+ /**
2
+ * Pagination helpers shared across Supabase stores.
3
+ *
4
+ * The platform contract specifies cursor pagination (`ListOptions.cursor`).
5
+ * Because Supabase/Postgres has no built-in opaque cursor format, we encode
6
+ * an offset as the cursor — simple, correct for stable sorts, and good
7
+ * enough for the volumes Selva deals with (admin/definition lists are
8
+ * bounded; nothing is infinite scroll over millions of rows).
9
+ *
10
+ * Keyset pagination would be faster at scale if it ever matters.
11
+ */
12
+ import { DEFAULT_PAGE_LIMIT, MAX_PAGE_LIMIT } from '@selvajs/platform';
13
+ /** Decode an opaque cursor string. Returns 0 for missing/invalid cursors. */
14
+ export function decodeCursor(cursor) {
15
+ if (!cursor)
16
+ return 0;
17
+ const n = parseInt(cursor, 10);
18
+ return Number.isFinite(n) && n >= 0 ? n : 0;
19
+ }
20
+ export function encodeCursor(offset) {
21
+ return String(offset);
22
+ }
23
+ /** Clamp limit + compute the PostgREST `range(from, to)` bounds. */
24
+ export function toRange(opts) {
25
+ const limit = Math.min(Math.max(opts?.limit ?? DEFAULT_PAGE_LIMIT, 1), MAX_PAGE_LIMIT);
26
+ const from = decodeCursor(opts?.cursor);
27
+ return { from, to: from + limit - 1, limit };
28
+ }
29
+ /**
30
+ * Build the `nextCursor` from the count returned by PostgREST. Returns
31
+ * undefined when there is no next page.
32
+ */
33
+ export function nextCursorFromRange(range, returnedCount, totalCount) {
34
+ const consumed = range.from + returnedCount;
35
+ if (totalCount != null) {
36
+ return consumed < totalCount ? encodeCursor(consumed) : undefined;
37
+ }
38
+ // Without total, we can only infer "there might be more" if we got a full page.
39
+ return returnedCount >= range.limit ? encodeCursor(consumed) : undefined;
40
+ }
41
+ /** Map `ListOptions.orderBy` to a Postgres column name. */
42
+ export function orderColumn(orderBy) {
43
+ switch (orderBy) {
44
+ case 'name':
45
+ return 'name';
46
+ case 'updatedAt':
47
+ return 'updated_at';
48
+ case 'createdAt':
49
+ default:
50
+ return 'created_at';
51
+ }
52
+ }
53
+ //# sourceMappingURL=pagination.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"pagination.js","sourceRoot":"","sources":["../../src/data/pagination.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAEH,OAAO,EAAE,kBAAkB,EAAE,cAAc,EAAE,MAAM,mBAAmB,CAAC;AASvE,6EAA6E;AAC7E,MAAM,UAAU,YAAY,CAAC,MAA0B;IACtD,IAAI,CAAC,MAAM;QAAE,OAAO,CAAC,CAAC;IACtB,MAAM,CAAC,GAAG,QAAQ,CAAC,MAAM,EAAE,EAAE,CAAC,CAAC;IAC/B,OAAO,MAAM,CAAC,QAAQ,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;AAC7C,CAAC;AAED,MAAM,UAAU,YAAY,CAAC,MAAc;IAC1C,OAAO,MAAM,CAAC,MAAM,CAAC,CAAC;AACvB,CAAC;AAED,oEAAoE;AACpE,MAAM,UAAU,OAAO,CAAC,IAAuD;IAC9E,MAAM,KAAK,GAAG,IAAI,CAAC,GAAG,CAAC,IAAI,CAAC,GAAG,CAAC,IAAI,EAAE,KAAK,IAAI,kBAAkB,EAAE,CAAC,CAAC,EAAE,cAAc,CAAC,CAAC;IACvF,MAAM,IAAI,GAAG,YAAY,CAAC,IAAI,EAAE,MAAM,CAAC,CAAC;IACxC,OAAO,EAAE,IAAI,EAAE,EAAE,EAAE,IAAI,GAAG,KAAK,GAAG,CAAC,EAAE,KAAK,EAAE,CAAC;AAC9C,CAAC;AAED;;;GAGG;AACH,MAAM,UAAU,mBAAmB,CAClC,KAAgB,EAChB,aAAqB,EACrB,UAAqC;IAErC,MAAM,QAAQ,GAAG,KAAK,CAAC,IAAI,GAAG,aAAa,CAAC;IAC5C,IAAI,UAAU,IAAI,IAAI,EAAE,CAAC;QACxB,OAAO,QAAQ,GAAG,UAAU,CAAC,CAAC,CAAC,YAAY,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;IACnE,CAAC;IACD,gFAAgF;IAChF,OAAO,aAAa,IAAI,KAAK,CAAC,KAAK,CAAC,CAAC,CAAC,YAAY,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;AAC1E,CAAC;AAED,2DAA2D;AAC3D,MAAM,UAAU,WAAW,CAAC,OAA2C;IACtE,QAAQ,OAAO,EAAE,CAAC;QACjB,KAAK,MAAM;YACV,OAAO,MAAM,CAAC;QACf,KAAK,WAAW;YACf,OAAO,YAAY,CAAC;QACrB,KAAK,WAAW,CAAC;QACjB;YACC,OAAO,YAAY,CAAC;IACtB,CAAC;AACF,CAAC"}
@@ -0,0 +1,9 @@
1
+ export { SupabaseStorageProvider } from './storage/SupabaseStorageProvider.js';
2
+ export type { SupabaseStorageProviderConfig } from './storage/SupabaseStorageProvider.js';
3
+ export { SupabaseOrgStore, SupabaseProjectStore, SupabaseDefinitionStore, SupabaseInviteStore, SupabaseComputeServerStore, SupabaseShareLinkStore, SupabaseDataProvider, SupabaseEventSink, SupabaseAuditQuery, buildClientBundle } from './data/index.js';
4
+ export type { ClientBundle, BuildClientOptions } from './data/index.js';
5
+ export { SupabaseUserProfileProvider } from './userProfile/index.js';
6
+ export { SupabaseAuthProvider } from './auth/index.js';
7
+ export type { SupabaseAuthProviderConfig } from './auth/index.js';
8
+ export { SupabasePlatformPermissionStore } from './permissions/index.js';
9
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,uBAAuB,EAAE,MAAM,sCAAsC,CAAC;AAC/E,YAAY,EAAE,6BAA6B,EAAE,MAAM,sCAAsC,CAAC;AAE1F,OAAO,EACN,gBAAgB,EAChB,oBAAoB,EACpB,uBAAuB,EACvB,mBAAmB,EACnB,0BAA0B,EAC1B,sBAAsB,EACtB,oBAAoB,EACpB,iBAAiB,EACjB,kBAAkB,EAClB,iBAAiB,EACjB,MAAM,iBAAiB,CAAC;AACzB,YAAY,EAAE,YAAY,EAAE,kBAAkB,EAAE,MAAM,iBAAiB,CAAC;AAExE,OAAO,EAAE,2BAA2B,EAAE,MAAM,wBAAwB,CAAC;AAErE,OAAO,EAAE,oBAAoB,EAAE,MAAM,iBAAiB,CAAC;AACvD,YAAY,EAAE,0BAA0B,EAAE,MAAM,iBAAiB,CAAC;AAElE,OAAO,EAAE,+BAA+B,EAAE,MAAM,wBAAwB,CAAC"}
package/dist/index.js ADDED
@@ -0,0 +1,6 @@
1
+ export { SupabaseStorageProvider } from './storage/SupabaseStorageProvider.js';
2
+ export { SupabaseOrgStore, SupabaseProjectStore, SupabaseDefinitionStore, SupabaseInviteStore, SupabaseComputeServerStore, SupabaseShareLinkStore, SupabaseDataProvider, SupabaseEventSink, SupabaseAuditQuery, buildClientBundle } from './data/index.js';
3
+ export { SupabaseUserProfileProvider } from './userProfile/index.js';
4
+ export { SupabaseAuthProvider } from './auth/index.js';
5
+ export { SupabasePlatformPermissionStore } from './permissions/index.js';
6
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,uBAAuB,EAAE,MAAM,sCAAsC,CAAC;AAG/E,OAAO,EACN,gBAAgB,EAChB,oBAAoB,EACpB,uBAAuB,EACvB,mBAAmB,EACnB,0BAA0B,EAC1B,sBAAsB,EACtB,oBAAoB,EACpB,iBAAiB,EACjB,kBAAkB,EAClB,iBAAiB,EACjB,MAAM,iBAAiB,CAAC;AAGzB,OAAO,EAAE,2BAA2B,EAAE,MAAM,wBAAwB,CAAC;AAErE,OAAO,EAAE,oBAAoB,EAAE,MAAM,iBAAiB,CAAC;AAGvD,OAAO,EAAE,+BAA+B,EAAE,MAAM,wBAAwB,CAAC"}
@@ -0,0 +1,25 @@
1
+ import type { IPlatformPermissionStore, PlatformPermission, RequestContext, UserManagementResult } from '@selvajs/platform';
2
+ import type { ClientBundle } from '../data/client.js';
3
+ /**
4
+ * Supabase-backed platform-permission store. Reads and writes
5
+ * `public.user_profiles.platform_permissions` (auto-seeded by the
6
+ * `handle_new_auth_user` trigger). Service-role throughout — the store's own
7
+ * `assertAdmin` / `assertCanRead` enforce the auth boundary at the app level
8
+ * since RLS on `user_profiles` is coarse-grained for cross-user reads.
9
+ *
10
+ * Disabled-user state lives on `auth.users.user_metadata.disabled`, so the
11
+ * invariant counters cross-reference the auth backend to exclude disabled
12
+ * admins (matches `Permissions.md §10` "enabled instance_admin" semantics).
13
+ */
14
+ export declare class SupabasePlatformPermissionStore implements IPlatformPermissionStore {
15
+ private readonly clients;
16
+ constructor(clients: ClientBundle);
17
+ private client;
18
+ getFor(ctx: RequestContext, userId: string): Promise<PlatformPermission[]>;
19
+ getForBatch(ctx: RequestContext, userIds: readonly string[]): Promise<Map<string, PlatformPermission[]>>;
20
+ set(ctx: RequestContext, userId: string, permissions: readonly PlatformPermission[]): Promise<UserManagementResult>;
21
+ hasInstanceAdmin(_ctx: RequestContext): Promise<boolean>;
22
+ countInstanceAdminsExcluding(_ctx: RequestContext, excludeUserId: string): Promise<number>;
23
+ private countOtherEnabledAdmins;
24
+ }
25
+ //# sourceMappingURL=SupabasePlatformPermissionStore.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"SupabasePlatformPermissionStore.d.ts","sourceRoot":"","sources":["../../src/permissions/SupabasePlatformPermissionStore.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EACX,wBAAwB,EACxB,kBAAkB,EAClB,cAAc,EACd,oBAAoB,EACpB,MAAM,mBAAmB,CAAC;AAE3B,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,mBAAmB,CAAC;AAEtD;;;;;;;;;;GAUG;AACH,qBAAa,+BAAgC,YAAW,wBAAwB;IACnE,OAAO,CAAC,QAAQ,CAAC,OAAO;gBAAP,OAAO,EAAE,YAAY;IAElD,OAAO,CAAC,MAAM;IAIR,MAAM,CAAC,GAAG,EAAE,cAAc,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,kBAAkB,EAAE,CAAC;IAW1E,WAAW,CAChB,GAAG,EAAE,cAAc,EACnB,OAAO,EAAE,SAAS,MAAM,EAAE,GACxB,OAAO,CAAC,GAAG,CAAC,MAAM,EAAE,kBAAkB,EAAE,CAAC,CAAC;IAevC,GAAG,CACR,GAAG,EAAE,cAAc,EACnB,MAAM,EAAE,MAAM,EACd,WAAW,EAAE,SAAS,kBAAkB,EAAE,GACxC,OAAO,CAAC,oBAAoB,CAAC;IA8B1B,gBAAgB,CAAC,IAAI,EAAE,cAAc,GAAG,OAAO,CAAC,OAAO,CAAC;IAgBxD,4BAA4B,CAAC,IAAI,EAAE,cAAc,EAAE,aAAa,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC;YAIlF,uBAAuB;CAgBrC"}
@@ -0,0 +1,153 @@
1
+ import { ProviderError, hasPermission, PlatformPermissionSchema } from '@selvajs/platform';
2
+ /**
3
+ * Supabase-backed platform-permission store. Reads and writes
4
+ * `public.user_profiles.platform_permissions` (auto-seeded by the
5
+ * `handle_new_auth_user` trigger). Service-role throughout — the store's own
6
+ * `assertAdmin` / `assertCanRead` enforce the auth boundary at the app level
7
+ * since RLS on `user_profiles` is coarse-grained for cross-user reads.
8
+ *
9
+ * Disabled-user state lives on `auth.users.user_metadata.disabled`, so the
10
+ * invariant counters cross-reference the auth backend to exclude disabled
11
+ * admins (matches `Permissions.md §10` "enabled instance_admin" semantics).
12
+ */
13
+ export class SupabasePlatformPermissionStore {
14
+ clients;
15
+ constructor(clients) {
16
+ this.clients = clients;
17
+ }
18
+ client() {
19
+ return this.clients.serviceClient;
20
+ }
21
+ async getFor(ctx, userId) {
22
+ assertCanRead(ctx, userId);
23
+ const { data, error } = await this.client()
24
+ .from('user_profiles')
25
+ .select('platform_permissions')
26
+ .eq('user_id', userId)
27
+ .maybeSingle();
28
+ if (error)
29
+ throw mapError(error);
30
+ return filterValid(data?.platform_permissions ?? []);
31
+ }
32
+ async getForBatch(ctx, userIds) {
33
+ assertAdmin(ctx);
34
+ const out = new Map();
35
+ if (userIds.length === 0)
36
+ return out;
37
+ const { data, error } = await this.client()
38
+ .from('user_profiles')
39
+ .select('user_id, platform_permissions')
40
+ .in('user_id', [...userIds]);
41
+ if (error)
42
+ throw mapError(error);
43
+ for (const row of data ?? []) {
44
+ out.set(row.user_id, filterValid((row.platform_permissions ?? [])));
45
+ }
46
+ return out;
47
+ }
48
+ async set(ctx, userId, permissions) {
49
+ assertAdmin(ctx);
50
+ // 1. Confirm the target exists in the auth backend (the FK + trigger
51
+ // means the user_profiles row should exist post-signup; if not,
52
+ // treat as not_found rather than auto-creating).
53
+ const { data: existing, error: fetchError } = await this.client()
54
+ .from('user_profiles')
55
+ .select('platform_permissions')
56
+ .eq('user_id', userId)
57
+ .maybeSingle();
58
+ if (fetchError)
59
+ throw mapError(fetchError);
60
+ if (!existing)
61
+ return 'not_found';
62
+ // 2. §2 invariant: refuse if dropping the last instance_admin.
63
+ const wasAdmin = (existing.platform_permissions ?? []).includes('instance_admin');
64
+ const willBeAdmin = permissions.includes('instance_admin');
65
+ if (wasAdmin && !willBeAdmin) {
66
+ const others = await this.countOtherEnabledAdmins(userId);
67
+ if (others === 0)
68
+ return 'last_admin';
69
+ }
70
+ // 3. Apply.
71
+ const { error } = await this.client()
72
+ .from('user_profiles')
73
+ .update({ platform_permissions: [...permissions] })
74
+ .eq('user_id', userId);
75
+ if (error)
76
+ throw mapError(error);
77
+ return 'ok';
78
+ }
79
+ async hasInstanceAdmin(_ctx) {
80
+ const { data, error } = await this.client()
81
+ .from('user_profiles')
82
+ .select('user_id')
83
+ .contains('platform_permissions', ['instance_admin']);
84
+ if (error)
85
+ throw mapError(error);
86
+ const candidates = (data ?? []).map((r) => r.user_id);
87
+ if (candidates.length === 0)
88
+ return false;
89
+ // Check at least one isn't disabled.
90
+ for (const id of candidates) {
91
+ const { data: authData } = await this.clients.serviceClient.auth.admin.getUserById(id);
92
+ if (authData.user && authData.user.user_metadata?.disabled !== true)
93
+ return true;
94
+ }
95
+ return false;
96
+ }
97
+ async countInstanceAdminsExcluding(_ctx, excludeUserId) {
98
+ return this.countOtherEnabledAdmins(excludeUserId);
99
+ }
100
+ async countOtherEnabledAdmins(excludeUserId) {
101
+ const { data, error } = await this.client()
102
+ .from('user_profiles')
103
+ .select('user_id')
104
+ .contains('platform_permissions', ['instance_admin'])
105
+ .neq('user_id', excludeUserId);
106
+ if (error)
107
+ throw mapError(error);
108
+ const candidates = (data ?? []).map((r) => r.user_id);
109
+ if (candidates.length === 0)
110
+ return 0;
111
+ let count = 0;
112
+ for (const id of candidates) {
113
+ const { data: authData } = await this.clients.serviceClient.auth.admin.getUserById(id);
114
+ if (authData.user && authData.user.user_metadata?.disabled !== true)
115
+ count += 1;
116
+ }
117
+ return count;
118
+ }
119
+ }
120
+ function filterValid(raw) {
121
+ return raw.filter((p) => PlatformPermissionSchema.safeParse(p).success);
122
+ }
123
+ function assertCanRead(ctx, userId) {
124
+ if (ctx.system)
125
+ return;
126
+ if (ctx.userId === userId)
127
+ return;
128
+ if (hasPermission(ctx, 'instance_admin'))
129
+ return;
130
+ throw new ProviderError('Forbidden: cannot read another user’s permissions', 403);
131
+ }
132
+ function assertAdmin(ctx) {
133
+ if (ctx.system)
134
+ return;
135
+ if (hasPermission(ctx, 'instance_admin'))
136
+ return;
137
+ throw new ProviderError('Forbidden: instance admin required', 403);
138
+ }
139
+ function mapError(e) {
140
+ const pg = e;
141
+ if (pg?.code === '23505')
142
+ return new ProviderError(pg.message ?? 'Duplicate record', 409);
143
+ if (pg?.code === '23503')
144
+ return new ProviderError(pg.message ?? 'Foreign key violation', 409);
145
+ if (e instanceof Error)
146
+ return e;
147
+ if (e && typeof e === 'object') {
148
+ const obj = e;
149
+ return new Error(obj.code ? `[${obj.code}] ${obj.message ?? ''}` : (obj.message ?? String(e)));
150
+ }
151
+ return new Error(String(e));
152
+ }
153
+ //# sourceMappingURL=SupabasePlatformPermissionStore.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"SupabasePlatformPermissionStore.js","sourceRoot":"","sources":["../../src/permissions/SupabasePlatformPermissionStore.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=conformance.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"conformance.test.d.ts","sourceRoot":"","sources":["../../../src/permissions/__tests__/conformance.test.ts"],"names":[],"mappings":""}