@noy-db/hub 0.6.0-pre.9 → 0.6.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.
- package/CHANGELOG.md +7079 -0
- package/codemods/0.6.0-pre.json +211 -0
- package/dist/api-6X2VLZ7J.js +20 -0
- package/dist/attestation/index.js +19 -19
- package/dist/{backup-KULFZ2T4.js → backup-VL4GRIEW.js} +36 -18
- package/dist/backup-VL4GRIEW.js.map +1 -0
- package/dist/blobs/index.js +22 -20
- package/dist/blobs/index.js.map +1 -1
- package/dist/broker/index.js +12 -12
- package/dist/cargo/index.js +35 -35
- package/dist/{chunk-KUDZVJKQ.js → chunk-22GR3O4J.js} +2 -2
- package/dist/{chunk-CCZJJ4I2.js → chunk-2CBFYXJX.js} +6 -6
- package/dist/{chunk-JJNOLSG5.js → chunk-2J5IT37K.js} +15 -16
- package/dist/chunk-2J5IT37K.js.map +1 -0
- package/dist/{chunk-PNKHAKQ7.js → chunk-2ZCWHCLF.js} +17 -10
- package/dist/chunk-2ZCWHCLF.js.map +1 -0
- package/dist/{chunk-2BMRJ6LQ.js → chunk-2ZT4INZ4.js} +8 -11
- package/dist/{chunk-2BMRJ6LQ.js.map → chunk-2ZT4INZ4.js.map} +1 -1
- package/dist/{chunk-FAXZQ5UF.js → chunk-323MN67Z.js} +2 -2
- package/dist/{chunk-VMCCGUQB.js → chunk-36CEG6CM.js} +2 -2
- package/dist/{chunk-PDLLCOGD.js → chunk-3OE2QNSM.js} +20 -17
- package/dist/chunk-3OE2QNSM.js.map +1 -0
- package/dist/{chunk-AHLJSVRL.js → chunk-3YGUHUJA.js} +5 -7
- package/dist/chunk-3YGUHUJA.js.map +1 -0
- package/dist/{chunk-ZJADGNYF.js → chunk-4AOERLTV.js} +1 -1
- package/dist/chunk-4AOERLTV.js.map +1 -0
- package/dist/{chunk-BRVW2GS5.js → chunk-4ATF4BLF.js} +87 -34
- package/dist/chunk-4ATF4BLF.js.map +1 -0
- package/dist/{chunk-747LRSOO.js → chunk-4K6BIMLF.js} +2 -2
- package/dist/{chunk-5O5HRRTV.js → chunk-5ATC6UT4.js} +7 -7
- package/dist/{chunk-5O5HRRTV.js.map → chunk-5ATC6UT4.js.map} +1 -1
- package/dist/{chunk-4GZ6XOVW.js → chunk-5F7BZAGV.js} +44 -42
- package/dist/chunk-5F7BZAGV.js.map +1 -0
- package/dist/{chunk-FNSMZQS4.js → chunk-5IHGJHWC.js} +2 -2
- package/dist/{chunk-4I72F5DF.js → chunk-5LZZQMIC.js} +11 -14
- package/dist/chunk-5LZZQMIC.js.map +1 -0
- package/dist/{chunk-HPLWFNG4.js → chunk-5O5ZSW7N.js} +2 -2
- package/dist/{chunk-CEJWMBXO.js → chunk-5OT4G5N5.js} +6 -2
- package/dist/chunk-5OT4G5N5.js.map +1 -0
- package/dist/{chunk-GAG7QOVO.js → chunk-64WHKBMP.js} +53 -18
- package/dist/chunk-64WHKBMP.js.map +1 -0
- package/dist/{chunk-7TSYBD3E.js → chunk-65JXA63J.js} +2 -2
- package/dist/{chunk-Z45YRGFO.js → chunk-6NR36UNB.js} +2 -2
- package/dist/{chunk-W77KZHCW.js → chunk-6RH7PRTL.js} +16 -17
- package/dist/chunk-6RH7PRTL.js.map +1 -0
- package/dist/{chunk-3JVXVJ7L.js → chunk-7OBIBPCV.js} +10 -10
- package/dist/{chunk-AR2JDFAE.js → chunk-7Q3RHOA5.js} +2 -2
- package/dist/chunk-7ZGPQOFV.js +190 -0
- package/dist/chunk-7ZGPQOFV.js.map +1 -0
- package/dist/{chunk-QULVCV3M.js → chunk-AJGGBXWA.js} +4 -4
- package/dist/{chunk-CADUYBQD.js → chunk-ATL3ZVXT.js} +2 -2
- package/dist/{chunk-DMQCLZ4Z.js → chunk-ATY3ZASK.js} +2 -2
- package/dist/{chunk-4HDYQL3J.js → chunk-B4CRUZPR.js} +2 -2
- package/dist/{chunk-RV3ARMPN.js → chunk-BMU2DS3S.js} +30 -21
- package/dist/chunk-BMU2DS3S.js.map +1 -0
- package/dist/{chunk-6SAFL5YE.js → chunk-BZ3WMOYX.js} +3 -3
- package/dist/{chunk-UHXCLPGC.js → chunk-C3XWJCG7.js} +2 -2
- package/dist/chunk-C3XWJCG7.js.map +1 -0
- package/dist/{chunk-HXGUIPQB.js → chunk-CKKN25P2.js} +3 -3
- package/dist/{chunk-3URQC7EH.js → chunk-CXPOG3ZY.js} +355 -132
- package/dist/chunk-CXPOG3ZY.js.map +1 -0
- package/dist/{chunk-3FSX6LDG.js → chunk-D2YFQ7XG.js} +18 -3
- package/dist/{chunk-3FSX6LDG.js.map → chunk-D2YFQ7XG.js.map} +1 -1
- package/dist/{chunk-52JPHN5N.js → chunk-D6SXRMZZ.js} +27 -149
- package/dist/chunk-D6SXRMZZ.js.map +1 -0
- package/dist/{chunk-2DHSSLOD.js → chunk-DECNV4QK.js} +13 -15
- package/dist/chunk-DECNV4QK.js.map +1 -0
- package/dist/{chunk-6BU3L4UE.js → chunk-DNKVKO7K.js} +7 -10
- package/dist/chunk-DNKVKO7K.js.map +1 -0
- package/dist/{chunk-6HFM7EIT.js → chunk-EHRIDNZX.js} +2 -2
- package/dist/{chunk-3737A6EA.js → chunk-EHW7NLGD.js} +127 -31
- package/dist/chunk-EHW7NLGD.js.map +1 -0
- package/dist/{chunk-BEFVYAR5.js → chunk-EQOTJL76.js} +4 -4
- package/dist/chunk-EQOTJL76.js.map +1 -0
- package/dist/{chunk-E6427JU2.js → chunk-EV2TDHQZ.js} +19 -3
- package/dist/chunk-EV2TDHQZ.js.map +1 -0
- package/dist/{chunk-WFUIE565.js → chunk-FNYCT27B.js} +17 -14
- package/dist/chunk-FNYCT27B.js.map +1 -0
- package/dist/{chunk-RTAMLDWP.js → chunk-FU5VYEYK.js} +2 -2
- package/dist/chunk-FX3UIDCS.js +66 -0
- package/dist/chunk-FX3UIDCS.js.map +1 -0
- package/dist/{chunk-7F4DBNSP.js → chunk-GANFIM2M.js} +135 -18
- package/dist/chunk-GANFIM2M.js.map +1 -0
- package/dist/{chunk-4VUPLMZ6.js → chunk-GCU42IG7.js} +66 -71
- package/dist/chunk-GCU42IG7.js.map +1 -0
- package/dist/{chunk-RXYYFSBB.js → chunk-GKTW3KLV.js} +4 -4
- package/dist/chunk-HK67PX4J.js +27 -0
- package/dist/chunk-HK67PX4J.js.map +1 -0
- package/dist/{chunk-OF3L2SD6.js → chunk-HOPNIR5R.js} +2 -2
- package/dist/{chunk-WLZ47GSL.js → chunk-HSJBJIB2.js} +12 -10
- package/dist/{chunk-WLZ47GSL.js.map → chunk-HSJBJIB2.js.map} +1 -1
- package/dist/{chunk-ADW22QSB.js → chunk-HWI7GHJZ.js} +4 -4
- package/dist/{chunk-GQ3BX5EA.js → chunk-I3ISCYT7.js} +2 -2
- package/dist/{chunk-YJ6IONGA.js → chunk-IWKCJCLP.js} +11 -3
- package/dist/{chunk-YJ6IONGA.js.map → chunk-IWKCJCLP.js.map} +1 -1
- package/dist/{chunk-NJDQ4YSV.js → chunk-IWQPYT6S.js} +4 -4
- package/dist/{chunk-JRKZTEZZ.js → chunk-J6I5VR6P.js} +444 -73
- package/dist/chunk-J6I5VR6P.js.map +1 -0
- package/dist/{chunk-2Z3NCLNX.js → chunk-JHYKSMVX.js} +7 -7
- package/dist/{chunk-6FJWSWFT.js → chunk-JIHWBKMQ.js} +3 -3
- package/dist/{chunk-YAWK6AWF.js → chunk-JKATP6OE.js} +2 -2
- package/dist/{chunk-PL2GHSCM.js → chunk-JMJSCI7U.js} +157 -90
- package/dist/chunk-JMJSCI7U.js.map +1 -0
- package/dist/{chunk-Q6TEJXBX.js → chunk-JXHNUYQO.js} +31 -49
- package/dist/chunk-JXHNUYQO.js.map +1 -0
- package/dist/{chunk-2GAJGUNM.js → chunk-JYPRZWCZ.js} +343 -229
- package/dist/chunk-JYPRZWCZ.js.map +1 -0
- package/dist/{chunk-5ZKS6ZE2.js → chunk-K6CPIK3R.js} +4 -4
- package/dist/chunk-K6CPIK3R.js.map +1 -0
- package/dist/{chunk-CDB2HVQW.js → chunk-KM6ZXG7U.js} +14 -15
- package/dist/chunk-KM6ZXG7U.js.map +1 -0
- package/dist/{chunk-DG27IUVI.js → chunk-LC6NE4IQ.js} +2 -2
- package/dist/{chunk-WASHZV34.js → chunk-LIR2DJWP.js} +63 -25
- package/dist/chunk-LIR2DJWP.js.map +1 -0
- package/dist/{chunk-VZ3XFUQ7.js → chunk-LUYPYCHY.js} +16 -22
- package/dist/chunk-LUYPYCHY.js.map +1 -0
- package/dist/{chunk-G6S5VVHP.js → chunk-M7WBE3OR.js} +10 -10
- package/dist/chunk-M7WBE3OR.js.map +1 -0
- package/dist/{chunk-VJFMXYKP.js → chunk-MPKP6L5E.js} +2 -2
- package/dist/{chunk-IGJCYUT5.js → chunk-NSITFOCJ.js} +1 -1
- package/dist/chunk-NSITFOCJ.js.map +1 -0
- package/dist/{chunk-FUHKW252.js → chunk-OCJ3JA4O.js} +2 -2
- package/dist/{chunk-VCETL77O.js → chunk-ONPVHX2Y.js} +36 -7
- package/dist/chunk-ONPVHX2Y.js.map +1 -0
- package/dist/{chunk-WLYIROCJ.js → chunk-OQMCFHUX.js} +2 -2
- package/dist/{chunk-JRCYZEHU.js → chunk-OR2FYRYR.js} +2 -2
- package/dist/{chunk-HNHCQ556.js → chunk-PFWE7FJG.js} +2 -2
- package/dist/{chunk-NPP5R7FF.js → chunk-PJX72ICF.js} +22 -18
- package/dist/chunk-PJX72ICF.js.map +1 -0
- package/dist/{chunk-U5O6GIWZ.js → chunk-POFYIGQ2.js} +3 -3
- package/dist/{chunk-35EBKWQU.js → chunk-QH47SQLD.js} +4 -4
- package/dist/{chunk-FZ6NYJ7L.js → chunk-QQRRKO7W.js} +11 -8
- package/dist/chunk-QQRRKO7W.js.map +1 -0
- package/dist/{chunk-HVQGCKY4.js → chunk-QVXZFJBU.js} +2 -2
- package/dist/{chunk-FMQJZH4R.js → chunk-RDB66EKD.js} +6 -6
- package/dist/{chunk-X56RTUK3.js → chunk-RJZQ2PVD.js} +3 -3
- package/dist/{chunk-SUFG5E73.js → chunk-RPRASGEY.js} +2 -2
- package/dist/{chunk-XWX7GL56.js → chunk-S2I5MYSA.js} +7 -10
- package/dist/chunk-S2I5MYSA.js.map +1 -0
- package/dist/{chunk-FFDNKRCY.js → chunk-S6PJ6ZKE.js} +2 -2
- package/dist/chunk-S6PJ6ZKE.js.map +1 -0
- package/dist/{chunk-JIUVJ4M7.js → chunk-S7PM7Z4K.js} +3 -3
- package/dist/{chunk-55LKVALY.js → chunk-T7IR4N2S.js} +1 -3
- package/dist/chunk-T7IR4N2S.js.map +1 -0
- package/dist/{chunk-N35NC4JH.js → chunk-TKBB62DN.js} +2 -2
- package/dist/{chunk-YPYHVOXP.js → chunk-UJ4Z67UQ.js} +2 -2
- package/dist/chunk-UJ4Z67UQ.js.map +1 -0
- package/dist/{chunk-7MNBICB5.js → chunk-W3HAIN6U.js} +16 -14
- package/dist/chunk-W3HAIN6U.js.map +1 -0
- package/dist/{chunk-4UVDI4XE.js → chunk-WPZ5FVAS.js} +4 -4
- package/dist/{chunk-MSWYQLMQ.js → chunk-XINT4VJA.js} +2 -2
- package/dist/{chunk-7G6VDWXB.js → chunk-XPEPMK4Y.js} +3 -3
- package/dist/chunk-XPEPMK4Y.js.map +1 -0
- package/dist/{chunk-W3TVWF6N.js → chunk-YCGLAANM.js} +2 -2
- package/dist/{chunk-O2ERS4UJ.js → chunk-YTUFV7U7.js} +80 -51
- package/dist/chunk-YTUFV7U7.js.map +1 -0
- package/dist/{chunk-FDX7OWWI.js → chunk-YYV53EHO.js} +2 -2
- package/dist/{chunk-HNGSV2YC.js → chunk-Z3BZXPRO.js} +67 -10
- package/dist/chunk-Z3BZXPRO.js.map +1 -0
- package/dist/{chunk-6NVPFKN3.js → chunk-ZIMQDXTQ.js} +92 -35
- package/dist/chunk-ZIMQDXTQ.js.map +1 -0
- package/dist/{chunk-5JY5TSVY.js → chunk-ZJUZOJVW.js} +25 -31
- package/dist/chunk-ZJUZOJVW.js.map +1 -0
- package/dist/{chunk-3IXIU6FP.js → chunk-ZY6P7M52.js} +7 -10
- package/dist/chunk-ZY6P7M52.js.map +1 -0
- package/dist/{chunk-BWVKEOPE.js → chunk-ZYZJLYNS.js} +7 -11
- package/dist/chunk-ZYZJLYNS.js.map +1 -0
- package/dist/classified/index.js +5 -5
- package/dist/{classified-marker-2KJAXRRO.js → classified-marker-AZDSDG6V.js} +3 -3
- package/dist/collection-facade-WSUAYFJ4.js +45 -0
- package/dist/{computed-6G5M3UPH.js → computed-VG2PCM4L.js} +3 -3
- package/dist/consent/index.js +10 -10
- package/dist/cover/index.js +10 -3
- package/dist/custody/index.js +12 -11
- package/dist/{dead-filter-DCB62VWW.js → dead-filter-JNQNB3TA.js} +2 -2
- package/dist/debug/index.js +1 -1
- package/dist/{delegation-MO7YZYJS.js → delegation-5F36DRDH.js} +24 -23
- package/dist/delegation-5F36DRDH.js.map +1 -0
- package/dist/derivations/index.js +12 -12
- package/dist/derive-MPOGZ4NR.js +22 -0
- package/dist/directory/index.js +10 -10
- package/dist/{dispatch-MJ6SHB3Y.js → dispatch-3ZA733EY.js} +18 -18
- package/dist/{dispatch-FZEAWKVM.js → dispatch-TNM5CRLZ.js} +9 -6
- package/dist/dispatch-TNM5CRLZ.js.map +1 -0
- package/dist/{enclave-JU4YIEPB.js → enclave-Y2ALNDRD.js} +31 -9
- package/dist/executor-BBEEUFO3.js +9 -0
- package/dist/executor-G6G3YEWR.js +9 -0
- package/dist/executor-ZUTUMTPA.js +29 -0
- package/dist/export-accessible-S3KEB763.js +23 -0
- package/dist/extract-partition-KVCTSUVE.js +38 -0
- package/dist/{fanout-sidecar-NNAJQXMX.js → fanout-sidecar-3QZU7ZZX.js} +18 -27
- package/dist/fanout-sidecar-3QZU7ZZX.js.map +1 -0
- package/dist/find-V4FN5ITT.js +11 -0
- package/dist/forget/index.js +9 -9
- package/dist/guards/index.js +7 -7
- package/dist/history/index.js +23 -20
- package/dist/history/index.js.map +1 -1
- package/dist/i18n/index.js +14 -14
- package/dist/index.d.ts +30 -13
- package/dist/index.js +180 -188
- package/dist/index.js.map +1 -1
- package/dist/indexing/index.js +4 -4
- package/dist/introspection/index.js +11 -11
- package/dist/issue-5CFBWBRX.js +19 -0
- package/dist/kernel/collection.d.ts +8 -2
- package/dist/kernel/constants.d.ts +36 -0
- package/dist/kernel/enclave/crypto.d.ts +52 -4
- package/dist/kernel/enclave/index.d.ts +10 -3
- package/dist/kernel/enclave/record-aad.d.ts +131 -0
- package/dist/kernel/enclave/record-envelope.d.ts +76 -0
- package/dist/kernel/enclave/record-keys/envelope-body.d.ts +34 -2
- package/dist/kernel/enclave/record-keys/lifecycle.d.ts +22 -5
- package/dist/kernel/enclave/record-keys/record-codec.d.ts +47 -14
- package/dist/kernel/enclave/record-keys/rekey-blob.d.ts +88 -0
- package/dist/kernel/enclave/record-keys/rekey.d.ts +91 -0
- package/dist/kernel/enclave/record-keys/tombstone.d.ts +3 -2
- package/dist/kernel/errors.d.ts +132 -12
- package/dist/kernel/merge-authority.d.ts +25 -0
- package/dist/kernel/noydb.d.ts +27 -4
- package/dist/kernel/query/builder.d.ts +51 -4
- package/dist/kernel/query/join.d.ts +27 -0
- package/dist/kernel/query/live.d.ts +31 -9
- package/dist/kernel/query/predicate.d.ts +9 -0
- package/dist/kernel/refs.d.ts +3 -1
- package/dist/kernel/sync-policy.d.ts +0 -2
- package/dist/kernel/tier-visibility.d.ts +34 -0
- package/dist/kernel/types.d.ts +111 -13
- package/dist/kernel/vault.d.ts +6 -6
- package/dist/kernel/via/index.d.ts +11 -2
- package/dist/kernel/via/reconcile.d.ts +12 -0
- package/dist/{ledger-AETNF4OM.js → ledger-MQIIOTZB.js} +11 -11
- package/dist/liberate-LW7OKVBH.js +25 -0
- package/dist/{link-set-E5HNY67I.js → link-set-5PJBBR63.js} +11 -11
- package/dist/{managed-secret-CWQ6PND5.js → managed-secret-ETDG6AAE.js} +11 -3
- package/dist/materialized-views/index.js +24 -24
- package/dist/migrate-cek-V3VDRV24.js +19 -0
- package/dist/migrate-cek-V3VDRV24.js.map +1 -0
- package/dist/money/index.js +5 -5
- package/dist/noydb-LFDRMYZ5.js +85 -0
- package/dist/overlay-views/index.js +4 -4
- package/dist/periods/index.js +12 -12
- package/dist/pod/index.js +79 -89
- package/dist/pod-handle-AZ3CXY5Y.js +41 -0
- package/dist/pod-handle-AZ3CXY5Y.js.map +1 -0
- package/dist/policy/index.js +11 -4
- package/dist/port/to/index.d.ts +4 -4
- package/dist/port/to/locator.d.ts +54 -8
- package/dist/port/with/i18n-strategy.d.ts +4 -1
- package/dist/port/with/lookup-strategy.d.ts +4 -1
- package/dist/port/with/merge-authority.d.ts +52 -0
- package/dist/port/with/service-bus.d.ts +0 -4
- package/dist/port/with/strategies.d.ts +2 -0
- package/dist/port/with/team-strategy.d.ts +5 -1
- package/dist/portability/index.js +8 -8
- package/dist/{post-register-2XSSMGEQ.js → post-register-QCJYRMIK.js} +6 -6
- package/dist/query/index.js +6 -6
- package/dist/reduce/index.js +6 -6
- package/dist/register-JBOEHTVX.js +32 -0
- package/dist/registry-5DYHQFJS.js +9 -0
- package/dist/registry-EANV44W2.js +9 -0
- package/dist/registry-J25H6VB4.js +19 -0
- package/dist/registry-R23SQUQH.js +18 -0
- package/dist/request-withdrawal-KQ4W4UT5.js +31 -0
- package/dist/{reveal-BW36KCOQ.js → reveal-W7BKZSUP.js} +6 -6
- package/dist/revoke-H3VSTAIE.js +24 -0
- package/dist/satellites/index.js +1 -1
- package/dist/schema-update/index.js +2 -2
- package/dist/sealed-record/index.js +20 -13
- package/dist/sealed-record/index.js.map +1 -1
- package/dist/search/index.js +4 -4
- package/dist/{seed-GDV5PT4R.js → seed-55FPOMYP.js} +20 -22
- package/dist/seed-55FPOMYP.js.map +1 -0
- package/dist/sequence/index.js +9 -9
- package/dist/session/index.js +10 -10
- package/dist/shadow/index.js +2 -2
- package/dist/share-link/index.js +1 -1
- package/dist/signer-53AQ3BU2.js +25 -0
- package/dist/snapshots/index.js +10 -10
- package/dist/snapshots/index.js.map +1 -1
- package/dist/{stale-ARHFVL5U.js → stale-TH7SSVRV.js} +10 -10
- package/dist/storage-WSF7ZKTL.js +23 -0
- package/dist/{store-coordination-provider-GFCUOBR6.js → store-coordination-provider-R27VRD6K.js} +18 -12
- package/dist/store-coordination-provider-R27VRD6K.js.map +1 -0
- package/dist/sync/index.js +11 -11
- package/dist/team/index.js +15 -14
- package/dist/tiers/index.js +11 -10
- package/dist/to/index.js +17 -9
- package/dist/to/index.js.map +1 -1
- package/dist/transactions/index.js +4 -4
- package/dist/{ulid-PTAIMDG4.js → ulid-VQW6ERQN.js} +2 -2
- package/dist/util/index.js +1 -1
- package/dist/vault-head/index.js +115 -0
- package/dist/vault-head/index.js.map +1 -0
- package/dist/{verify-RO5RTZOJ.js → verify-M5LQH43C.js} +5 -5
- package/dist/via/blob/index.d.ts +3 -0
- package/dist/via/lookup/handle.d.ts +4 -1
- package/dist/walk-NABCHDZN.js +21 -0
- package/dist/with-audit/periods/periods.d.ts +1 -1
- package/dist/with-audit/periods/strategy.d.ts +1 -1
- package/dist/with-audit/sealed-record/index.d.ts +13 -0
- package/dist/with-audit/tiers/index.d.ts +17 -2
- package/dist/with-cargo/adopt-partition.d.ts +1 -1
- package/dist/with-cargo/extract-partition.d.ts +1 -1
- package/dist/with-cargo/index.d.ts +1 -1
- package/dist/with-commit/history/history.d.ts +26 -0
- package/dist/with-commit/history/index.d.ts +2 -1
- package/dist/with-commit/history/ledger/store.d.ts +7 -1
- package/dist/with-commit/history/strategy.d.ts +11 -1
- package/dist/with-commit/numbering/index.d.ts +0 -5
- package/dist/with-commit/vault-head/active.d.ts +2 -0
- package/dist/with-commit/vault-head/head.d.ts +28 -0
- package/dist/with-commit/vault-head/index.d.ts +10 -0
- package/dist/with-commit/vault-head/strategy.d.ts +127 -0
- package/dist/with-commit/vault-head/verify.d.ts +90 -0
- package/dist/with-formula/materialized-views/dependency-analyzer.d.ts +4 -0
- package/dist/with-formula/materialized-views/projection-legs.d.ts +59 -0
- package/dist/with-formula/materialized-views/registry.d.ts +50 -0
- package/dist/with-formula/materialized-views/types.d.ts +68 -10
- package/dist/with-party/directory/cover/storage.d.ts +0 -8
- package/dist/with-party/directory/storage.d.ts +0 -11
- package/dist/with-party/directory/visibility.d.ts +0 -21
- package/dist/with-party/policy/storage.d.ts +0 -10
- package/dist/with-party/team/index.d.ts +1 -1
- package/dist/with-party/team/keyring.d.ts +139 -2
- package/dist/with-party/team/noydb-facade.d.ts +5 -1
- package/dist/with-party/team/roster-tag.d.ts +101 -0
- package/dist/with-party/team/tiers.d.ts +2 -1
- package/dist/with-pod/format.d.ts +10 -12
- package/dist/with-pod/index.d.ts +10 -10
- package/dist/with-pod/open.d.ts +2 -2
- package/dist/with-pod/pod-handle.d.ts +19 -0
- package/dist/with-pod/pod-store.d.ts +0 -8
- package/dist/with-pod/{bundle.d.ts → pod.d.ts} +11 -19
- package/dist/with-pod/ulid.d.ts +1 -1
- package/dist/with-shape/blobs/blob-compaction.d.ts +13 -0
- package/dist/with-shape/blobs/blob-set.d.ts +83 -11
- package/dist/with-shape/blobs/orphan-report.d.ts +62 -0
- package/dist/with-sync/engine.d.ts +54 -5
- package/dist/with-sync/strategy.d.ts +3 -0
- package/dist/withdraw-accessible-VCINIG6V.js +28 -0
- package/package.json +10 -4
- package/dist/api-RXUMEKT3.js +0 -20
- package/dist/backup-KULFZ2T4.js.map +0 -1
- package/dist/bundle-handle-GFNHT52M.js +0 -36
- package/dist/bundle-handle-GFNHT52M.js.map +0 -1
- package/dist/chunk-2DHSSLOD.js.map +0 -1
- package/dist/chunk-2GAJGUNM.js.map +0 -1
- package/dist/chunk-3737A6EA.js.map +0 -1
- package/dist/chunk-3IXIU6FP.js.map +0 -1
- package/dist/chunk-3URQC7EH.js.map +0 -1
- package/dist/chunk-4GZ6XOVW.js.map +0 -1
- package/dist/chunk-4I72F5DF.js.map +0 -1
- package/dist/chunk-4VUPLMZ6.js.map +0 -1
- package/dist/chunk-52JPHN5N.js.map +0 -1
- package/dist/chunk-55LKVALY.js.map +0 -1
- package/dist/chunk-5JY5TSVY.js.map +0 -1
- package/dist/chunk-5ZKS6ZE2.js.map +0 -1
- package/dist/chunk-6BU3L4UE.js.map +0 -1
- package/dist/chunk-6NVPFKN3.js.map +0 -1
- package/dist/chunk-7F4DBNSP.js.map +0 -1
- package/dist/chunk-7G6VDWXB.js.map +0 -1
- package/dist/chunk-7H73RIE3.js +0 -45
- package/dist/chunk-7H73RIE3.js.map +0 -1
- package/dist/chunk-7MNBICB5.js.map +0 -1
- package/dist/chunk-AFHQATY4.js +0 -47
- package/dist/chunk-AFHQATY4.js.map +0 -1
- package/dist/chunk-AHLJSVRL.js.map +0 -1
- package/dist/chunk-BEFVYAR5.js.map +0 -1
- package/dist/chunk-BRVW2GS5.js.map +0 -1
- package/dist/chunk-BWVKEOPE.js.map +0 -1
- package/dist/chunk-CDB2HVQW.js.map +0 -1
- package/dist/chunk-CEJWMBXO.js.map +0 -1
- package/dist/chunk-E6427JU2.js.map +0 -1
- package/dist/chunk-FFDNKRCY.js.map +0 -1
- package/dist/chunk-FZ6NYJ7L.js.map +0 -1
- package/dist/chunk-G6S5VVHP.js.map +0 -1
- package/dist/chunk-GAG7QOVO.js.map +0 -1
- package/dist/chunk-HNGSV2YC.js.map +0 -1
- package/dist/chunk-IGJCYUT5.js.map +0 -1
- package/dist/chunk-JJNOLSG5.js.map +0 -1
- package/dist/chunk-JRKZTEZZ.js.map +0 -1
- package/dist/chunk-NPP5R7FF.js.map +0 -1
- package/dist/chunk-O2ERS4UJ.js.map +0 -1
- package/dist/chunk-PDLLCOGD.js.map +0 -1
- package/dist/chunk-PL2GHSCM.js.map +0 -1
- package/dist/chunk-PNKHAKQ7.js.map +0 -1
- package/dist/chunk-Q6TEJXBX.js.map +0 -1
- package/dist/chunk-RV3ARMPN.js.map +0 -1
- package/dist/chunk-UHXCLPGC.js.map +0 -1
- package/dist/chunk-VCETL77O.js.map +0 -1
- package/dist/chunk-VZ3XFUQ7.js.map +0 -1
- package/dist/chunk-W77KZHCW.js.map +0 -1
- package/dist/chunk-WASHZV34.js.map +0 -1
- package/dist/chunk-WFUIE565.js.map +0 -1
- package/dist/chunk-XWX7GL56.js.map +0 -1
- package/dist/chunk-YPYHVOXP.js.map +0 -1
- package/dist/chunk-ZJADGNYF.js.map +0 -1
- package/dist/collection-facade-QEJIM6BC.js +0 -45
- package/dist/delegation-MO7YZYJS.js.map +0 -1
- package/dist/derive-IUA6JFLB.js +0 -22
- package/dist/dispatch-FZEAWKVM.js.map +0 -1
- package/dist/executor-CYJQLKKI.js +0 -9
- package/dist/executor-S4QIKEHW.js +0 -9
- package/dist/executor-YIQB2S6N.js +0 -29
- package/dist/export-accessible-4S36PQNR.js +0 -23
- package/dist/extract-partition-IO7FDZ2P.js +0 -38
- package/dist/fanout-sidecar-NNAJQXMX.js.map +0 -1
- package/dist/find-RBBYKXI7.js +0 -11
- package/dist/issue-RIVHSY2S.js +0 -19
- package/dist/liberate-GFN4C7RR.js +0 -24
- package/dist/noydb-ASEXNJS6.js +0 -83
- package/dist/register-4EFJCVYD.js +0 -32
- package/dist/registry-4SDHHOJ7.js +0 -18
- package/dist/registry-CZVINVQH.js +0 -9
- package/dist/registry-IKUR2MXD.js +0 -9
- package/dist/registry-OYTFGWVK.js +0 -19
- package/dist/request-withdrawal-KGXGDPVQ.js +0 -31
- package/dist/revoke-JFN773KF.js +0 -24
- package/dist/seed-GDV5PT4R.js.map +0 -1
- package/dist/signer-TA55QB6R.js +0 -25
- package/dist/storage-V7MTFAQJ.js +0 -23
- package/dist/store-coordination-provider-GFCUOBR6.js.map +0 -1
- package/dist/walk-3ZECBFDA.js +0 -21
- package/dist/with-pod/bundle-handle.d.ts +0 -9
- package/dist/withdraw-accessible-7PG4DYQK.js +0 -28
- /package/dist/{api-RXUMEKT3.js.map → api-6X2VLZ7J.js.map} +0 -0
- /package/dist/{chunk-KUDZVJKQ.js.map → chunk-22GR3O4J.js.map} +0 -0
- /package/dist/{chunk-CCZJJ4I2.js.map → chunk-2CBFYXJX.js.map} +0 -0
- /package/dist/{chunk-FAXZQ5UF.js.map → chunk-323MN67Z.js.map} +0 -0
- /package/dist/{chunk-VMCCGUQB.js.map → chunk-36CEG6CM.js.map} +0 -0
- /package/dist/{chunk-747LRSOO.js.map → chunk-4K6BIMLF.js.map} +0 -0
- /package/dist/{chunk-FNSMZQS4.js.map → chunk-5IHGJHWC.js.map} +0 -0
- /package/dist/{chunk-HPLWFNG4.js.map → chunk-5O5ZSW7N.js.map} +0 -0
- /package/dist/{chunk-7TSYBD3E.js.map → chunk-65JXA63J.js.map} +0 -0
- /package/dist/{chunk-Z45YRGFO.js.map → chunk-6NR36UNB.js.map} +0 -0
- /package/dist/{chunk-3JVXVJ7L.js.map → chunk-7OBIBPCV.js.map} +0 -0
- /package/dist/{chunk-AR2JDFAE.js.map → chunk-7Q3RHOA5.js.map} +0 -0
- /package/dist/{chunk-QULVCV3M.js.map → chunk-AJGGBXWA.js.map} +0 -0
- /package/dist/{chunk-CADUYBQD.js.map → chunk-ATL3ZVXT.js.map} +0 -0
- /package/dist/{chunk-DMQCLZ4Z.js.map → chunk-ATY3ZASK.js.map} +0 -0
- /package/dist/{chunk-4HDYQL3J.js.map → chunk-B4CRUZPR.js.map} +0 -0
- /package/dist/{chunk-6SAFL5YE.js.map → chunk-BZ3WMOYX.js.map} +0 -0
- /package/dist/{chunk-HXGUIPQB.js.map → chunk-CKKN25P2.js.map} +0 -0
- /package/dist/{chunk-6HFM7EIT.js.map → chunk-EHRIDNZX.js.map} +0 -0
- /package/dist/{chunk-RTAMLDWP.js.map → chunk-FU5VYEYK.js.map} +0 -0
- /package/dist/{chunk-RXYYFSBB.js.map → chunk-GKTW3KLV.js.map} +0 -0
- /package/dist/{chunk-OF3L2SD6.js.map → chunk-HOPNIR5R.js.map} +0 -0
- /package/dist/{chunk-ADW22QSB.js.map → chunk-HWI7GHJZ.js.map} +0 -0
- /package/dist/{chunk-GQ3BX5EA.js.map → chunk-I3ISCYT7.js.map} +0 -0
- /package/dist/{chunk-NJDQ4YSV.js.map → chunk-IWQPYT6S.js.map} +0 -0
- /package/dist/{chunk-2Z3NCLNX.js.map → chunk-JHYKSMVX.js.map} +0 -0
- /package/dist/{chunk-6FJWSWFT.js.map → chunk-JIHWBKMQ.js.map} +0 -0
- /package/dist/{chunk-YAWK6AWF.js.map → chunk-JKATP6OE.js.map} +0 -0
- /package/dist/{chunk-DG27IUVI.js.map → chunk-LC6NE4IQ.js.map} +0 -0
- /package/dist/{chunk-VJFMXYKP.js.map → chunk-MPKP6L5E.js.map} +0 -0
- /package/dist/{chunk-FUHKW252.js.map → chunk-OCJ3JA4O.js.map} +0 -0
- /package/dist/{chunk-WLYIROCJ.js.map → chunk-OQMCFHUX.js.map} +0 -0
- /package/dist/{chunk-JRCYZEHU.js.map → chunk-OR2FYRYR.js.map} +0 -0
- /package/dist/{chunk-HNHCQ556.js.map → chunk-PFWE7FJG.js.map} +0 -0
- /package/dist/{chunk-U5O6GIWZ.js.map → chunk-POFYIGQ2.js.map} +0 -0
- /package/dist/{chunk-35EBKWQU.js.map → chunk-QH47SQLD.js.map} +0 -0
- /package/dist/{chunk-HVQGCKY4.js.map → chunk-QVXZFJBU.js.map} +0 -0
- /package/dist/{chunk-FMQJZH4R.js.map → chunk-RDB66EKD.js.map} +0 -0
- /package/dist/{chunk-X56RTUK3.js.map → chunk-RJZQ2PVD.js.map} +0 -0
- /package/dist/{chunk-SUFG5E73.js.map → chunk-RPRASGEY.js.map} +0 -0
- /package/dist/{chunk-JIUVJ4M7.js.map → chunk-S7PM7Z4K.js.map} +0 -0
- /package/dist/{chunk-N35NC4JH.js.map → chunk-TKBB62DN.js.map} +0 -0
- /package/dist/{chunk-4UVDI4XE.js.map → chunk-WPZ5FVAS.js.map} +0 -0
- /package/dist/{chunk-MSWYQLMQ.js.map → chunk-XINT4VJA.js.map} +0 -0
- /package/dist/{chunk-W3TVWF6N.js.map → chunk-YCGLAANM.js.map} +0 -0
- /package/dist/{chunk-FDX7OWWI.js.map → chunk-YYV53EHO.js.map} +0 -0
- /package/dist/{classified-marker-2KJAXRRO.js.map → classified-marker-AZDSDG6V.js.map} +0 -0
- /package/dist/{collection-facade-QEJIM6BC.js.map → collection-facade-WSUAYFJ4.js.map} +0 -0
- /package/dist/{computed-6G5M3UPH.js.map → computed-VG2PCM4L.js.map} +0 -0
- /package/dist/{dead-filter-DCB62VWW.js.map → dead-filter-JNQNB3TA.js.map} +0 -0
- /package/dist/{derive-IUA6JFLB.js.map → derive-MPOGZ4NR.js.map} +0 -0
- /package/dist/{dispatch-MJ6SHB3Y.js.map → dispatch-3ZA733EY.js.map} +0 -0
- /package/dist/{enclave-JU4YIEPB.js.map → enclave-Y2ALNDRD.js.map} +0 -0
- /package/dist/{executor-CYJQLKKI.js.map → executor-BBEEUFO3.js.map} +0 -0
- /package/dist/{executor-S4QIKEHW.js.map → executor-G6G3YEWR.js.map} +0 -0
- /package/dist/{executor-YIQB2S6N.js.map → executor-ZUTUMTPA.js.map} +0 -0
- /package/dist/{export-accessible-4S36PQNR.js.map → export-accessible-S3KEB763.js.map} +0 -0
- /package/dist/{extract-partition-IO7FDZ2P.js.map → extract-partition-KVCTSUVE.js.map} +0 -0
- /package/dist/{find-RBBYKXI7.js.map → find-V4FN5ITT.js.map} +0 -0
- /package/dist/{issue-RIVHSY2S.js.map → issue-5CFBWBRX.js.map} +0 -0
- /package/dist/{ledger-AETNF4OM.js.map → ledger-MQIIOTZB.js.map} +0 -0
- /package/dist/{liberate-GFN4C7RR.js.map → liberate-LW7OKVBH.js.map} +0 -0
- /package/dist/{link-set-E5HNY67I.js.map → link-set-5PJBBR63.js.map} +0 -0
- /package/dist/{managed-secret-CWQ6PND5.js.map → managed-secret-ETDG6AAE.js.map} +0 -0
- /package/dist/{noydb-ASEXNJS6.js.map → noydb-LFDRMYZ5.js.map} +0 -0
- /package/dist/{post-register-2XSSMGEQ.js.map → post-register-QCJYRMIK.js.map} +0 -0
- /package/dist/{register-4EFJCVYD.js.map → register-JBOEHTVX.js.map} +0 -0
- /package/dist/{registry-4SDHHOJ7.js.map → registry-5DYHQFJS.js.map} +0 -0
- /package/dist/{registry-CZVINVQH.js.map → registry-EANV44W2.js.map} +0 -0
- /package/dist/{registry-IKUR2MXD.js.map → registry-J25H6VB4.js.map} +0 -0
- /package/dist/{registry-OYTFGWVK.js.map → registry-R23SQUQH.js.map} +0 -0
- /package/dist/{request-withdrawal-KGXGDPVQ.js.map → request-withdrawal-KQ4W4UT5.js.map} +0 -0
- /package/dist/{reveal-BW36KCOQ.js.map → reveal-W7BKZSUP.js.map} +0 -0
- /package/dist/{revoke-JFN773KF.js.map → revoke-H3VSTAIE.js.map} +0 -0
- /package/dist/{signer-TA55QB6R.js.map → signer-53AQ3BU2.js.map} +0 -0
- /package/dist/{stale-ARHFVL5U.js.map → stale-TH7SSVRV.js.map} +0 -0
- /package/dist/{storage-V7MTFAQJ.js.map → storage-WSF7ZKTL.js.map} +0 -0
- /package/dist/{ulid-PTAIMDG4.js.map → ulid-VQW6ERQN.js.map} +0 -0
- /package/dist/{verify-RO5RTZOJ.js.map → verify-M5LQH43C.js.map} +0 -0
- /package/dist/{walk-3ZECBFDA.js.map → walk-NABCHDZN.js.map} +0 -0
- /package/dist/{withdraw-accessible-7PG4DYQK.js.map → withdraw-accessible-VCINIG6V.js.map} +0 -0
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import type { NoydbStore, KeyringFile, KeyringAuthenticator, Role, Permissions, GrantOptions, RevokeOptions, UpdateUserOptions, UserInfo, EncryptedEnvelope, ExportCapability, ExportFormat, ImportCapability, VaultPolicyOnDisk, UserEnvelope } from '../../kernel/types.js';
|
|
2
2
|
import { type EnclaveKey, type EchoSecretParts } from '../../kernel/enclave/index.js';
|
|
3
|
+
import type { KeyringTamperedReason } from '../../kernel/errors.js';
|
|
3
4
|
import { type SecretPolicy, type EchoSecretPolicy } from '../../kernel/validation.js';
|
|
4
5
|
import type { DeviceSealProvider } from './device-seal.js';
|
|
5
6
|
/** In-memory representation of an unlocked keyring. */
|
|
@@ -9,6 +10,11 @@ export interface UnlockedKeyring {
|
|
|
9
10
|
readonly role: Role;
|
|
10
11
|
readonly permissions: Permissions;
|
|
11
12
|
readonly deks: Map<string, EnclaveKey>;
|
|
13
|
+
/**
|
|
14
|
+
* Unwrapped counterpart of {@link KeyringFile.pending_deks} — an
|
|
15
|
+
* uncommitted rotation (#1074). Empty in the normal state.
|
|
16
|
+
*/
|
|
17
|
+
readonly pendingDeks?: Map<string, EnclaveKey> | undefined;
|
|
12
18
|
/**
|
|
13
19
|
* The KEK, when this keyring was unlocked via tier 1 (secret) or
|
|
14
20
|
* a wrap-KEK tier-2 method (WebAuthn / OIDC). `null` when the
|
|
@@ -72,6 +78,23 @@ export interface UnlockedKeyring {
|
|
|
72
78
|
}
|
|
73
79
|
/** Mint a fresh wrapped-canary string. Deterministic for a given KEK. */
|
|
74
80
|
export declare function mintKeyringCanary(kek: EnclaveKey): Promise<string>;
|
|
81
|
+
/**
|
|
82
|
+
* The vault roster key held by this keyring, or `null` when the keyring
|
|
83
|
+
* carries none.
|
|
84
|
+
*
|
|
85
|
+
* Null is expected on the resume-style paths (`kek: null` sessions, tier-3
|
|
86
|
+
* PIN resume, plaintext mode) — none of which may write a keyring file.
|
|
87
|
+
* Every stamping site null-guards this exactly as it guards `kek`: minting a
|
|
88
|
+
* file without a verifiable `roster_tag` would be worse than refusing, since
|
|
89
|
+
* it is indistinguishable on the next load from a store having stripped it.
|
|
90
|
+
*/
|
|
91
|
+
export declare function rosterKeyOf(keyring: UnlockedKeyring): EnclaveKey | null;
|
|
92
|
+
/**
|
|
93
|
+
* Shared wording for the stamping-site guards — mirrors the `kek` guard's shape.
|
|
94
|
+
* Exported so every roster-stamping site in the hub raises ONE error with one
|
|
95
|
+
* wording, rather than each hand-copying it (`peer-recover`, `liberate`).
|
|
96
|
+
*/
|
|
97
|
+
export declare function requireRosterKey(keyring: UnlockedKeyring, fn: string): EnclaveKey;
|
|
75
98
|
/** Options for {@link loadKeyring} (#846b). */
|
|
76
99
|
export interface LoadKeyringOptions {
|
|
77
100
|
/** The user whose keyring to unlock. */
|
|
@@ -168,6 +191,100 @@ export declare function createOwnerKeyring(store: NoydbStore, vault: string, opt
|
|
|
168
191
|
export declare function grant(store: NoydbStore, vault: string, callerKeyring: UnlockedKeyring, options: GrantOptions): Promise<void>;
|
|
169
192
|
/** Revoke a user's access. Optionally rotate keys for affected collections. */
|
|
170
193
|
export declare function revoke(store: NoydbStore, vault: string, callerKeyring: UnlockedKeyring, options: RevokeOptions): Promise<void>;
|
|
194
|
+
/** What {@link verifyRoster} found. */
|
|
195
|
+
export interface RosterVerifyResult {
|
|
196
|
+
/**
|
|
197
|
+
* How many `_keyring` files were examined.
|
|
198
|
+
*
|
|
199
|
+
* Reported first, and deliberately: "nothing unverified" is equally true of a
|
|
200
|
+
* sweep that examined nothing, and a roster check that silently covered zero
|
|
201
|
+
* members would look identical to a healthy vault. Same lesson as the vault
|
|
202
|
+
* head's `no-expectations` verdict (#1101).
|
|
203
|
+
*/
|
|
204
|
+
readonly checked: number;
|
|
205
|
+
/** The files that failed authentication, and why. */
|
|
206
|
+
readonly unverified: ReadonlyArray<{
|
|
207
|
+
readonly userId: string;
|
|
208
|
+
readonly reason: KeyringTamperedReason;
|
|
209
|
+
}>;
|
|
210
|
+
}
|
|
211
|
+
export declare function verifyRoster(store: NoydbStore, vault: string, callerKeyring: UnlockedKeyring): Promise<RosterVerifyResult>;
|
|
212
|
+
/** What {@link quarantineKeyring} did. */
|
|
213
|
+
export interface QuarantineResult {
|
|
214
|
+
readonly userId: string;
|
|
215
|
+
/** Why the file could not be authenticated — the justification for removing it. */
|
|
216
|
+
readonly reason: KeyringTamperedReason;
|
|
217
|
+
/** Collections re-keyed as part of the removal. */
|
|
218
|
+
readonly rotated: readonly string[];
|
|
219
|
+
/**
|
|
220
|
+
* (member, collection) pairs whose access the rotation dropped — the OTHER
|
|
221
|
+
* members, who must be re-granted.
|
|
222
|
+
*
|
|
223
|
+
* Passed through from `rotateKeys` rather than discarded, because a
|
|
224
|
+
* quarantine rotates broadly (see the scope note on the function) and so
|
|
225
|
+
* de-provisions more people than the one being removed. An operator who is
|
|
226
|
+
* not told this discovers it as unrelated `NoAccessError`s later.
|
|
227
|
+
*/
|
|
228
|
+
readonly needsRegrant: RotateResult['needsRegrant'];
|
|
229
|
+
/**
|
|
230
|
+
* OTHER members whose own files also failed authentication, found while
|
|
231
|
+
* rotating. One forged file is rarely the only one, and the operator is
|
|
232
|
+
* already holding the tool for them.
|
|
233
|
+
*/
|
|
234
|
+
readonly alsoUnverified: RotateResult['unverified'];
|
|
235
|
+
}
|
|
236
|
+
/**
|
|
237
|
+
* Remove a `_keyring` file that cannot be authenticated, and re-key behind it
|
|
238
|
+
* (#1121).
|
|
239
|
+
*
|
|
240
|
+
* ## Why this is not a flag on `revoke`
|
|
241
|
+
*
|
|
242
|
+
* `revoke` reads the target's own `role` to decide whether the caller may
|
|
243
|
+
* revoke them, so it cannot act on a file it will not trust — which left a
|
|
244
|
+
* forged file removable only by editing the store by hand. Relaxing `revoke`
|
|
245
|
+
* conditionally would grow the safe path a parameter that turns it into the
|
|
246
|
+
* dangerous one; ADR 0003's standing rule is that if the implementation needs
|
|
247
|
+
* to weaken a guard, the design is wrong. This is a separate operation with its
|
|
248
|
+
* own contract, so `revoke`'s invariant stays absolute and the dangerous act is
|
|
249
|
+
* named at the call site rather than hidden in an option bag.
|
|
250
|
+
*
|
|
251
|
+
* ## The two properties that keep it from being a backdoor
|
|
252
|
+
*
|
|
253
|
+
* 1. **It refuses a file that verifies.** Otherwise it would delete any keyring
|
|
254
|
+
* while ignoring `canRevoke` — including an owner's, which `revoke` protects
|
|
255
|
+
* unconditionally.
|
|
256
|
+
* 2. **Because of (1) it can safely ignore the claimed `role` — and it must.**
|
|
257
|
+
* `canRevoke` refuses any target whose role reads `owner`, so a store that
|
|
258
|
+
* forged `"role":"owner"` onto its victim would otherwise make them
|
|
259
|
+
* permanently unremovable. Consulting the forged field is exactly the
|
|
260
|
+
* mistake this operation exists to avoid.
|
|
261
|
+
*
|
|
262
|
+
* Owner-only: the narrowest role that can always act, and quarantine
|
|
263
|
+
* deliberately consumes NO field of the file it is removing.
|
|
264
|
+
*
|
|
265
|
+
* ## Why it rotates, and why the scope comes from the CALLER
|
|
266
|
+
*
|
|
267
|
+
* Deleting the file is not a revocation — the store may decline the delete, and
|
|
268
|
+
* the member may already hold unwrapped DEKs. So this rotates, exactly as
|
|
269
|
+
* `revoke` does. The scope is every collection the CALLER holds, not the
|
|
270
|
+
* target's DEK map: that map is unauthenticated (#1115), so deriving the scope
|
|
271
|
+
* from it would let the store choose which collections survive a quarantine.
|
|
272
|
+
*
|
|
273
|
+
* ⚠️ **That is the security-correct scope, and it is NOT free.** An earlier
|
|
274
|
+
* draft of this comment called over-rotating "the safe direction"; a review
|
|
275
|
+
* probe disproved it. Rotation re-keys `store.list(vault, <name>)` plus the
|
|
276
|
+
* derived refs `rotateKeys` knows about, so a DEK slot whose ciphertext lives
|
|
277
|
+
* under a *different* collection name — `_blob`, whose data sits in
|
|
278
|
+
* `_blob_index`/`_blob_chunks`, and the `collection#tier` slots — is re-keyed
|
|
279
|
+
* without its data being re-encrypted, and that data then fails to open. That
|
|
280
|
+
* gap belongs to `rotateKeys` (it is reachable through an ordinary `revoke` of
|
|
281
|
+
* a whole-vault grantee, with no quarantine involved) and is filed as #1122,
|
|
282
|
+
* but a quarantine takes the maximal scope *unconditionally*, so it meets the
|
|
283
|
+
* gap every time rather than occasionally. Until that is fixed, treat a
|
|
284
|
+
* quarantine as an emergency operation with a real blast radius, and read
|
|
285
|
+
* `needsRegrant` afterwards.
|
|
286
|
+
*/
|
|
287
|
+
export declare function quarantineKeyring(store: NoydbStore, vault: string, callerKeyring: UnlockedKeyring, userId: string): Promise<QuarantineResult>;
|
|
171
288
|
/**
|
|
172
289
|
* Mutate `role`, `displayName`, and/or `permissions` on an existing
|
|
173
290
|
* keyring. Pure plaintext-header rewrite — no DEK rewrap, no KEK
|
|
@@ -217,6 +334,26 @@ export interface RotateResult {
|
|
|
217
334
|
readonly userId: string;
|
|
218
335
|
readonly collection: string;
|
|
219
336
|
}>;
|
|
337
|
+
/**
|
|
338
|
+
* Members skipped because their `_keyring` file failed roster verification
|
|
339
|
+
* (#1114).
|
|
340
|
+
*
|
|
341
|
+
* Rotation hands a member re-wrapped DEKs, so skipping one gives them
|
|
342
|
+
* **less**, never more: the file is left untouched and its wrappings for the
|
|
343
|
+
* rotated collections go stale. That is the same fail-closed end state as
|
|
344
|
+
* `needsRegrant`, but it needs a different remedy and so gets a different
|
|
345
|
+
* field — a `needsRegrant` entry is fixed by `grant()`, whereas one of these
|
|
346
|
+
* is a file that no longer authenticates and cannot be repaired by granting
|
|
347
|
+
* over it.
|
|
348
|
+
*
|
|
349
|
+
* Before this existed, one such file threw and took `revoke` and
|
|
350
|
+
* `rotateKeys` down vault-wide — the two operations most needed when a
|
|
351
|
+
* roster is suspect.
|
|
352
|
+
*/
|
|
353
|
+
readonly unverified: ReadonlyArray<{
|
|
354
|
+
readonly userId: string;
|
|
355
|
+
readonly reason: KeyringTamperedReason;
|
|
356
|
+
}>;
|
|
220
357
|
}
|
|
221
358
|
/** Options for {@link rotateKeys} (#846b — was a bare `string[]`). */
|
|
222
359
|
export interface RotateKeysOptions {
|
|
@@ -261,7 +398,7 @@ export interface EchoRecipientSecret extends EchoSecretParts {
|
|
|
261
398
|
*
|
|
262
399
|
* @public
|
|
263
400
|
*/
|
|
264
|
-
export interface
|
|
401
|
+
export interface PodRecipient {
|
|
265
402
|
/** User id stamped onto the keyring file in the bundle. */
|
|
266
403
|
readonly id: string;
|
|
267
404
|
/** Optional display name. Defaults to `id`. */
|
|
@@ -312,7 +449,7 @@ export interface BundleRecipient {
|
|
|
312
449
|
*
|
|
313
450
|
* @internal
|
|
314
451
|
*/
|
|
315
|
-
export declare function buildRecipientKeyringFile(callerKeyring: UnlockedKeyring, recipient:
|
|
452
|
+
export declare function buildRecipientKeyringFile(callerKeyring: UnlockedKeyring, recipient: PodRecipient): Promise<KeyringFile>;
|
|
316
453
|
/** List all users with access to a vault. */
|
|
317
454
|
export declare function listUsers(store: NoydbStore, vault: string): Promise<UserInfo[]>;
|
|
318
455
|
/**
|
|
@@ -19,7 +19,7 @@
|
|
|
19
19
|
* Internal service — reached through `noydb.team.rotateSecret(...)` etc.
|
|
20
20
|
*/
|
|
21
21
|
import type { NoydbOptions, NoydbStore, KeyringAuthenticator } from '../../kernel/types.js';
|
|
22
|
-
import type { RotateResult, RotateKeysOptions } from './keyring.js';
|
|
22
|
+
import type { RotateResult, RotateKeysOptions, RosterVerifyResult, QuarantineResult } from './keyring.js';
|
|
23
23
|
import { type RotateSecretInput, type RecoverSecretInput, type RecoverSecretResult, type RotateRecoveryOptions, type RotateRecoveryResult, type EnrollRecoveryResult, type RecoveryEnrollmentInput, type RecoveryProof } from './rotate-recover.js';
|
|
24
24
|
import { type RecoverUserOptions } from './peer-recover.js';
|
|
25
25
|
import { type PaperRecoveryEntry, type ShamirRecoveryEntry } from './recovery.js';
|
|
@@ -74,6 +74,10 @@ export declare class TeamFacade {
|
|
|
74
74
|
runRevoke(engine: (adapter: NoydbStore, vault: string, callerKeyring: UnlockedKeyring, options: RevokeOptions) => Promise<void>, vault: string, options: RevokeOptions, factors?: FactorProofBundle): Promise<void>;
|
|
75
75
|
/** Gate + run a `rotateKeys` engine. See `Noydb.rotate` for the public contract. */
|
|
76
76
|
runRotate(engine: (store: NoydbStore, vault: string, callerKeyring: UnlockedKeyring, opts: RotateKeysOptions) => Promise<RotateResult>, vault: string, collections: string[]): Promise<RotateResult>;
|
|
77
|
+
/** Gate + run the `verifyRoster` engine (#1121). See `Noydb.verifyRoster`. */
|
|
78
|
+
runVerifyRoster(engine: (store: NoydbStore, vault: string, callerKeyring: UnlockedKeyring) => Promise<RosterVerifyResult>, vault: string): Promise<RosterVerifyResult>;
|
|
79
|
+
/** Gate + run the `quarantineKeyring` engine (#1121). See `Noydb.quarantineKeyring`. */
|
|
80
|
+
runQuarantine(engine: (store: NoydbStore, vault: string, callerKeyring: UnlockedKeyring, userId: string) => Promise<QuarantineResult>, vault: string, userId: string, factors?: FactorProofBundle): Promise<QuarantineResult>;
|
|
77
81
|
/**
|
|
78
82
|
* Add a tier-2 authenticator slot to the calling user's keyring.
|
|
79
83
|
* Each slot independently wraps the SAME KEK under a method-specific
|
|
@@ -0,0 +1,101 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* #1096 — the authenticated half of a `_keyring` file's AUTHORITY.
|
|
3
|
+
*
|
|
4
|
+
* A `_keyring` file is stored plaintext (`_iv: ''`) so admins can edit a
|
|
5
|
+
* member's authority without holding that member's credential. That means
|
|
6
|
+
* `role`/`permissions` were authenticated by NOTHING — a hostile store could
|
|
7
|
+
* promote a viewer to admin by editing one word (proven in
|
|
8
|
+
* `__tests__/keyring-replay-escalation.test.ts`).
|
|
9
|
+
*
|
|
10
|
+
* The fix is a vault-wide ROSTER KEY, carried as a reserved DEK-map entry
|
|
11
|
+
* (`deks['_roster']`, see `ROSTER_KEY_ID`) so it reaches every member through
|
|
12
|
+
* the channels a DEK already travels — grant's `_`-prefix propagation,
|
|
13
|
+
* `persistKeyring`, the wrapped-DEKs recovery blob, `peer-recover`, pod
|
|
14
|
+
* recipient slots — and a `roster_tag`: AES-GCM of the canonical authority
|
|
15
|
+
* fields under that key. Every roster EDITOR holds the key (constraint:
|
|
16
|
+
* admins edit authority they don't hold the target's credential for) — which
|
|
17
|
+
* is what sets the bound below.
|
|
18
|
+
*
|
|
19
|
+
* `user_id` is inside the canonical string so a genuine tag cannot be
|
|
20
|
+
* transplanted onto another member's file.
|
|
21
|
+
*
|
|
22
|
+
* ## What "authority half" does NOT cover
|
|
23
|
+
*
|
|
24
|
+
* The canonical string is exactly {@link RosterAuthorityFields} — the fields a
|
|
25
|
+
* privilege decision reads. Other plaintext fields are deliberately excluded
|
|
26
|
+
* and REMAIN FORGEABLE by the store: `display_name` (cosmetic), `policy`
|
|
27
|
+
* (round-tripped, never enforced at v1.0), `echo` and `authenticators` (each
|
|
28
|
+
* authenticated by its own wrapped key material — a forged one fails to
|
|
29
|
+
* unlock rather than granting anything), plus `created_at` / `salt` /
|
|
30
|
+
* `_noydb_keyring`. Adding a field to the tag means adding it to
|
|
31
|
+
* `rosterCanonical`; nothing else here is a claim about it.
|
|
32
|
+
*
|
|
33
|
+
* ## The bound
|
|
34
|
+
*
|
|
35
|
+
* This stops the STORE, which holds no keys. It deliberately does NOT stop a
|
|
36
|
+
* malicious MEMBER: every roster editor must hold the roster key, so anyone
|
|
37
|
+
* who legitimately holds it can forge any authority field for any member.
|
|
38
|
+
* That bound must be stated in `SECURITY.md` (tracked as part of the #1096
|
|
39
|
+
* PR) — it is not written there yet.
|
|
40
|
+
*/
|
|
41
|
+
import type { KeyringFile } from '../../kernel/types.js';
|
|
42
|
+
import type { EnclaveKey } from '../../kernel/enclave/index.js';
|
|
43
|
+
export interface RosterTag {
|
|
44
|
+
readonly iv: string;
|
|
45
|
+
readonly data: string;
|
|
46
|
+
}
|
|
47
|
+
export type RosterAuthorityFields = Pick<KeyringFile, 'user_id' | 'role' | 'permissions' | 'granted_by' | 'expires_at' | 'export_capability' | 'import_capability' | 'deks' | 'pending_deks'>;
|
|
48
|
+
export declare function rosterCanonical(file: RosterAuthorityFields): string;
|
|
49
|
+
export declare function mintRosterTag(file: RosterAuthorityFields, rosterKey: EnclaveKey): Promise<RosterTag>;
|
|
50
|
+
/**
|
|
51
|
+
* false on decrypt failure OR canonical mismatch — never throws.
|
|
52
|
+
*
|
|
53
|
+
* `null` is accepted alongside `undefined` because the tag arrives from
|
|
54
|
+
* JSON a store controls: `"roster_tag": null` is a shape the type system
|
|
55
|
+
* says is impossible and the wire permits.
|
|
56
|
+
*/
|
|
57
|
+
export declare function verifyRosterTag(file: RosterAuthorityFields, tag: RosterTag | undefined | null, rosterKey: EnclaveKey): Promise<boolean>;
|
|
58
|
+
/**
|
|
59
|
+
* #1096 — THE CHOKEPOINT. Verify a keyring file's plaintext AUTHORITY half
|
|
60
|
+
* against the roster key carried in its own, already-unwrapped, DEK set.
|
|
61
|
+
* Throws {@link KeyringTamperedError}; returns silently when the roster is
|
|
62
|
+
* authentic.
|
|
63
|
+
*
|
|
64
|
+
* **Every path that builds an `UnlockedKeyring` from a `KeyringFile` must call
|
|
65
|
+
* this — not just `loadKeyring`.** A tier-2 unlock that reconstructs
|
|
66
|
+
* `role`/`permissions` from the plaintext header without it accepts exactly
|
|
67
|
+
* the forgery tier-1 refuses, and the vault is only as strong as its weakest
|
|
68
|
+
* unlock path. That is not hypothetical: the wrap-DEKs password path shipped
|
|
69
|
+
* in this state until it was caught in review.
|
|
70
|
+
*
|
|
71
|
+
* Deliberately says nothing about the canary. The canary proves the KEK, and
|
|
72
|
+
* tier-2 paths have no KEK to prove — the roster key they hold comes from the
|
|
73
|
+
* slot's own wrapped-DEK blob, which is authenticated by its own AES-GCM tag.
|
|
74
|
+
* Callers that DO hold a KEK check the canary separately, before this.
|
|
75
|
+
*
|
|
76
|
+
* @param deks the caller's UNWRAPPED DEK set — a roster key here is proof of
|
|
77
|
+
* possession, so this must never be handed a map built from unverified input.
|
|
78
|
+
*/
|
|
79
|
+
export declare function assertRosterAuthenticated(file: KeyringFile, deks: ReadonlyMap<string, EnclaveKey>, userId: string): Promise<void>;
|
|
80
|
+
/**
|
|
81
|
+
* #1096 — VERIFY BEFORE YOU TRUST, and especially before you RESTAMP.
|
|
82
|
+
*
|
|
83
|
+
* The sibling of {@link assertRosterAuthenticated} for the other half of the
|
|
84
|
+
* problem. That one guards paths that *unlock* a keyring; this one guards paths
|
|
85
|
+
* that **read another member's file** — because the roster key is vault-wide, a
|
|
86
|
+
* caller holding it can verify any member's tag, not just their own.
|
|
87
|
+
*
|
|
88
|
+
* Every read-modify-write on a member's roster must call this **before** the
|
|
89
|
+
* modify. A flow that reads a forged file, edits one field and restamps does
|
|
90
|
+
* not merely tolerate the forgery — it **launders** it, converting a file
|
|
91
|
+
* `loadKeyring` refuses into one it accepts, under a genuine tag. `revoke`
|
|
92
|
+
* calls into such a flow unconditionally, so without this a single forged
|
|
93
|
+
* member plus any later revocation anywhere in the vault is a complete bypass.
|
|
94
|
+
*
|
|
95
|
+
* Fail-closed, deliberately: a forged member's file aborts the operation rather
|
|
96
|
+
* than being skipped. Skipping would complete the revoke while leaving the
|
|
97
|
+
* forgery in place, and an untrusted store can already refuse writes — so the
|
|
98
|
+
* availability it costs was never guaranteed, while the integrity it buys is
|
|
99
|
+
* the point of the mechanism.
|
|
100
|
+
*/
|
|
101
|
+
export declare function assertRosterTagValid(file: KeyringFile, rosterKey: EnclaveKey, userId: string): Promise<void>;
|
|
@@ -18,7 +18,8 @@
|
|
|
18
18
|
*/
|
|
19
19
|
import type { UnlockedKeyring } from './keyring.js';
|
|
20
20
|
/** Canonical DEK key for a given collection + tier. Tier 0 → bare name. */
|
|
21
|
-
|
|
21
|
+
import { dekKey } from '../../kernel/tier-visibility.js';
|
|
22
|
+
export { dekKey };
|
|
22
23
|
/**
|
|
23
24
|
* Returns the user's effective clearance for a given collection: the
|
|
24
25
|
* maximum tier for which their keyring holds a DEK. Falls back to 0
|
|
@@ -47,14 +47,14 @@
|
|
|
47
47
|
*/
|
|
48
48
|
import type { Cover } from '../with-party/directory/cover/types.js';
|
|
49
49
|
import type { Redirect } from './redirect.js';
|
|
50
|
-
/** Magic bytes 'NDB1' (ASCII)
|
|
51
|
-
export declare const
|
|
50
|
+
/** Magic bytes 'NDB1' (ASCII) — `NoyDB 1` — identifying a NOYDB pod (`.noydb` container). */
|
|
51
|
+
export declare const NOYDB_POD_MAGIC: Uint8Array<ArrayBuffer>;
|
|
52
52
|
/** Total fixed prefix before the header JSON: 4+1+1+4 bytes. */
|
|
53
|
-
export declare const
|
|
53
|
+
export declare const NOYDB_POD_PREFIX_BYTES = 10;
|
|
54
54
|
/** Current bundle format version. Bumped on layout changes. Default for unsigned pods. */
|
|
55
|
-
export declare const
|
|
55
|
+
export declare const NOYDB_POD_FORMAT_VERSION = 1;
|
|
56
56
|
/** Format version for pods carrying a header signature (`sig`/`keyId`/`sigAlg`). */
|
|
57
|
-
export declare const
|
|
57
|
+
export declare const NOYDB_POD_FORMAT_VERSION_SIGNED = 2;
|
|
58
58
|
/**
|
|
59
59
|
* Bitfield interpretation of the flags byte.
|
|
60
60
|
*
|
|
@@ -85,7 +85,7 @@ export type CompressionAlgo = 0 | 1 | 2;
|
|
|
85
85
|
*
|
|
86
86
|
* **Minimum-disclosure rules:** these are the ONLY allowed keys.
|
|
87
87
|
* Any other key in a parsed header causes
|
|
88
|
-
* `
|
|
88
|
+
* `validatePodHeaderFields` to throw. The set is kept short to
|
|
89
89
|
* minimize attack surface from cloud-storage metadata indexing —
|
|
90
90
|
* see the file-level doc comment for the rationale.
|
|
91
91
|
*
|
|
@@ -249,8 +249,6 @@ export interface NoydbPodHeader {
|
|
|
249
249
|
* family (see `unlockMethods` doc comment on `NoydbPodHeader`).
|
|
250
250
|
*/
|
|
251
251
|
export type UnlockMethod = 'password' | 'webauthn' | 'oidc' | 'totp' | 'email-otp' | 'magic-link' | 'pin' | 'recovery' | 'shamir';
|
|
252
|
-
/** @deprecated Use `NoydbPodHeader`. */
|
|
253
|
-
export type NoydbBundleHeader = NoydbPodHeader;
|
|
254
252
|
/**
|
|
255
253
|
* Validate a parsed bundle header. Throws on any deviation from
|
|
256
254
|
* the minimum-disclosure schema:
|
|
@@ -266,18 +264,18 @@ export type NoydbBundleHeader = NoydbPodHeader;
|
|
|
266
264
|
* The error messages name the offending field so consumers can
|
|
267
265
|
* fix the producer rather than the reader.
|
|
268
266
|
*/
|
|
269
|
-
export declare function
|
|
267
|
+
export declare function validatePodHeaderFields(parsed: unknown): asserts parsed is NoydbPodHeader;
|
|
270
268
|
/**
|
|
271
269
|
* Encode a header object to UTF-8 JSON bytes after validating
|
|
272
270
|
* minimum disclosure. Used by the writer to serialize the header
|
|
273
271
|
* region of the container.
|
|
274
272
|
*/
|
|
275
|
-
export declare function
|
|
273
|
+
export declare function encodePodHeader(header: NoydbPodHeader): Uint8Array;
|
|
276
274
|
/**
|
|
277
275
|
* Parse a bundle header from its UTF-8 JSON bytes. Throws on
|
|
278
276
|
* invalid JSON or any minimum-disclosure violation.
|
|
279
277
|
*/
|
|
280
|
-
export declare function
|
|
278
|
+
export declare function decodePodHeader(bytes: Uint8Array): NoydbPodHeader;
|
|
281
279
|
/**
|
|
282
280
|
* Read a uint32 from `bytes` at `offset` in big-endian byte order.
|
|
283
281
|
* No bounds check — callers must guarantee `offset + 4 <= bytes.length`.
|
|
@@ -295,4 +293,4 @@ export declare function writeUint32BE(bytes: Uint8Array, offset: number, value:
|
|
|
295
293
|
* 4 bytes match `NDB1`. Used by readers as a fast file-type check
|
|
296
294
|
* before any further parsing.
|
|
297
295
|
*/
|
|
298
|
-
export declare function
|
|
296
|
+
export declare function hasNoydbPodMagic(bytes: Uint8Array): boolean;
|
package/dist/with-pod/index.d.ts
CHANGED
|
@@ -11,19 +11,19 @@
|
|
|
11
11
|
* omit this subpath and save ~805 LOC of format code + Brotli/gzip
|
|
12
12
|
* wiring.
|
|
13
13
|
*/
|
|
14
|
-
export { writePod, readPod, readPodHeader, readPodCover,
|
|
14
|
+
export { writePod, readPod, readPodHeader, readPodCover, resetBrotliSupportCache, } from './pod.js';
|
|
15
15
|
export type { Cover } from '../with-party/directory/cover/types.js';
|
|
16
|
-
export type { WritePodOptions,
|
|
17
|
-
export { verifyPodHeader } from './
|
|
18
|
-
export type { PodVerifyResult } from './
|
|
16
|
+
export type { WritePodOptions, ReadPodOptions, PodReadResult, } from './pod.js';
|
|
17
|
+
export { verifyPodHeader } from './pod.js';
|
|
18
|
+
export type { PodVerifyResult } from './pod.js';
|
|
19
19
|
export { signRecord, verifyRecord, signedBytes, POD_SIG_ALG } from './signature.js';
|
|
20
|
-
export {
|
|
21
|
-
export type { CompressionAlgo, NoydbPodHeader,
|
|
20
|
+
export { NOYDB_POD_MAGIC, NOYDB_POD_PREFIX_BYTES, NOYDB_POD_FORMAT_VERSION, FLAG_COMPRESSED, FLAG_HAS_INTEGRITY_HASH, COMPRESSION_NONE, COMPRESSION_GZIP, COMPRESSION_BROTLI, validatePodHeaderFields, encodePodHeader, hasNoydbPodMagic, } from './format.js';
|
|
21
|
+
export type { CompressionAlgo, NoydbPodHeader, UnlockMethod, } from './format.js';
|
|
22
22
|
export { generateULID, isULID } from './ulid.js';
|
|
23
|
-
export { wrapPodStore, createPodStore
|
|
24
|
-
export type { WrappedPodNoydbStore, WrapPodStoreOptions,
|
|
25
|
-
export {
|
|
26
|
-
export { readPodRedirect } from './
|
|
23
|
+
export { wrapPodStore, createPodStore } from './pod-store.js';
|
|
24
|
+
export type { WrappedPodNoydbStore, WrapPodStoreOptions, } from './pod-store.js';
|
|
25
|
+
export { PodIntegrityError, PodSealMismatchError, PodVersionConflictError, BackupLedgerError, BackupCorruptedError, } from '../kernel/errors.js';
|
|
26
|
+
export { readPodRedirect } from './pod.js';
|
|
27
27
|
export { signRedirect, verifyRedirect, followRedirects } from './redirect.js';
|
|
28
28
|
export type { Redirect, RedirectHop, FollowRedirectsResult } from './redirect.js';
|
|
29
29
|
export type { DocSigner } from '../with-audit/attestation/signer.js';
|
package/dist/with-pod/open.d.ts
CHANGED
|
@@ -6,7 +6,7 @@
|
|
|
6
6
|
* reachable through published seams). Composes, in order:
|
|
7
7
|
*
|
|
8
8
|
* 1. `readPod` — parse + integrity-check the container (throws
|
|
9
|
-
* `
|
|
9
|
+
* `PodIntegrityError` on a corrupted/truncated pod).
|
|
10
10
|
* 2. `verifyPodHeader` — only when `opts.trustedKeys` is supplied.
|
|
11
11
|
* `'unsigned'` is benign (legacy pod, or `writePod({ sign: false })`)
|
|
12
12
|
* and open() proceeds; `'untrusted'` / `'tampered'` are fail-closed —
|
|
@@ -63,7 +63,7 @@
|
|
|
63
63
|
* @module
|
|
64
64
|
*/
|
|
65
65
|
import type { NoydbPodHeader } from './format.js';
|
|
66
|
-
import type { PodVerifyResult } from './
|
|
66
|
+
import type { PodVerifyResult } from './pod.js';
|
|
67
67
|
import type { Noydb } from '../kernel/noydb.js';
|
|
68
68
|
import type { Vault } from '../kernel/vault.js';
|
|
69
69
|
import type { NoydbOptions, NoydbStore, EchoSecretParts } from '../kernel/types.js';
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Vault bundle handle — the stable opaque ULID identifying a vault
|
|
3
|
+
* across `.noydb` exports.
|
|
4
|
+
*
|
|
5
|
+
* Behaviour is byte-identical to the inline `Vault.getPodHandle`
|
|
6
|
+
* method this function replaced. `Vault` keeps the public method as
|
|
7
|
+
* a thin delegator.
|
|
8
|
+
*
|
|
9
|
+
* Internal — reached through `vault.getPodHandle()`.
|
|
10
|
+
*/
|
|
11
|
+
import type { NoydbStore } from '../kernel/types.js';
|
|
12
|
+
/**
|
|
13
|
+
* Return the stable opaque bundle handle for the given vault adapter,
|
|
14
|
+
* generating and persisting a fresh ULID on first call.
|
|
15
|
+
*
|
|
16
|
+
* See {@link import('../kernel/vault.js').Vault.getPodHandle} for
|
|
17
|
+
* the full rationale and storage-path documentation.
|
|
18
|
+
*/
|
|
19
|
+
export declare function buildPodHandle(adapter: NoydbStore, name: string): Promise<string>;
|
|
@@ -44,11 +44,3 @@ export declare function wrapPodStore(bundle: NoydbPodStore, options?: WrapPodSto
|
|
|
44
44
|
* analogous to `createStore` for KV stores.
|
|
45
45
|
*/
|
|
46
46
|
export declare function createPodStore<TOptions>(factory: (options: TOptions) => NoydbPodStore): (options: TOptions) => NoydbPodStore;
|
|
47
|
-
/** @deprecated Use wrapPodStore. */
|
|
48
|
-
export declare const wrapBundleStore: typeof wrapPodStore;
|
|
49
|
-
/** @deprecated Use createPodStore. */
|
|
50
|
-
export declare const createBundleStore: typeof createPodStore;
|
|
51
|
-
/** @deprecated Use WrappedPodNoydbStore. */
|
|
52
|
-
export type WrappedBundleNoydbStore = WrappedPodNoydbStore;
|
|
53
|
-
/** @deprecated Use WrapPodStoreOptions. */
|
|
54
|
-
export type WrapBundleStoreOptions = WrapPodStoreOptions;
|
|
@@ -36,7 +36,7 @@ import { type NoydbPodHeader, type UnlockMethod } from './format.js';
|
|
|
36
36
|
import type { Redirect } from './redirect.js';
|
|
37
37
|
import type { DocSigner } from '../with-audit/attestation/signer.js';
|
|
38
38
|
import type { Vault } from '../kernel/vault.js';
|
|
39
|
-
import type {
|
|
39
|
+
import type { PodRecipient } from '../with-party/team/keyring.js';
|
|
40
40
|
import type { Cover } from '../with-party/directory/cover/types.js';
|
|
41
41
|
import type { SealingKeyProvider, RecipientSealer, RecipientHint } from '../with-party/team/managed-secret.js';
|
|
42
42
|
/**
|
|
@@ -128,7 +128,7 @@ export interface WritePodOptions {
|
|
|
128
128
|
* the bundle inherits the source keyring as-is (today's behaviour,
|
|
129
129
|
* suited to personal backup-and-restore).
|
|
130
130
|
*/
|
|
131
|
-
readonly recipients?: readonly
|
|
131
|
+
readonly recipients?: readonly PodRecipient[];
|
|
132
132
|
/**
|
|
133
133
|
* Auto-unlock — unsealed per-user credentials.
|
|
134
134
|
*
|
|
@@ -266,8 +266,6 @@ export interface WritePodOptions {
|
|
|
266
266
|
*/
|
|
267
267
|
readonly redirect?: Redirect;
|
|
268
268
|
}
|
|
269
|
-
/** @deprecated Use `WritePodOptions`. */
|
|
270
|
-
export type WriteNoydbBundleOptions = WritePodOptions;
|
|
271
269
|
/**
|
|
272
270
|
* Every key `writePod` reads, in declaration order (#991).
|
|
273
271
|
*
|
|
@@ -289,7 +287,7 @@ export declare const WRITE_POD_OPTION_KEYS: readonly ["compression", "collection
|
|
|
289
287
|
* actually restore a vault. Splitting the layers keeps the
|
|
290
288
|
* bundle module free of crypto concerns — see file-level docs.
|
|
291
289
|
*/
|
|
292
|
-
export interface
|
|
290
|
+
export interface PodReadResult {
|
|
293
291
|
readonly header: NoydbPodHeader;
|
|
294
292
|
readonly dumpJson: string;
|
|
295
293
|
/**
|
|
@@ -317,7 +315,7 @@ export interface NoydbBundleReadResult {
|
|
|
317
315
|
* auto-unlock paths. Without these the reader behaves exactly as before
|
|
318
316
|
* (header parsed; body returned as `dumpJson`).
|
|
319
317
|
*/
|
|
320
|
-
export interface
|
|
318
|
+
export interface ReadPodOptions {
|
|
321
319
|
/**
|
|
322
320
|
* Recipient-side sealing providers used to unseal entries from
|
|
323
321
|
* `sealedSecrets`. The reader picks the one whose `.id`
|
|
@@ -373,7 +371,7 @@ export declare function resetBrotliSupportCache(): void;
|
|
|
373
371
|
*
|
|
374
372
|
* Pipeline:
|
|
375
373
|
* 1. Resolve or create the compartment's stable bundle handle
|
|
376
|
-
* via `vault.
|
|
374
|
+
* via `vault.getPodHandle()` — same handle on
|
|
377
375
|
* every export from the same vault instance, so cloud
|
|
378
376
|
* adapters can use it as a primary key.
|
|
379
377
|
* 2. `vault.dump()` → JSON string with encrypted records
|
|
@@ -398,7 +396,7 @@ export declare function resetBrotliSupportCache(): void;
|
|
|
398
396
|
*
|
|
399
397
|
* @internal
|
|
400
398
|
*/
|
|
401
|
-
export declare function
|
|
399
|
+
export declare function assemblePodContainer(opts: {
|
|
402
400
|
handle: string;
|
|
403
401
|
bodyJsonStr: string;
|
|
404
402
|
compression: WritePodOptions['compression'];
|
|
@@ -413,8 +411,6 @@ export declare function assembleBundleContainer(opts: {
|
|
|
413
411
|
signer?: DocSigner;
|
|
414
412
|
}): Promise<Uint8Array>;
|
|
415
413
|
export declare function writePod(vault: Vault, opts?: WritePodOptions): Promise<Uint8Array>;
|
|
416
|
-
/** @deprecated Use `writePod`. */
|
|
417
|
-
export declare const writeNoydbBundle: typeof writePod;
|
|
418
414
|
/**
|
|
419
415
|
* Read just the bundle header — no body decompression, no
|
|
420
416
|
* integrity verification. Intended for cloud-listing UIs that want
|
|
@@ -430,8 +426,6 @@ export declare const writeNoydbBundle: typeof writePod;
|
|
|
430
426
|
* range requests against bundles that may carry icons.
|
|
431
427
|
*/
|
|
432
428
|
export declare function readPodHeader(bytes: Uint8Array): NoydbPodHeader;
|
|
433
|
-
/** @deprecated Use `readPodHeader`. */
|
|
434
|
-
export declare const readNoydbBundleHeader: typeof readPodHeader;
|
|
435
429
|
/**
|
|
436
430
|
* Outcome of {@link verifyPodHeader}.
|
|
437
431
|
*
|
|
@@ -457,7 +451,7 @@ export interface PodVerifyResult {
|
|
|
457
451
|
* (`keyId → publicKeyB64` the caller already trusts), it reports whether the
|
|
458
452
|
* header was signed by a trusted document signer.
|
|
459
453
|
*
|
|
460
|
-
* Pairs with the signing half in `
|
|
454
|
+
* Pairs with the signing half in `assemblePodContainer`/`writePod`: the
|
|
461
455
|
* signed payload is the final wire header with `sig` removed, so verification
|
|
462
456
|
* reconstructs it by stripping EXACTLY the `sig` field — `keyId`, `sigAlg`,
|
|
463
457
|
* and every other header field stay in the verified payload.
|
|
@@ -469,7 +463,7 @@ export interface PodVerifyResult {
|
|
|
469
463
|
* header (which includes the *claimed* `bodySha256`) is signed by a trusted
|
|
470
464
|
* key; it does NOT prove the body matches that hash. To trust the pod's
|
|
471
465
|
* BODY you MUST also confirm the body hashes to `header.bodySha256` — call
|
|
472
|
-
* `readPod`, which throws `
|
|
466
|
+
* `readPod`, which throws `PodIntegrityError` on mismatch. A `verified`
|
|
473
467
|
* header paired with a swapped body is caught only by that integrity check.
|
|
474
468
|
* This function stays body-free by design so a static page can authenticate a
|
|
475
469
|
* header without decompressing the body; composing the two checks is the
|
|
@@ -498,7 +492,7 @@ export declare function readPodCover(bytes: Uint8Array, opts?: {
|
|
|
498
492
|
* the header's `redirect` field or `undefined` if the bundle was written
|
|
499
493
|
* without one.
|
|
500
494
|
*
|
|
501
|
-
* The record is returned UNVERIFIED: `
|
|
495
|
+
* The record is returned UNVERIFIED: `validatePodHeaderFields` only checks
|
|
502
496
|
* its shape at parse time (a parser has no `trustedKeys`). Callers that
|
|
503
497
|
* intend to follow the redirect MUST separately call `verifyRedirect`
|
|
504
498
|
* (`redirect.js`) before trusting `target`.
|
|
@@ -510,7 +504,7 @@ export declare function readPodRedirect(bytes: Uint8Array): Redirect | undefined
|
|
|
510
504
|
* original `vault.dump()` JSON string ready to pass to
|
|
511
505
|
* `vault.load()`.
|
|
512
506
|
*
|
|
513
|
-
* Throws `
|
|
507
|
+
* Throws `PodIntegrityError` if the body's actual SHA-256 does
|
|
514
508
|
* not match the value declared in the header. Distinct from a
|
|
515
509
|
* format error so consumers can pattern-match in catch blocks
|
|
516
510
|
* (corrupted-in-transit vs malformed-by-producer).
|
|
@@ -522,6 +516,4 @@ export declare function readPodRedirect(bytes: Uint8Array): Redirect | undefined
|
|
|
522
516
|
* free of crypto concerns and lets the same code feed format
|
|
523
517
|
* inspectors that never decrypt anything.
|
|
524
518
|
*/
|
|
525
|
-
export declare function readPod(bytes: Uint8Array, opts?:
|
|
526
|
-
/** @deprecated Use `readPod`. */
|
|
527
|
-
export declare const readNoydbBundle: typeof readPod;
|
|
519
|
+
export declare function readPod(bytes: Uint8Array, opts?: ReadPodOptions): Promise<PodReadResult>;
|
package/dist/with-pod/ulid.d.ts
CHANGED
|
@@ -39,7 +39,7 @@
|
|
|
39
39
|
*
|
|
40
40
|
* If a future use case needs timestamp-free handles, a v2 of the
|
|
41
41
|
* format could specify "use the random portion only" without a
|
|
42
|
-
* format break — `
|
|
42
|
+
* format break — `validatePodHeaderFields` only checks the regex
|
|
43
43
|
* shape, not the encoded timestamp.
|
|
44
44
|
*/
|
|
45
45
|
/**
|
|
@@ -30,6 +30,7 @@
|
|
|
30
30
|
*/
|
|
31
31
|
import type { NoydbStore, SlotInfo } from '../../kernel/types.js';
|
|
32
32
|
import { type EnclaveKey } from '../../kernel/enclave/index.js';
|
|
33
|
+
import { type OrphanChunkReport } from './orphan-report.js';
|
|
33
34
|
export interface BlobFieldPolicy<T = unknown> {
|
|
34
35
|
/**
|
|
35
36
|
* Via port brand marker — lets a `BlobFieldPolicy` satisfy the kernel's
|
|
@@ -145,6 +146,18 @@ export interface CompactionResult {
|
|
|
145
146
|
records: number;
|
|
146
147
|
evicted: number;
|
|
147
148
|
}>;
|
|
149
|
+
/**
|
|
150
|
+
* #1133 — chunk rows in `_blob_chunks` with no surviving `_blob_index` entry.
|
|
151
|
+
* Pre-#1127 residue: unreachable by every reader AND by rotation, so for a
|
|
152
|
+
* legacy blob the bytes stay openable under a retired `_blob` DEK.
|
|
153
|
+
*
|
|
154
|
+
* REPORTED, never reclaimed — deciding "orphaned" means trusting the store's
|
|
155
|
+
* `list`, and a store that withholds one index row would have us destroy a
|
|
156
|
+
* LIVE blob's chunks. See `orphan-report.ts` for the full argument. A vault
|
|
157
|
+
* that has run `migrate()` has no legacy chunks to strand, and `chunks: 0`
|
|
158
|
+
* is the expected reading everywhere else.
|
|
159
|
+
*/
|
|
160
|
+
readonly orphanBlobChunks: OrphanChunkReport;
|
|
148
161
|
}
|
|
149
162
|
export interface CompactRunOptions {
|
|
150
163
|
/** Override "now" for deterministic testing. */
|