permdock 0.0.0 → 0.2.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 (344) hide show
  1. package/README.md +327 -1
  2. package/dist/a2a/index.d.ts +169 -0
  3. package/dist/a2a/index.js +232 -0
  4. package/dist/adapter-context-mlWsVGGg.js +23 -0
  5. package/dist/ai-sdk/index.d.ts +95 -0
  6. package/dist/ai-sdk/index.js +154 -0
  7. package/dist/approval-required-TzNB9oQA.js +6 -0
  8. package/dist/approvals/index.d.ts +3 -0
  9. package/dist/approvals/index.js +5 -0
  10. package/dist/approvals-DbYAuNkG.js +224 -0
  11. package/dist/approvers-DT4AVyIg.js +52 -0
  12. package/dist/arazzo-BAgw9ap6.js +70 -0
  13. package/dist/arazzo-cmvX2jDe.js +54 -0
  14. package/dist/authzen/index.d.ts +39 -0
  15. package/dist/authzen/index.js +302 -0
  16. package/dist/better-auth/index.d.ts +109 -0
  17. package/dist/better-auth/index.js +344 -0
  18. package/dist/better-supabase/index.d.ts +206 -0
  19. package/dist/better-supabase/index.js +620 -0
  20. package/dist/bind-CVy3Espv.d.ts +25 -0
  21. package/dist/bind-VnYn2HKq.js +97 -0
  22. package/dist/boundary-BM8a_P6E.js +13 -0
  23. package/dist/boundary-BmHxVH1J.d.ts +15 -0
  24. package/dist/budget-JqcRqyhK.d.ts +11 -0
  25. package/dist/budget-NbEtbJC_.js +11 -0
  26. package/dist/canonical-json-DemiK4Vp.js +26 -0
  27. package/dist/capability-4qPdO9gk.js +173 -0
  28. package/dist/capability-Dq43tT1u.d.ts +99 -0
  29. package/dist/catalog/index.d.ts +12 -0
  30. package/dist/catalog/index.js +2 -0
  31. package/dist/catalog-BjZSovXQ.js +2 -0
  32. package/dist/catalog-doc-Dsc9y7sd.js +309 -0
  33. package/dist/catalog-h2tlKFkq.js +48 -0
  34. package/dist/catalog-path-CnI0XTFK.js +12 -0
  35. package/dist/catalog-z8q6bi_r.js +55 -0
  36. package/dist/claude-agent/index.d.ts +72 -0
  37. package/dist/claude-agent/index.js +77 -0
  38. package/dist/clerk/index.d.ts +65 -0
  39. package/dist/clerk/index.js +301 -0
  40. package/dist/cli/bin.d.ts +1 -0
  41. package/dist/cli/bin.js +20 -0
  42. package/dist/cli/index.d.ts +46 -0
  43. package/dist/cli/index.js +5 -0
  44. package/dist/clients-C7zLFuWT.d.ts +12 -0
  45. package/dist/clients-DjU5ABMy.js +23 -0
  46. package/dist/cloud/index.d.ts +90 -0
  47. package/dist/cloud/index.js +404 -0
  48. package/dist/cloud-BGhHS-lY.js +50 -0
  49. package/dist/cloud-Bo3e9Ak3.js +118 -0
  50. package/dist/collect-DDDv_ESs.js +502 -0
  51. package/dist/collect-DLlujdHC.js +83 -0
  52. package/dist/collect-rG2IQ3t0.js +2 -0
  53. package/dist/commands-DWOrSQic.js +97 -0
  54. package/dist/compact-y6vfu2_f.js +19 -0
  55. package/dist/compare-pfyVnBjE.js +12 -0
  56. package/dist/compile/index.d.ts +3 -0
  57. package/dist/compile/index.js +2 -0
  58. package/dist/compile-Ba4blROR.js +613 -0
  59. package/dist/compile-CNnl6uIt.d.ts +94 -0
  60. package/dist/config-BJiM-xAm.js +157 -0
  61. package/dist/config-Bn00Z3ks.js +36 -0
  62. package/dist/config-report-Dw_JcUqT.js +44 -0
  63. package/dist/connection-CU8MQxRi.js +194 -0
  64. package/dist/context-Ttp0ekMT.js +82 -0
  65. package/dist/convex/index.d.ts +45 -0
  66. package/dist/convex/index.js +65 -0
  67. package/dist/create-BWyx3jua.d.ts +245 -0
  68. package/dist/create-CPhDL6qx.js +253 -0
  69. package/dist/credential-8P81ff4u.js +306 -0
  70. package/dist/delegation-D8pUEuce.js +103 -0
  71. package/dist/describe-B_gVZEVi.js +94 -0
  72. package/dist/describe-PdoqESvg.d.ts +36 -0
  73. package/dist/diff-B8Tunc3o.js +451 -0
  74. package/dist/diff-CzqLxZ77.js +48 -0
  75. package/dist/digest-B3kc_PgQ.d.ts +19 -0
  76. package/dist/digest-BI-6aa6d.js +27 -0
  77. package/dist/doctor-WpvG6p4k.js +1194 -0
  78. package/dist/doctor-collect-ByfYlNv1.js +664 -0
  79. package/dist/doctor-rOr-4ZfS.js +53 -0
  80. package/dist/drizzle/index.d.ts +73 -0
  81. package/dist/drizzle/index.js +160 -0
  82. package/dist/duration-xK2jGFVc.js +25 -0
  83. package/dist/elysia/index.d.ts +49 -0
  84. package/dist/elysia/index.js +59 -0
  85. package/dist/errors-CWfoNg9N.js +47 -0
  86. package/dist/errors-Cz5zn0mW.js +123 -0
  87. package/dist/errors-DAqevpNk.d.ts +125 -0
  88. package/dist/errors-DRnGZHzF.js +30 -0
  89. package/dist/evaluation-items-CfCCejQd.js +40 -0
  90. package/dist/evaluations-tz6D9A2G.js +461 -0
  91. package/dist/eve/index.d.ts +86 -0
  92. package/dist/eve/index.js +176 -0
  93. package/dist/expiry-BoBJ8Tvc.js +7 -0
  94. package/dist/express/index.d.ts +23 -0
  95. package/dist/express/index.js +78 -0
  96. package/dist/fastify/index.d.ts +33 -0
  97. package/dist/fastify/index.js +92 -0
  98. package/dist/fields-BMl1RxoX.js +26 -0
  99. package/dist/files-DWUN9PzI.js +125 -0
  100. package/dist/fixtures-ht28Cplr.js +67 -0
  101. package/dist/freeze-CrU8nQeX.js +60 -0
  102. package/dist/from-snapshot-C3sHpZNS.js +569 -0
  103. package/dist/generate-CH7ThJ14.js +173 -0
  104. package/dist/grantee-Cv5Sogfv.js +602 -0
  105. package/dist/graph-sql-B-dsAT6j.d.ts +29 -0
  106. package/dist/headers-BZSDieNT.js +6 -0
  107. package/dist/headers-Cf-zWvsO.d.ts +6 -0
  108. package/dist/helpers-H_KARDVC.js +421 -0
  109. package/dist/hono/index.d.ts +48 -0
  110. package/dist/hono/index.js +99 -0
  111. package/dist/hosted-DJQw46hn.js +266 -0
  112. package/dist/http-BIhmLfCc.js +95 -0
  113. package/dist/http-DPuDaChb.d.ts +13 -0
  114. package/dist/http-SO7qGttf.js +44 -0
  115. package/dist/ids-DC4V4CFu.js +18 -0
  116. package/dist/index-A0YNL8jZ.d.ts +177 -0
  117. package/dist/index-CtE07CBF.d.ts +6 -0
  118. package/dist/index-D3vbkoSI.d.ts +483 -0
  119. package/dist/index-D6_cSa1z.d.ts +201 -0
  120. package/dist/index.d.ts +16 -0
  121. package/dist/index.js +26 -0
  122. package/dist/instance-options-BK_rNOSC.d.ts +11 -0
  123. package/dist/instance-options-Dhhcnm3y.js +22 -0
  124. package/dist/json-schema-BsAflUGW.js +106 -0
  125. package/dist/jwt/index.d.ts +91 -0
  126. package/dist/jwt/index.js +590 -0
  127. package/dist/kernel-GSQnMz3O.js +208 -0
  128. package/dist/kysely/index.d.ts +78 -0
  129. package/dist/kysely/index.js +129 -0
  130. package/dist/live-options-H2eG8dfJ.js +60 -0
  131. package/dist/load-DhWEB9P1.js +75 -0
  132. package/dist/load-DwJUafYN.js +2 -0
  133. package/dist/load-jose-BL6LH4bL.js +11 -0
  134. package/dist/lru-8q4WZjBV.js +28 -0
  135. package/dist/manifest-iaoBXHKc.js +783 -0
  136. package/dist/manifest-uDS9y5de.d.ts +206 -0
  137. package/dist/map-AcxK9o_D.js +147 -0
  138. package/dist/map-claims-Z4QZOiFF.js +369 -0
  139. package/dist/map-error-pgUWNNtG.js +23 -0
  140. package/dist/markers-B0hYLvMD.js +60 -0
  141. package/dist/may-use-DndQ5tQ-.js +77 -0
  142. package/dist/mcp/index.d.ts +159 -0
  143. package/dist/mcp/index.js +603 -0
  144. package/dist/nest/index.d.ts +75 -0
  145. package/dist/nest/index.js +261 -0
  146. package/dist/next/client.d.ts +23 -0
  147. package/dist/next/client.js +33 -0
  148. package/dist/next/index.d.ts +93 -0
  149. package/dist/next/index.js +180 -0
  150. package/dist/next/plugin.d.ts +14 -0
  151. package/dist/next/plugin.js +33 -0
  152. package/dist/node/index.d.ts +24 -0
  153. package/dist/node/index.js +34 -0
  154. package/dist/openai/index.d.ts +62 -0
  155. package/dist/openai/index.js +92 -0
  156. package/dist/openapi/index.d.ts +176 -0
  157. package/dist/openapi/index.js +3 -0
  158. package/dist/openapi-Bbg4wGVL.js +164 -0
  159. package/dist/openapi-BqRBvAng.js +538 -0
  160. package/dist/openapi-CqqEbHsL.js +250 -0
  161. package/dist/openapi-import-cmwetbzw.js +5959 -0
  162. package/dist/openapi-schema--ARjyfQr.js +6902 -0
  163. package/dist/orpc/index.d.ts +51 -0
  164. package/dist/orpc/index.js +145 -0
  165. package/dist/otel/index.d.ts +13 -0
  166. package/dist/otel/index.js +202 -0
  167. package/dist/package-root-zGkxO3oN.js +30 -0
  168. package/dist/parse-BuyjxhZV.js +53 -0
  169. package/dist/parse-local-manifest-BkGQNzAh.d.ts +10 -0
  170. package/dist/parse-local-manifest-BrMozJCo.js +36 -0
  171. package/dist/pdp/index.d.ts +22 -0
  172. package/dist/pdp/index.js +682 -0
  173. package/dist/peer-BOr_kJE1.js +31 -0
  174. package/dist/permdock-CzqXjCpU.js +3471 -0
  175. package/dist/permissions-CDgvKG5L.d.ts +52 -0
  176. package/dist/permissions-CpZrivYv.js +142 -0
  177. package/dist/permissions-DVoF6dMt.js +662 -0
  178. package/dist/permissions-DttnqqxC.d.ts +214 -0
  179. package/dist/pins-8ILTftC9.js +12 -0
  180. package/dist/policy-CFZAr_Al.d.ts +2252 -0
  181. package/dist/policy-D8UFyERw.d.ts +20 -0
  182. package/dist/policy-xyWg7QdR.js +1122 -0
  183. package/dist/powersync-A8x_Yyvh.js +2 -0
  184. package/dist/powersync-C7kLglqX.js +540 -0
  185. package/dist/powersync-yW1UUFzp.js +62 -0
  186. package/dist/prisma/index.d.ts +136 -0
  187. package/dist/prisma/index.js +455 -0
  188. package/dist/problem-B43ztKIm.js +191 -0
  189. package/dist/problem-details-CkL50EEf.d.ts +7 -0
  190. package/dist/problem-details-_AMOYz-w.js +144 -0
  191. package/dist/prompt-CXYhLfsS.js +32 -0
  192. package/dist/protected-CNsMzrVd.d.ts +27 -0
  193. package/dist/protected-Cs6kTaHo.js +100 -0
  194. package/dist/protected-bZs6rbT1.d.ts +40 -0
  195. package/dist/provider-Cjr62YMV.d.ts +6 -0
  196. package/dist/provider-DLzpb2Xz.js +52 -0
  197. package/dist/provider-store-DNyC1y48.js +43 -0
  198. package/dist/react/index.d.ts +8 -0
  199. package/dist/react/index.js +7 -0
  200. package/dist/react/provider-client.d.ts +2 -0
  201. package/dist/react/provider-client.js +3 -0
  202. package/dist/react-native/index.d.ts +198 -0
  203. package/dist/react-native/index.js +696 -0
  204. package/dist/refs-KYb4ntaz.js +91 -0
  205. package/dist/relations-cjOL01hZ.js +505 -0
  206. package/dist/replay-BsOyTrdV.js +28 -0
  207. package/dist/replay-sqBGMnNs.d.ts +5 -0
  208. package/dist/resource-ref-CaS9yVPi.js +20 -0
  209. package/dist/revocations-Bhr0aMIC.js +27 -0
  210. package/dist/revocations-Cy06JNx2.d.ts +21 -0
  211. package/dist/rls-BMNydpHk.js +2521 -0
  212. package/dist/rls-CEvs64Kj.js +238 -0
  213. package/dist/rls-fields-BMasREhR.js +3502 -0
  214. package/dist/rls-graph-pc9fuXYm.js +435 -0
  215. package/dist/rls-import-D8F7j35Q.js +943 -0
  216. package/dist/rls-migrate-7wikfrVI.js +367 -0
  217. package/dist/rls-ownership-B5Lkq62W.js +843 -0
  218. package/dist/rls-shared-aOQ4hGTO.js +493 -0
  219. package/dist/rls-verify-D8B7dOTh.js +745 -0
  220. package/dist/row-check-Dt35czLy.d.ts +40 -0
  221. package/dist/rpc-DOK54_CS.js +89 -0
  222. package/dist/run-YXCJDNYk.js +174 -0
  223. package/dist/runtime-CB8gQFvS.js +11 -0
  224. package/dist/saas-Bj_FFkjN.js +1203 -0
  225. package/dist/schema-D3MnDMxa.js +300 -0
  226. package/dist/scim/index.d.ts +2 -0
  227. package/dist/scim/index.js +2 -0
  228. package/dist/scim-BFGBBAqR.js +1445 -0
  229. package/dist/scopes-CVdPrWN-.js +239 -0
  230. package/dist/server/index.d.ts +134 -0
  231. package/dist/server/index.js +11 -0
  232. package/dist/server-DlZ28Oz5.js +268 -0
  233. package/dist/sha256-BO0swRXL.js +150 -0
  234. package/dist/shared-DRu8VFVM.js +123 -0
  235. package/dist/sink-Bd9PSyfq.js +141 -0
  236. package/dist/sink-Gs6TTVa-.d.ts +104 -0
  237. package/dist/skills-Biq5uup3.js +192 -0
  238. package/dist/skills-JaymNCdK.js +56 -0
  239. package/dist/snapshot-Enxd0n-s.js +975 -0
  240. package/dist/snapshot-cache-D6jLelln.js +44 -0
  241. package/dist/snapshot-cache-DwQH8ufx.d.ts +45 -0
  242. package/dist/solid/index.d.ts +93 -0
  243. package/dist/solid/index.js +188 -0
  244. package/dist/sources-B0UvrJ21.js +534 -0
  245. package/dist/sources-BcJgw0lt.d.ts +192 -0
  246. package/dist/sql-xdg5f4Fi.js +27 -0
  247. package/dist/src-CSbUiozF.js +568 -0
  248. package/dist/ssf/index.d.ts +4 -0
  249. package/dist/ssf/index.js +596 -0
  250. package/dist/store-DMAWwAJV.js +371 -0
  251. package/dist/store-D_pjn91-.d.ts +36 -0
  252. package/dist/store-options-yO0V6gRn.js +716 -0
  253. package/dist/stores-4_sqiOA1.js +87 -0
  254. package/dist/stores-DVR5NHLE.d.ts +52 -0
  255. package/dist/stream-DDpvynSB.js +66 -0
  256. package/dist/stream-DlvG2hs-.d.ts +12 -0
  257. package/dist/style-CTm1AXDT.js +22 -0
  258. package/dist/subject-C6dLxqHU.js +24 -0
  259. package/dist/subject-settings-BwBmCdTR.js +128 -0
  260. package/dist/supabase/index.d.ts +183 -0
  261. package/dist/supabase/index.js +5 -0
  262. package/dist/supabase/middleware.d.ts +82 -0
  263. package/dist/supabase/middleware.js +102 -0
  264. package/dist/supabase-CwafwxxF.js +83 -0
  265. package/dist/supabase-DTBaC20O.js +774 -0
  266. package/dist/supabase-config-Bs44dare.js +472 -0
  267. package/dist/supabase-hook-BuxLQLpU.js +1814 -0
  268. package/dist/supabase-hook-D5qVd_D8.js +2 -0
  269. package/dist/supautils-DYZnzRWV.js +91 -0
  270. package/dist/svelte/PermissionBoundary.svelte +37 -0
  271. package/dist/svelte/Protected.svelte +40 -0
  272. package/dist/svelte/index.d.ts +13 -0
  273. package/dist/svelte/index.js +107 -0
  274. package/dist/svelte/runtime.d.ts +7 -0
  275. package/dist/svelte/runtime.js +4 -0
  276. package/dist/svelte/source.d.ts +13 -0
  277. package/dist/svelte/source.js +11 -0
  278. package/dist/terminal/index.d.ts +163 -0
  279. package/dist/terminal/index.js +833 -0
  280. package/dist/testing/index.d.ts +745 -0
  281. package/dist/testing/index.js +3672 -0
  282. package/dist/testing/saas/index.d.ts +194 -0
  283. package/dist/testing/saas/index.js +3 -0
  284. package/dist/testing/saas/permissions.d.ts +2 -0
  285. package/dist/testing/saas/permissions.js +2 -0
  286. package/dist/text-diff-BdkkYSbi.js +15 -0
  287. package/dist/thenable-okc2xDsj.js +10 -0
  288. package/dist/timeout-D51niuQP.js +8 -0
  289. package/dist/token-CIWxJOCh.js +50 -0
  290. package/dist/trpc/index.d.ts +61 -0
  291. package/dist/trpc/index.js +122 -0
  292. package/dist/types-9AWO9EGt.d.ts +197 -0
  293. package/dist/types-BPxgszlT.d.ts +550 -0
  294. package/dist/types-BVyImy5I.d.ts +120 -0
  295. package/dist/types-Bvc4oWT6.d.ts +9 -0
  296. package/dist/types-C3s9xVJG.d.ts +48 -0
  297. package/dist/types-Dnemwd77.d.ts +183 -0
  298. package/dist/types-kxznc7cn.d.ts +52 -0
  299. package/dist/types-vKyAMtcX.d.ts +157 -0
  300. package/dist/types-vNSDF7Dq.d.ts +66 -0
  301. package/dist/types-yF5LmQVD.d.ts +306 -0
  302. package/dist/unplugin/index.d.ts +7 -0
  303. package/dist/unplugin/index.js +31 -0
  304. package/dist/usage-D07N9QJ3.js +42 -0
  305. package/dist/usage-D82l1CwK.js +2 -0
  306. package/dist/usage-DG1oeCca.js +693 -0
  307. package/dist/validation-error-CnjZ4t92.js +33 -0
  308. package/dist/validation-error-CtF23SrC.d.ts +26 -0
  309. package/dist/validity-uOp8UpYn.js +245 -0
  310. package/dist/verifier-BxBo6I44.js +466 -0
  311. package/dist/version-BvacVTZR.js +17 -0
  312. package/dist/views-Soe7bGSC.js +95 -0
  313. package/dist/vocabulary-DA8a8zif.d.ts +56 -0
  314. package/dist/vue/index.d.ts +79 -0
  315. package/dist/vue/index.js +196 -0
  316. package/dist/watch-Etoa_Mvr.js +2 -0
  317. package/dist/watch-UihESpsJ.js +128 -0
  318. package/dist/webmcp/index.d.ts +75 -0
  319. package/dist/webmcp/index.js +307 -0
  320. package/package.json +450 -5
  321. package/rulesets/permdock.yaml +29 -0
  322. package/schemas/approval-request-v1.json +175 -0
  323. package/schemas/catalog-v1.json +535 -0
  324. package/schemas/openapi/oas-3.1.json +1298 -0
  325. package/schemas/openapi/oas-3.2.json +1516 -0
  326. package/schemas/openapi/overlay-1.1.json +79 -0
  327. package/schemas/supabase-claims-v1.json +144 -0
  328. package/schemas/supabase-manifest-v1.json +361 -0
  329. package/skills/permdock/SKILL.md +66 -0
  330. package/skills/permdock-agents/SKILL.md +77 -0
  331. package/skills/permdock-agents/references/runtimes.md +213 -0
  332. package/skills/permdock-approvals/SKILL.md +80 -0
  333. package/skills/permdock-approvals/references/stores-and-resume.md +94 -0
  334. package/skills/permdock-audit/SKILL.md +67 -0
  335. package/skills/permdock-credentials/SKILL.md +55 -0
  336. package/skills/permdock-credentials/references/tokens-keys-links.md +132 -0
  337. package/skills/permdock-data/SKILL.md +57 -0
  338. package/skills/permdock-data/references/queries-and-rls.md +62 -0
  339. package/skills/permdock-data/references/relationships.md +67 -0
  340. package/skills/permdock-tenancy/SKILL.md +80 -0
  341. package/skills/permdock-tenancy/references/ownership-and-custom-roles.md +89 -0
  342. package/skills/permdock-wire/SKILL.md +116 -0
  343. package/skills/permdock-wire/references/adapters.md +492 -0
  344. package/skills/permdock-wire/references/policy-options.md +45 -0
@@ -0,0 +1,682 @@
1
+ import { n as isReadonlyArray, t as compact } from "../compact-y6vfu2_f.js";
2
+ import { n as freezeDeep } from "../freeze-CrU8nQeX.js";
3
+ import { _ as listPermissions, c as getResource } from "../permissions-DVoF6dMt.js";
4
+ import { n as PermDockValidationError } from "../validation-error-CnjZ4t92.js";
5
+ import { a as deniedMessage, i as approvalMessage, n as PermDockDeniedError, t as PermDockApprovalRequiredError } from "../errors-Cz5zn0mW.js";
6
+ import { d as isArazzoSimulateInput } from "../snapshot-Enxd0n-s.js";
7
+ import { n as isThenable } from "../thenable-okc2xDsj.js";
8
+ import { t as createPermDock$1 } from "../permdock-CzqXjCpU.js";
9
+ import { s as isRecord } from "../map-AcxK9o_D.js";
10
+ import { a as postJson, c as ttlMs, i as joinUrl, n as denied, o as resourceIdOf, r as granted, s as ttlCache, t as cacheKey } from "../shared-DRu8VFVM.js";
11
+ //#region src/pdp/create.ts
12
+ function withoutProviders(policy) {
13
+ if (policy.providers === void 0 || policy.providers.length === 0) return policy;
14
+ return freezeDeep(compact({
15
+ permissions: policy.permissions,
16
+ roles: policy.roles,
17
+ rolesByName: policy.rolesByName,
18
+ grants: policy.grants,
19
+ vocabulary: policy.vocabulary,
20
+ scopes: policy.scopes,
21
+ principal(user) {
22
+ return policy.principal(user);
23
+ },
24
+ subject(user) {
25
+ return policy.subject(user);
26
+ },
27
+ context(user) {
28
+ return policy.context?.(user);
29
+ },
30
+ validate: policy.validate,
31
+ onDenied: policy.onDenied,
32
+ fingerprint: policy.fingerprint,
33
+ resources: policy.resources,
34
+ index: policy.index
35
+ }));
36
+ }
37
+ function providerFor(providers, permission) {
38
+ for (const provider of providers) if (provider.handles(permission)) return provider;
39
+ }
40
+ function idFieldOf(policy, permission) {
41
+ return getResource(policy.permissions, permission.resource)?.id ?? "id";
42
+ }
43
+ function isExplicitDeny(decision) {
44
+ return decision.outcome === "denied" && decision.denials.some((denial) => denial.reason === "deny");
45
+ }
46
+ function isLocalShortCircuit(decision) {
47
+ if (decision.outcome !== "denied") return false;
48
+ if (isExplicitDeny(decision)) return true;
49
+ return decision.denials.some((denial) => {
50
+ switch (denial.reason) {
51
+ case "no-grant":
52
+ case "inactive-grant": return false;
53
+ case "pdp-denied":
54
+ case "pdp-unavailable":
55
+ case "pdp-invalid-response": return false;
56
+ case "anonymous":
57
+ case "validation":
58
+ case "not-delegated":
59
+ case "no-delegation":
60
+ case "condition":
61
+ case "deny":
62
+ case "closure-error":
63
+ case "opaque-condition":
64
+ case "server-only":
65
+ case "insufficient-user-authentication":
66
+ case "not-entitled":
67
+ case "purpose":
68
+ case "reason-required":
69
+ case "actor-required":
70
+ case "limit":
71
+ case "limit-unavailable":
72
+ case "relation-depth":
73
+ case "relation-unavailable":
74
+ case "tenant-mismatch":
75
+ case "no-membership":
76
+ case "scope":
77
+ case "expired-membership":
78
+ case "stale-credentials":
79
+ case "unknown-role":
80
+ case "last-holder":
81
+ case "max-holders":
82
+ case "transfer-only":
83
+ case "not-assignable-by":
84
+ case "self-demotion":
85
+ case "externally-managed":
86
+ case "not-allowed-for-membership":
87
+ case "conflicting-role":
88
+ case "approval":
89
+ case "stale-approval":
90
+ case "undocumented":
91
+ case "unsupported":
92
+ case "exceeds-creator":
93
+ case "credential-policy": return true;
94
+ default: return denial.reason;
95
+ }
96
+ });
97
+ }
98
+ function wrap(permdock, policy, subject, providers) {
99
+ const decideLocal = permdock.decide;
100
+ const decide = async (permission, data, options) => {
101
+ const local = decideLocal(permission, data, options);
102
+ const provider = providerFor(providers, permission);
103
+ if (provider === void 0 || isLocalShortCircuit(local)) return local;
104
+ try {
105
+ return await provider.decide({
106
+ permission,
107
+ data,
108
+ subject,
109
+ local
110
+ });
111
+ } catch {
112
+ return denied("pdp-unavailable");
113
+ }
114
+ };
115
+ /** The local trace; a remote decision evaluated no local grant, so its trace is empty. */
116
+ const explain = async (permission, data, options) => {
117
+ const decision = await decide(permission, data, {
118
+ ...options,
119
+ source: options?.source ?? "explain",
120
+ explain: true
121
+ });
122
+ if (decision.trace !== void 0) return decision;
123
+ return freezeDeep({
124
+ ...decision,
125
+ trace: {
126
+ evaluated: 0,
127
+ allows: [],
128
+ denies: [],
129
+ skipped: []
130
+ }
131
+ });
132
+ };
133
+ const permittedIds = async (provider, permission) => {
134
+ if (provider?.permitted === void 0 || subject.principal === null) return;
135
+ try {
136
+ return await provider.permitted({
137
+ permission,
138
+ subject
139
+ });
140
+ } catch {
141
+ return null;
142
+ }
143
+ };
144
+ const can = async (permission, data, options) => {
145
+ try {
146
+ return (await decide(permission, data, options)).outcome === "granted";
147
+ } catch {
148
+ return false;
149
+ }
150
+ };
151
+ const assert = async (permission, data, options) => {
152
+ const decision = await decide(permission, data, {
153
+ ...options,
154
+ source: options?.source ?? "assert"
155
+ });
156
+ if (decision.outcome === "granted") return decision;
157
+ const onDenied = options?.onDenied ?? policy.onDenied;
158
+ if (onDenied !== void 0) onDenied(decision);
159
+ const resource = getResource(policy.permissions, permission.resource);
160
+ const resourceId = data !== null && typeof data === "object" ? data[resource?.id ?? "id"] : void 0;
161
+ const resourceRef = compact({
162
+ type: permission.resource,
163
+ id: resourceId === void 0 ? void 0 : String(resourceId)
164
+ });
165
+ if (decision.outcome === "approval-required") throw new PermDockApprovalRequiredError({
166
+ decision,
167
+ permission: permission.key,
168
+ scope: permission.scope,
169
+ resource: resourceRef,
170
+ message: approvalMessage(permission.key, decision.reason, decision.token)
171
+ });
172
+ if (decision.denials.some((denial) => denial.reason === "validation")) {
173
+ const detail = decision.denials[0]?.detail;
174
+ if (detail instanceof PermDockValidationError) throw detail;
175
+ }
176
+ throw new PermDockDeniedError({
177
+ decision,
178
+ permission: permission.key,
179
+ scope: permission.scope,
180
+ resource: resourceRef,
181
+ subject,
182
+ message: deniedMessage(permission.key, subject.principal?.id, decision.denials, decision.alternatives.map((leaf) => leaf.key))
183
+ });
184
+ };
185
+ const simulate = ((input, options) => {
186
+ if (isReadonlyArray(input)) return Promise.all(input.map(([permission, data]) => decide(permission, data, compact({
187
+ source: "simulate",
188
+ now: options?.now
189
+ }))));
190
+ if (isArazzoSimulateInput(input)) return permdock.simulate(input);
191
+ return wrap(permdock.simulate(input), policy, subject, providers);
192
+ });
193
+ return {
194
+ can,
195
+ decide,
196
+ assert,
197
+ explain,
198
+ async filter(permission, rows, options) {
199
+ const next = {
200
+ ...options,
201
+ source: "filter"
202
+ };
203
+ const provider = providerFor(providers, permission);
204
+ const ids = await permittedIds(provider, permission);
205
+ if (ids === void 0) {
206
+ const decisions = await Promise.all(rows.map((row) => decide(permission, row, next)));
207
+ return rows.filter((_, index) => decisions[index]?.outcome === "granted");
208
+ }
209
+ const allowed = new Set(ids ?? []);
210
+ const field = idFieldOf(policy, permission);
211
+ return rows.filter((row) => {
212
+ const id = resourceIdOf(row, field);
213
+ return allowed.has(id) && !isLocalShortCircuit(decideLocal(permission, row, next));
214
+ });
215
+ },
216
+ pick: permdock.pick.bind(permdock),
217
+ async where(permission) {
218
+ const provider = providerFor(providers, permission);
219
+ if (provider === void 0) return permdock.where(permission);
220
+ const ids = await permittedIds(provider, permission);
221
+ if (ids === void 0) return {
222
+ condition: {
223
+ op: "or",
224
+ conditions: []
225
+ },
226
+ partial: true
227
+ };
228
+ if (ids === null || ids.length === 0) return {
229
+ condition: {
230
+ op: "or",
231
+ conditions: []
232
+ },
233
+ partial: false
234
+ };
235
+ const remote = {
236
+ op: "in",
237
+ field: idFieldOf(policy, permission),
238
+ value: [...ids]
239
+ };
240
+ const local = permdock.where(permission);
241
+ return local.condition.op !== "or" || local.condition.conditions.length > 0 ? {
242
+ condition: {
243
+ op: "and",
244
+ conditions: [local.condition, remote]
245
+ },
246
+ partial: local.partial
247
+ } : {
248
+ condition: remote,
249
+ partial: true
250
+ };
251
+ },
252
+ actions: permdock.actions.bind(permdock),
253
+ simulate,
254
+ snapshot: permdock.snapshot.bind(permdock),
255
+ on: permdock.on.bind(permdock),
256
+ tenant: (id) => {
257
+ const next = permdock.tenant(id);
258
+ return wrap(next, policy, next.subject, providers);
259
+ },
260
+ team: (id) => {
261
+ const next = permdock.team(id);
262
+ return wrap(next, policy, next.subject, providers);
263
+ },
264
+ derive: (options) => {
265
+ const next = permdock.derive(options);
266
+ return isThenable(next) ? next.then((derived) => wrap(derived, policy, derived.subject, providers)) : wrap(next, policy, next.subject, providers);
267
+ },
268
+ memberships: permdock.memberships.bind(permdock),
269
+ tenants: permdock.tenants.bind(permdock),
270
+ heldRoles: permdock.heldRoles.bind(permdock),
271
+ audiences: permdock.audiences.bind(permdock),
272
+ assignableRoles: permdock.assignableRoles.bind(permdock),
273
+ assignablePermissions: permdock.assignablePermissions.bind(permdock),
274
+ assignableLevels: permdock.assignableLevels.bind(permdock),
275
+ decideRoleChange: permdock.decideRoleChange.bind(permdock),
276
+ loadRelations: permdock.loadRelations.bind(permdock),
277
+ whoCan: permdock.whoCan.bind(permdock),
278
+ activate: permdock.activate.bind(permdock),
279
+ permissions: permdock.permissions,
280
+ roles: permdock.roles,
281
+ plans: permdock.plans,
282
+ subject
283
+ };
284
+ }
285
+ async function createPermDock(policy, user, options = {}) {
286
+ const localPolicy = withoutProviders(policy);
287
+ const permdock = await createPermDock$1(localPolicy, user, options);
288
+ return wrap(permdock, localPolicy, permdock.subject, policy.providers ?? []);
289
+ }
290
+ //#endregion
291
+ //#region src/pdp/relations.ts
292
+ function relationProvider(backend) {
293
+ const callbacks = /* @__PURE__ */ new Map();
294
+ for (const [permission, callback] of backend.map) callbacks.set(permission.key, callback);
295
+ const timeout = backend.timeout ?? 300;
296
+ const decisions = ttlCache(ttlMs(backend.cache));
297
+ const lists = ttlCache(ttlMs(backend.cache));
298
+ const fetcher = backend.fetch ?? fetch;
299
+ const post = async (url, body) => {
300
+ const posted = await postJson(fetcher, url, body, {
301
+ auth: backend.auth,
302
+ timeout
303
+ });
304
+ return posted.ok ? posted.response : null;
305
+ };
306
+ function tupleFor(permission, subject, data) {
307
+ const callback = callbacks.get(permission.key);
308
+ if (callback === void 0) return null;
309
+ try {
310
+ return callback(subject, data);
311
+ } catch {
312
+ return "invalid";
313
+ }
314
+ }
315
+ return {
316
+ name: backend.name,
317
+ handles(permission) {
318
+ return callbacks.has(permission.key);
319
+ },
320
+ async decide(request) {
321
+ if (request.subject.principal === null) return denied("anonymous");
322
+ const tuple = tupleFor(request.permission, request.subject, request.data);
323
+ if (tuple === "invalid") return denied("pdp-invalid-response");
324
+ if (tuple === null) return denied("pdp-denied");
325
+ const key = cacheKey(request.subject, request.permission, tuple);
326
+ const hit = decisions.get(key);
327
+ if (hit !== void 0) return hit;
328
+ const result = await backend.check(tuple, post);
329
+ if (result === "unavailable") return denied("pdp-unavailable");
330
+ if (result === "invalid") return denied("pdp-invalid-response");
331
+ const decision = result ? granted(backend.name, request.permission, request.subject, request.data) : denied("pdp-denied");
332
+ decisions.set(key, decision);
333
+ return decision;
334
+ },
335
+ async permitted(request) {
336
+ if (request.subject.principal === null) return [];
337
+ const tuple = tupleFor(request.permission, request.subject, void 0);
338
+ if (tuple === "invalid") return null;
339
+ if (tuple === null) return [];
340
+ const key = cacheKey(request.subject, request.permission, tuple);
341
+ const hit = lists.get(key);
342
+ if (hit !== void 0) return hit;
343
+ const ids = await backend.list(tuple, post);
344
+ if (ids !== null) lists.set(key, ids);
345
+ return ids;
346
+ }
347
+ };
348
+ }
349
+ async function jsonOf(response) {
350
+ if (response === null) return;
351
+ try {
352
+ return await response.json();
353
+ } catch {
354
+ return null;
355
+ }
356
+ }
357
+ /**
358
+ * An OpenFGA store as a decision provider: `check` decides one row and
359
+ * `list-objects` lists the ids `filter` and `where` use.
360
+ */
361
+ function openfga(options) {
362
+ const store = joinUrl(options.url, `/stores/${encodeURIComponent(options.storeId)}`);
363
+ const model = compact({ authorization_model_id: options.authorizationModelId });
364
+ return relationProvider(compact({
365
+ name: "openfga",
366
+ map: options.map,
367
+ auth: options.auth,
368
+ timeout: options.timeout,
369
+ cache: options.cache,
370
+ fetch: options.fetch,
371
+ async check(tuple, post) {
372
+ if (tuple.id === void 0) return "invalid";
373
+ const body = await jsonOf(await post(`${store}/check`, {
374
+ ...model,
375
+ tuple_key: {
376
+ user: tuple.user,
377
+ relation: tuple.relation,
378
+ object: `${tuple.type}:${tuple.id}`
379
+ }
380
+ }));
381
+ if (body === void 0) return "unavailable";
382
+ return isRecord(body) && typeof body["allowed"] === "boolean" ? body["allowed"] : "invalid";
383
+ },
384
+ async list(tuple, post) {
385
+ const body = await jsonOf(await post(`${store}/list-objects`, {
386
+ ...model,
387
+ type: tuple.type,
388
+ relation: tuple.relation,
389
+ user: tuple.user
390
+ }));
391
+ if (!isRecord(body) || !Array.isArray(body["objects"])) return null;
392
+ const prefix = `${tuple.type}:`;
393
+ const ids = [];
394
+ for (const object of body["objects"]) {
395
+ if (typeof object !== "string" || !object.startsWith(prefix)) return null;
396
+ ids.push(object.slice(prefix.length));
397
+ }
398
+ return Object.freeze(ids);
399
+ }
400
+ }));
401
+ }
402
+ function subjectReference(check) {
403
+ return compact({
404
+ object: {
405
+ objectType: check.subject.type,
406
+ objectId: check.subject.id
407
+ },
408
+ optionalRelation: check.subject.relation
409
+ });
410
+ }
411
+ /**
412
+ * A SpiceDB HTTP gateway as a decision provider: `CheckPermission` decides
413
+ * one row and `LookupResources` lists the ids `filter` and `where` use. A
414
+ * conditional permissionship (a caveat missing context) is a denial.
415
+ */
416
+ function spicedb(options) {
417
+ const consistency = options.consistency === "fully-consistent" ? { fullyConsistent: true } : { minimizeLatency: true };
418
+ return relationProvider(compact({
419
+ name: "spicedb",
420
+ map: options.map,
421
+ auth: { bearer: options.token },
422
+ timeout: options.timeout,
423
+ cache: options.cache,
424
+ fetch: options.fetch,
425
+ async check(check, post) {
426
+ if (check.resource.id === void 0) return "invalid";
427
+ const body = await jsonOf(await post(joinUrl(options.url, "/v1/permissions/check"), {
428
+ consistency,
429
+ resource: {
430
+ objectType: check.resource.type,
431
+ objectId: check.resource.id
432
+ },
433
+ permission: check.permission,
434
+ subject: subjectReference(check)
435
+ }));
436
+ if (body === void 0) return "unavailable";
437
+ if (!isRecord(body)) return "invalid";
438
+ switch (body["permissionship"]) {
439
+ case "PERMISSIONSHIP_HAS_PERMISSION": return true;
440
+ case "PERMISSIONSHIP_NO_PERMISSION":
441
+ case "PERMISSIONSHIP_CONDITIONAL_PERMISSION": return false;
442
+ default: return "invalid";
443
+ }
444
+ },
445
+ async list(check, post) {
446
+ const response = await post(joinUrl(options.url, "/v1/permissions/resources"), {
447
+ consistency,
448
+ resourceObjectType: check.resource.type,
449
+ permission: check.permission,
450
+ subject: subjectReference(check)
451
+ });
452
+ if (response === null) return null;
453
+ let text;
454
+ try {
455
+ text = await response.text();
456
+ } catch {
457
+ return null;
458
+ }
459
+ const ids = [];
460
+ for (const line of text.split("\n")) {
461
+ if (line.trim() === "") continue;
462
+ let parsed;
463
+ try {
464
+ parsed = JSON.parse(line);
465
+ } catch {
466
+ return null;
467
+ }
468
+ const result = isRecord(parsed) ? parsed["result"] : void 0;
469
+ if (!isRecord(result) || typeof result["resourceObjectId"] !== "string") return null;
470
+ if (result["permissionship"] === "LOOKUP_PERMISSIONSHIP_HAS_PERMISSION") ids.push(result["resourceObjectId"]);
471
+ }
472
+ return Object.freeze(ids);
473
+ }
474
+ }));
475
+ }
476
+ //#endregion
477
+ //#region src/pdp/remote.ts
478
+ const DEFAULT_EVALUATION = "/access/v1/evaluation";
479
+ const DEFAULT_EVALUATIONS = "/access/v1/evaluations";
480
+ const MAX_SEARCH_PAGES = 100;
481
+ function delegatedKeys(listed) {
482
+ if (listed === void 0) return null;
483
+ const keys = /* @__PURE__ */ new Set();
484
+ for (const item of listed) for (const leaf of listPermissions(item)) keys.add(leaf.key);
485
+ return keys;
486
+ }
487
+ function parseDiscovery(url, body) {
488
+ if (!isRecord(body)) return null;
489
+ const evaluation = typeof body["access_evaluation_endpoint"] === "string" ? body["access_evaluation_endpoint"] : typeof body["policy_decision_point"] === "string" ? joinUrl(body["policy_decision_point"], DEFAULT_EVALUATION) : joinUrl(url, DEFAULT_EVALUATION);
490
+ return compact({
491
+ evaluation,
492
+ evaluations: typeof body["access_evaluations_endpoint"] === "string" ? body["access_evaluations_endpoint"] : joinUrl(url, DEFAULT_EVALUATIONS),
493
+ searchResource: typeof body["search_resource_endpoint"] === "string" ? body["search_resource_endpoint"] : void 0
494
+ });
495
+ }
496
+ function mapEvaluationBody(permission, data, subject, mapping) {
497
+ const defaultId = data !== null && typeof data === "object" ? data["id"] : void 0;
498
+ const mappedSubject = mapping?.subject?.(subject) ?? compact({
499
+ type: "user",
500
+ id: subject.principal?.id,
501
+ properties: compact({
502
+ orgId: subject.principal?.tenant,
503
+ roles: subject.principal?.roles,
504
+ actor: subject.actor,
505
+ delegation: subject.delegation
506
+ })
507
+ });
508
+ const mappedResource = mapping?.resource?.(permission, data) ?? compact({
509
+ type: permission.resource,
510
+ id: typeof defaultId === "string" || typeof defaultId === "number" ? String(defaultId) : resourceIdOf(data),
511
+ properties: data
512
+ });
513
+ return {
514
+ subject: mappedSubject,
515
+ action: mapping?.action?.(permission) ?? { name: permission.action },
516
+ resource: mappedResource,
517
+ context: compact({
518
+ tenant: subject.principal?.tenant,
519
+ actor: subject.actor,
520
+ delegation: subject.delegation
521
+ })
522
+ };
523
+ }
524
+ function parseRemoteDecision(body, permission, subject, data) {
525
+ if (!isRecord(body) || typeof body["decision"] !== "boolean") return denied("pdp-invalid-response");
526
+ if (body["decision"]) return granted("pdp", permission, subject, data);
527
+ const context = isRecord(body["context"]) && isRecord(body["context"]["permdock"]) ? body["context"]["permdock"] : {};
528
+ if (context["outcome"] === "approval-required") {
529
+ const token = typeof context["token"] === "string" ? context["token"] : "";
530
+ return {
531
+ outcome: "approval-required",
532
+ grant: {
533
+ role: "pdp",
534
+ permission: permission.key,
535
+ provider: "pdp",
536
+ approval: "human"
537
+ },
538
+ reason: "human",
539
+ token
540
+ };
541
+ }
542
+ if (Array.isArray(context["denials"])) {
543
+ const denials = context["denials"].flatMap((item) => {
544
+ if (!isRecord(item) || typeof item["reason"] !== "string") return [];
545
+ return [compact({
546
+ role: typeof item["role"] === "string" ? item["role"] : null,
547
+ reason: item["reason"],
548
+ detail: item["detail"]
549
+ })];
550
+ });
551
+ if (denials.length > 0) return {
552
+ outcome: "denied",
553
+ denials,
554
+ alternatives: []
555
+ };
556
+ }
557
+ return denied("pdp-denied");
558
+ }
559
+ function mapSearchBody(permission, subject, mapping) {
560
+ const body = mapEvaluationBody(permission, void 0, subject, mapping);
561
+ const resource = isRecord(body["resource"]) ? body["resource"] : {};
562
+ return {
563
+ ...body,
564
+ resource: { type: resource["type"] ?? permission.resource }
565
+ };
566
+ }
567
+ function searchIds(body, type) {
568
+ if (!isRecord(body) || !Array.isArray(body["results"])) return null;
569
+ const ids = [];
570
+ for (const entity of body["results"]) {
571
+ if (!isRecord(entity) || entity["type"] !== type || typeof entity["id"] !== "string") return null;
572
+ ids.push(entity["id"]);
573
+ }
574
+ return ids;
575
+ }
576
+ function nextToken(body) {
577
+ if (!isRecord(body) || !isRecord(body["page"])) return;
578
+ const token = body["page"]["next_token"];
579
+ return typeof token === "string" && token !== "" ? token : void 0;
580
+ }
581
+ function remotePdp(options) {
582
+ const keys = delegatedKeys(options.permissions);
583
+ const timeout = options.timeout ?? 300;
584
+ const decisions = ttlCache(ttlMs(options.cache));
585
+ const lists = ttlCache(ttlMs(options.cache));
586
+ const fetcher = options.fetch ?? fetch;
587
+ const post = {
588
+ auth: options.auth,
589
+ timeout
590
+ };
591
+ let discovery = options.endpoints?.evaluation === void 0 ? null : compact({
592
+ evaluation: options.endpoints.evaluation,
593
+ evaluations: options.endpoints.evaluations,
594
+ searchResource: options.endpoints.searchResource
595
+ });
596
+ async function discover() {
597
+ if (discovery !== null) return discovery;
598
+ try {
599
+ const signal = AbortSignal.timeout(timeout);
600
+ const response = await fetcher(joinUrl(options.url, "/.well-known/authzen-configuration"), { signal });
601
+ if (!response.ok) return null;
602
+ const parsed = parseDiscovery(options.url, await response.json());
603
+ if (parsed === null) return null;
604
+ discovery = parsed;
605
+ return parsed;
606
+ } catch {
607
+ return null;
608
+ }
609
+ }
610
+ async function readJson(url, body) {
611
+ const posted = await postJson(fetcher, url, body, post);
612
+ if (!posted.ok) return posted;
613
+ try {
614
+ return {
615
+ ok: true,
616
+ body: await posted.response.json()
617
+ };
618
+ } catch {
619
+ return { ok: false };
620
+ }
621
+ }
622
+ return {
623
+ name: "pdp",
624
+ handles(permission) {
625
+ return keys === null || keys.has(permission.key);
626
+ },
627
+ async decide(request) {
628
+ if (request.subject.principal === null) return denied("anonymous");
629
+ let body;
630
+ try {
631
+ body = mapEvaluationBody(request.permission, request.data, request.subject, options.mapping);
632
+ } catch {
633
+ return denied("pdp-invalid-response");
634
+ }
635
+ const key = cacheKey(request.subject, request.permission, body);
636
+ const hit = decisions.get(key);
637
+ if (hit !== void 0) return hit;
638
+ const endpoints = await discover();
639
+ if (endpoints === null) return denied("pdp-unavailable");
640
+ const posted = await readJson(endpoints.evaluation, body);
641
+ if (!posted.ok) return denied("pdp-unavailable");
642
+ const decision = parseRemoteDecision(posted.body, request.permission, request.subject, request.data);
643
+ if (decision.outcome === "granted" || decision.outcome === "approval-required" || decision.outcome === "denied" && decision.denials[0]?.reason === "pdp-denied") decisions.set(key, decision);
644
+ return decision;
645
+ },
646
+ async permitted(request) {
647
+ if (request.subject.principal === null) return [];
648
+ const endpoints = await discover();
649
+ if (endpoints === null) return null;
650
+ if (endpoints.searchResource === void 0) return;
651
+ let body;
652
+ try {
653
+ body = mapSearchBody(request.permission, request.subject, options.mapping);
654
+ } catch {
655
+ return null;
656
+ }
657
+ const key = cacheKey(request.subject, request.permission, body);
658
+ const hit = lists.get(key);
659
+ if (hit !== void 0) return hit;
660
+ const type = isRecord(body["resource"]) ? body["resource"]["type"] : void 0;
661
+ const url = endpoints.searchResource;
662
+ const collect = async (token, page, ids) => {
663
+ if (page >= MAX_SEARCH_PAGES) return null;
664
+ const posted = await readJson(url, token === void 0 ? body : {
665
+ ...body,
666
+ page: { token }
667
+ });
668
+ const found = posted.ok ? searchIds(posted.body, type) : null;
669
+ if (!posted.ok || found === null) return null;
670
+ const next = nextToken(posted.body);
671
+ return next === void 0 ? [...ids, ...found] : collect(next, page + 1, [...ids, ...found]);
672
+ };
673
+ const ids = await collect(void 0, 0, []);
674
+ if (ids === null) return null;
675
+ const frozen = Object.freeze([...ids]);
676
+ lists.set(key, frozen);
677
+ return frozen;
678
+ }
679
+ };
680
+ }
681
+ //#endregion
682
+ export { createPermDock, openfga, remotePdp, spicedb };