@voltro/plugin-storage 0.85.0 → 0.87.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 (52) hide show
  1. package/CHANGELOG.md +5987 -0
  2. package/README.md +77 -0
  3. package/THIRD-PARTY-NOTICES.md +860 -249
  4. package/dist/access.js +47 -0
  5. package/dist/assetRef.js +13 -0
  6. package/dist/avatar.js +39 -0
  7. package/dist/byteSecurity.d.ts +3 -0
  8. package/dist/byteSecurity.js +7 -0
  9. package/dist/connection.js +99 -0
  10. package/dist/constraints.js +93 -0
  11. package/dist/custody.js +132 -0
  12. package/dist/derivatives.js +30 -0
  13. package/dist/env.js +162 -0
  14. package/dist/grant.js +132 -0
  15. package/dist/index.d.ts +525 -203
  16. package/dist/index.js +765 -3196
  17. package/dist/ingest.js +87 -0
  18. package/dist/ingestPolicy.js +1 -0
  19. package/dist/metadataError.js +19 -0
  20. package/dist/objectAbandon.js +16 -0
  21. package/dist/objectLifecycle.js +243 -0
  22. package/dist/objectMetadata.js +308 -0
  23. package/dist/objectWriter.js +87 -0
  24. package/dist/pathDurability.js +16 -0
  25. package/dist/physicalReferences.js +54 -0
  26. package/dist/providers.js +638 -0
  27. package/dist/referenceCatalogue.js +31 -0
  28. package/dist/renditionProof.js +82 -0
  29. package/dist/retainedCapture.js +391 -0
  30. package/dist/retainedObjects.js +190 -0
  31. package/dist/rpc.d.ts +3 -15
  32. package/dist/rpc.js +3 -1
  33. package/dist/scanners.js +46 -0
  34. package/dist/server.d.ts +153 -0
  35. package/dist/server.js +4 -0
  36. package/dist/service.js +1418 -0
  37. package/dist/sourceIdentity.js +14 -0
  38. package/dist/sourcePin.js +35 -0
  39. package/dist/storageNamespaces.js +80 -0
  40. package/dist/storageNumbers.js +13 -0
  41. package/dist/storageObjectNamespaces.js +243 -0
  42. package/dist/storageReferenceInstances.js +52 -0
  43. package/dist/storageRequest.js +10 -0
  44. package/dist/storageRouting.js +46 -0
  45. package/dist/streamBridge.js +33 -0
  46. package/dist/table.js +54 -0
  47. package/dist/transcodeVideo.js +91 -0
  48. package/dist/transform.js +94 -0
  49. package/dist/transformCache.js +31 -0
  50. package/dist/types.d.ts +116 -134
  51. package/dist/types.js +14 -14
  52. package/package.json +17 -6
package/dist/ingest.js ADDED
@@ -0,0 +1,87 @@
1
+ import { StorageError as e, StorageRejected as t } from "./types.js";
2
+ import { Effect as n } from "effect";
3
+ //#region src/ingest.ts
4
+ var r = 67108864, i = (e) => new t({
5
+ reason: "too-large",
6
+ detail: `remote body exceeds the ${e}-byte ingest limit`
7
+ }), a = (e, n) => new t({
8
+ reason: "blocked-source",
9
+ detail: `will not fetch ${e}: ${n}`
10
+ }), o = (o, s, c = {}) => n.suspend(() => {
11
+ let l = s ?? r;
12
+ return !Number.isSafeInteger(l) || l < 0 ? n.fail(new e({
13
+ provider: "ingest",
14
+ message: "limits.maxBytes must be a non-negative safe integer",
15
+ transient: !1
16
+ })) : typeof c != "object" || !c || Array.isArray(c) || c.requireHttps !== void 0 && typeof c.requireHttps != "boolean" ? n.fail(new e({
17
+ provider: "ingest",
18
+ message: "Ingest policy must be an object with an optional boolean requireHttps",
19
+ transient: !1,
20
+ status: 400
21
+ })) : n.tryPromise({
22
+ try: async (t) => {
23
+ let { ssrfReason: n } = await import("./ingestPolicy.js");
24
+ t.throwIfAborted();
25
+ let r = o, s;
26
+ for (let e = 0;; e++) {
27
+ let i = n(r, { ...c.allowHosts === void 0 ? {} : { allowHosts: c.allowHosts } });
28
+ if (i !== null) throw a(r, i);
29
+ if (c.requireHttps === !0 && new URL(r).protocol !== "https:") throw a(r, "HTTPS is required for this source and its redirects");
30
+ s = await fetch(r, {
31
+ signal: t,
32
+ redirect: "manual"
33
+ });
34
+ let o = s.headers.get("location");
35
+ if (s.status < 300 || s.status >= 400 || o === null) break;
36
+ if (await s.body?.cancel().catch(() => {}), e >= (c.maxRedirects ?? 5)) throw a(r, "too many redirects");
37
+ r = new URL(o, r).toString();
38
+ }
39
+ let u;
40
+ try {
41
+ if (!s.ok) throw new e({
42
+ provider: "ingest",
43
+ message: `remote server returned HTTP ${s.status}`,
44
+ transient: s.status === 429 || s.status >= 500,
45
+ status: s.status
46
+ });
47
+ let t = s.headers.get("content-length"), n = s.headers.get("content-encoding")?.trim().toLowerCase();
48
+ if ((!n || n === "identity") && t !== null && /^\d+$/.test(t) && BigInt(t) > BigInt(l)) throw i(l);
49
+ let r = /* @__PURE__ */ new Uint8Array(), a = 0;
50
+ if (s.body !== null) for (u = s.body.getReader();;) {
51
+ let e = await u.read();
52
+ if (e.done) break;
53
+ if (e.value.byteLength > l - a) throw i(l);
54
+ if (e.value.byteLength !== 0) {
55
+ let t = a + e.value.byteLength;
56
+ if (t > r.byteLength) {
57
+ let e = Math.min(l, Math.max(65536, r.byteLength * 2, t)), n = new Uint8Array(e);
58
+ n.set(r), r = n;
59
+ }
60
+ r.set(e.value, a), a = t;
61
+ }
62
+ }
63
+ return {
64
+ bytes: a === r.byteLength ? r : r.slice(0, a),
65
+ contentType: s.headers.get("content-type")?.split(";")[0]?.trim() || "application/octet-stream"
66
+ };
67
+ } finally {
68
+ u === void 0 ? await s.body?.cancel().catch(() => {}) : (await u.cancel().catch(() => {}), u.releaseLock());
69
+ }
70
+ },
71
+ catch: (n) => n instanceof t || n instanceof e ? n : new e({
72
+ provider: "ingest",
73
+ message: "remote fetch or body read failed",
74
+ transient: !0
75
+ })
76
+ });
77
+ }), s = (e, t) => n.suspend(() => {
78
+ if (t === void 0) return e;
79
+ if (t.aborted) return n.interrupt;
80
+ let r = n.callback((e) => {
81
+ let r = () => e(n.interrupt);
82
+ return t.addEventListener("abort", r, { once: !0 }), t.aborted && r(), n.sync(() => t.removeEventListener("abort", r));
83
+ });
84
+ return n.raceFirst(e, r);
85
+ });
86
+ //#endregion
87
+ export { o as fetchIngestBody, s as withIngestAbort };
@@ -0,0 +1 @@
1
+ export { ssrfReason } from "@voltro/protocol";
@@ -0,0 +1,19 @@
1
+ import { StorageError as e, StorageRejected as t } from "./types.js";
2
+ import { Schema as n } from "effect";
3
+ import { causeBranches as r, extractDbCause as i, isTransientContention as a, wireSafeCause as o } from "@voltro/database";
4
+ //#region src/metadataError.ts
5
+ var s = (t, s, c = !1) => {
6
+ let l = r(t).find(n.is(e));
7
+ if (l !== void 0) return l;
8
+ let u = i(t), d = u.dbCode === "22003" || u.dbSqlState === "22003" || u.dbCode === "ER_WARN_DATA_OUT_OF_RANGE" || u.dbErrno === 1264 || u.dbNumber === 8115 || u.dbNumber === 248, f = new e({
9
+ provider: s,
10
+ message: `${d ? "Storage metadata numeric value out of range: " : ""}${o(t)}`,
11
+ transient: d ? !1 : a(t) || c
12
+ });
13
+ return Object.defineProperty(f, "cause", {
14
+ value: t,
15
+ configurable: !0
16
+ }), f;
17
+ }, c = (e) => r(e).find(n.is(t));
18
+ //#endregion
19
+ export { s as storageMetadataError, c as storageRejectedCause };
@@ -0,0 +1,16 @@
1
+ import { storageMetadataError as e } from "./metadataError.js";
2
+ import { beginStorageObjectAbandon as t, makeStorageObjectMetadata as n } from "./objectMetadata.js";
3
+ import { Effect as r } from "effect";
4
+ //#region src/objectAbandon.ts
5
+ var i = (t) => r.tryPromise({
6
+ try: t,
7
+ catch: (t) => e(t, "metadata")
8
+ }), a = (e, a, o) => r.gen(function* () {
9
+ let r = yield* i(() => t(e, o));
10
+ return r.state === "retired" ? (r.operation.deleteKey !== null && (yield* a.delete(r.operation.deleteKey)), yield* i(() => n(e, o).confirmDelete(r.identity)), {
11
+ state: "abandoned",
12
+ refId: r.operation.refId
13
+ }) : r;
14
+ });
15
+ //#endregion
16
+ export { a as abandonStorageObject };
@@ -0,0 +1,243 @@
1
+ import { requireStorageReferenceScope as e } from "./storageNamespaces.js";
2
+ import { StorageRejected as t } from "./types.js";
3
+ import { storageInteger as n, storageIntegerSum as r } from "./storageNumbers.js";
4
+ import { Schema as i } from "effect";
5
+ import { createHash as a, randomUUID as o } from "node:crypto";
6
+ import { and as s, bigint as c, eq as l, neq as u, table as d, text as f } from "@voltro/database";
7
+ //#region src/objectLifecycle.ts
8
+ var p = "_voltro_storage_operation_locks", m = "_voltro_storage_object_heads", h = "_voltro_storage_operations", g = "_voltro_storage_object_claims", _ = [
9
+ d(p, {
10
+ id: f().maxLength(64),
11
+ nonce: f()
12
+ }).primaryKey(["id"]).nonReactive(),
13
+ d(m, {
14
+ id: f().maxLength(64),
15
+ objectNamespace: f().maxLength(64).nullable(),
16
+ generation: f(),
17
+ key: f(),
18
+ reservations: c()
19
+ }).primaryKey(["id"]).nonReactive(),
20
+ d(h, {
21
+ id: f().maxLength(64),
22
+ storageInstance: f().nullable(),
23
+ objectNamespace: f().maxLength(64).nullable(),
24
+ objectId: f().maxLength(64),
25
+ fingerprint: f().maxLength(64),
26
+ generation: f(),
27
+ key: f(),
28
+ refId: f(),
29
+ state: f(),
30
+ deleteKey: f().nullable()
31
+ }).primaryKey(["id"]).nonReactive(),
32
+ d(g, {
33
+ id: f().maxLength(64),
34
+ operationId: f().maxLength(64),
35
+ claim: f()
36
+ }).primaryKey(["id"]).nonReactive()
37
+ ], v = i.Struct({
38
+ id: i.String,
39
+ storageInstance: i.String,
40
+ objectNamespace: i.String,
41
+ objectId: i.String,
42
+ fingerprint: i.String,
43
+ generation: i.String,
44
+ key: i.String,
45
+ refId: i.String,
46
+ state: i.Literals([
47
+ "reserved",
48
+ "ready",
49
+ "deleting",
50
+ "deleted"
51
+ ]),
52
+ deleteKey: i.NullOr(i.String)
53
+ }), y = i.Struct({
54
+ id: i.String,
55
+ objectNamespace: i.String,
56
+ generation: i.String,
57
+ key: i.String,
58
+ reservations: i.Int.pipe(i.check(i.isGreaterThanOrEqualTo(0)))
59
+ }), b = (e) => i.decodeUnknownSync(y)({
60
+ ...e,
61
+ reservations: n(e.reservations, "shared-object reservation count")
62
+ }), x = (e) => a("sha256").update(JSON.stringify(e)).digest("hex"), S = (e, t) => x([e, t]), C = (n) => {
63
+ if (n.tenantId !== null && (typeof n.tenantId != "string" || !n.tenantId.trim() || n.tenantId.length > 191) || typeof n.bucket != "string" || !n.bucket.trim() || n.bucket.length > 200 || typeof n.operationId != "string" || !n.operationId.trim() || n.operationId.length > 200) throw new t({
64
+ reason: "operation-identity-reused",
65
+ detail: "Storage operation lookup requires explicit valid tenant, destination and operation identity"
66
+ });
67
+ return e(n), x([
68
+ n.storageInstance,
69
+ n.objectNamespace,
70
+ n.bucket,
71
+ n.tenantId,
72
+ n.operationId
73
+ ]);
74
+ }, w = (e) => C(e), T = async (e, t) => {
75
+ let n = await e.query({
76
+ table: h,
77
+ predicate: l("id", C(t)),
78
+ order: [],
79
+ take: 1,
80
+ skip: void 0,
81
+ projection: void 0
82
+ });
83
+ return n[0] ? i.decodeUnknownSync(v)(n[0]) : void 0;
84
+ }, E = async (e, t, n) => {
85
+ if (typeof n != "string" || !n.trim() || n.length > 200) throw Error("Storage operation lookup requires a bounded claim");
86
+ return (await e.query({
87
+ table: g,
88
+ predicate: s(l("id", S(t, n)), l("operationId", t), l("claim", n)),
89
+ order: [],
90
+ take: 1,
91
+ skip: void 0,
92
+ projection: ["id"]
93
+ })).length === 1;
94
+ }, D = (t) => {
95
+ if (e(t), !t.bucket || !t.operationId || !t.logicalKey || !/^[a-f0-9]{64}$/.test(t.fingerprint) || !/^[a-f0-9]{64}$/.test(t.checksum) || t.retainedSource !== void 0 && (!t.retainedSource.refId || !/^[a-f0-9]{64}$/.test(t.retainedSource.digest))) throw Error("Storage operation requires a bucket, operation identity, key and SHA-256 fingerprint");
96
+ return {
97
+ id: C(t),
98
+ objectId: x([
99
+ t.objectNamespace,
100
+ t.bucket,
101
+ t.tenantId,
102
+ t.logicalKey,
103
+ t.checksum
104
+ ]),
105
+ lockId: x([t.tenantId])
106
+ };
107
+ }, O = async (e, t, n) => {
108
+ let { lockId: r } = D(t);
109
+ return await e.insertIgnoreWithOutcome(p, {
110
+ id: r,
111
+ nonce: o()
112
+ }, { conflictColumns: ["id"] }), e.transactional(async (e) => {
113
+ if ((await e.query({
114
+ table: p,
115
+ predicate: l("id", r),
116
+ lock: "update",
117
+ order: [],
118
+ take: 1,
119
+ skip: void 0,
120
+ projection: void 0
121
+ })).length !== 1 || await e.update(p, r, { nonce: o() }) === null) throw Error("Storage operation lock is unavailable");
122
+ return n(e);
123
+ });
124
+ }, k = async (e, n) => {
125
+ let r = D(n), a = await e.query({
126
+ table: h,
127
+ predicate: l("id", r.id),
128
+ order: [],
129
+ take: 1,
130
+ skip: void 0,
131
+ projection: void 0
132
+ });
133
+ if (!a[0]) return;
134
+ let o = i.decodeUnknownSync(v)(a[0]);
135
+ if (o.storageInstance !== n.storageInstance || o.objectNamespace !== n.objectNamespace || o.fingerprint !== n.fingerprint || o.objectId !== r.objectId) throw new t({
136
+ reason: "operation-identity-reused",
137
+ detail: `storage operation '${n.operationId}' was already used with different inputs`
138
+ });
139
+ return o;
140
+ }, A = async (e, t) => {
141
+ let n = await k(e, t);
142
+ if (n) return n;
143
+ let { id: i, objectId: a } = D(t), s = await e.query({
144
+ table: m,
145
+ predicate: l("id", a),
146
+ order: [],
147
+ take: 1,
148
+ skip: void 0,
149
+ projection: void 0
150
+ }), c = s[0] ? b(s[0]) : void 0, u = c?.generation ?? o(), d = c?.key ?? `${t.logicalKey}/g-${u}`;
151
+ c ? await e.update(m, a, { reservations: String(r(c.reservations, 1, "shared-object reservation count")) }) : await e.insert(m, {
152
+ id: a,
153
+ objectNamespace: t.objectNamespace,
154
+ generation: u,
155
+ key: d,
156
+ reservations: "1"
157
+ });
158
+ let f = {
159
+ id: i,
160
+ storageInstance: t.storageInstance,
161
+ objectNamespace: t.objectNamespace,
162
+ objectId: a,
163
+ fingerprint: t.fingerprint,
164
+ generation: u,
165
+ key: d,
166
+ refId: `file_${o()}`,
167
+ state: "reserved",
168
+ deleteKey: null
169
+ };
170
+ return await e.insert(h, f), f;
171
+ }, j = async (e, t) => {
172
+ let n = await k(e, t);
173
+ if (!n) throw Error("Storage operation is missing");
174
+ if (n.state === "deleting" || n.state === "deleted") throw Error("Deleted storage operation cannot be confirmed by a late put");
175
+ return await e.update(h, n.id, { state: "ready" }), {
176
+ ...n,
177
+ state: "ready"
178
+ };
179
+ }, M = async (e, t, n) => {
180
+ let r = await k(e, t);
181
+ if (!r) throw Error("Storage operation is missing");
182
+ if (r.state === "deleting" || r.state === "deleted") return r;
183
+ if (r.state !== n) throw Error(n === "ready" ? "An unconfirmed put cannot be deleted" : "A confirmed put cannot be abandoned");
184
+ if (n === "reserved" && (await e.query({
185
+ table: g,
186
+ predicate: l("operationId", r.id),
187
+ order: [],
188
+ take: 1,
189
+ skip: void 0,
190
+ projection: ["id"]
191
+ })).length !== 0) throw Error("An unconfirmed operation unexpectedly holds claims");
192
+ let i = await e.query({
193
+ table: m,
194
+ predicate: l("id", r.objectId),
195
+ order: [],
196
+ take: 1,
197
+ skip: void 0,
198
+ projection: void 0
199
+ }), a = i[0] ? b(i[0]) : void 0;
200
+ if (!a || a.generation !== r.generation || a.reservations < 1) throw Error("Storage object generation does not own its reservation");
201
+ let o = a.reservations === 1 ? a.key : null;
202
+ return o === null ? await e.update(m, a.id, { reservations: String(a.reservations - 1) }) : await e.delete(m, a.id), o !== null && (await e.query({
203
+ table: m,
204
+ predicate: s(l("objectNamespace", t.objectNamespace), l("key", o)),
205
+ order: [],
206
+ take: 1,
207
+ skip: void 0,
208
+ projection: ["id"]
209
+ })).length && (o = null), await e.update(h, r.id, {
210
+ state: "deleting",
211
+ deleteKey: o
212
+ }), {
213
+ ...r,
214
+ state: "deleting",
215
+ deleteKey: o
216
+ };
217
+ }, N = (e, t) => M(e, t, "ready"), P = (e, t) => M(e, t, "reserved"), F = async (e, t) => {
218
+ let n = await k(e, t);
219
+ if (!n || n.state !== "deleting" && n.state !== "deleted") throw Error("Storage deletion has not been accepted");
220
+ return n.state !== "deleted" && (await e.update(h, n.id, { state: "deleted" }), !0);
221
+ }, I = async (e, t, n) => {
222
+ if (!n) throw Error("Storage object claim must be a non-empty string");
223
+ await e.insertIgnoreWithOutcome(g, {
224
+ id: S(t, n),
225
+ operationId: t,
226
+ claim: n
227
+ }, { conflictColumns: ["id"] });
228
+ }, L = async (e, t, n) => {
229
+ let r = S(t, n);
230
+ return {
231
+ held: await e.delete(g, r),
232
+ others: (await e.query({
233
+ table: g,
234
+ predicate: s(l("operationId", t), u("claim", n)),
235
+ order: [],
236
+ take: 1,
237
+ skip: void 0,
238
+ projection: void 0
239
+ })).length > 0
240
+ };
241
+ }, R = (e, t) => e.deleteMany(g, { where: l("operationId", t) });
242
+ //#endregion
243
+ export { P as beginStorageObjectAbandonInTransaction, N as beginStorageObjectDeleteInTransaction, I as claimStorageObjectInTransaction, R as clearStorageObjectClaimsInTransaction, F as confirmStorageObjectDeleteInTransaction, j as confirmStorageObjectInTransaction, E as hasStorageObjectClaimInTransaction, T as lookupStorageObjectOperationInTransaction, k as readStorageObjectOperationInTransaction, L as releaseStorageObjectClaimInTransaction, A as reserveStorageObjectInTransaction, S as storageObjectClaimId, D as storageObjectIdentifiers, _ as storageObjectLifecycleTables, w as storageObjectOperationId, O as withStorageOperationTransaction };
@@ -0,0 +1,308 @@
1
+ import { requireStorageReferenceScope as e, storageReferenceScopeFor as t } from "./storageNamespaces.js";
2
+ import { StorageRejected as n, storageRefAddress as r } from "./types.js";
3
+ import { beginStorageObjectAbandonInTransaction as i, beginStorageObjectDeleteInTransaction as a, claimStorageObjectInTransaction as o, clearStorageObjectClaimsInTransaction as s, confirmStorageObjectDeleteInTransaction as c, confirmStorageObjectInTransaction as l, hasStorageObjectClaimInTransaction as u, lookupStorageObjectOperationInTransaction as d, readStorageObjectOperationInTransaction as f, releaseStorageObjectClaimInTransaction as p, reserveStorageObjectInTransaction as m, storageObjectOperationId as h, withStorageOperationTransaction as g } from "./objectLifecycle.js";
4
+ import { dataStoreGrantStore as _, dataStoreRefStore as v, toRef as y } from "./service.js";
5
+ import { StorageAddress as b } from "@voltro/kv/storage";
6
+ import { Effect as x, Schema as S } from "effect";
7
+ import { and as C, eq as w, json as T, table as E, text as D } from "@voltro/database";
8
+ //#region src/objectMetadata.ts
9
+ var O = "_voltro_storage_put_intents", k = E(O, {
10
+ id: D().maxLength(64),
11
+ refId: D().maxLength(64),
12
+ storageInstance: D().nullable(),
13
+ objectNamespace: D().maxLength(64).nullable(),
14
+ identity: T(),
15
+ ref: T()
16
+ }).primaryKey(["id"]).unique("storagePutRef", ["refId"]).nonReactive(), A = S.Struct({
17
+ storageInstance: S.String,
18
+ objectNamespace: S.String,
19
+ tenantId: S.NullOr(S.String),
20
+ bucket: S.String,
21
+ operationId: S.String,
22
+ fingerprint: S.String,
23
+ checksum: S.String,
24
+ logicalKey: S.String,
25
+ retainedSource: S.optionalKey(S.Struct({
26
+ refId: S.String,
27
+ digest: S.String
28
+ }))
29
+ }), j = async (e, t, n) => {
30
+ let r = await e.query({
31
+ table: O,
32
+ predicate: C(w("storageInstance", n.storageInstance), w("objectNamespace", n.objectNamespace), w("refId", t)),
33
+ order: [],
34
+ take: 2,
35
+ skip: void 0,
36
+ projection: void 0
37
+ });
38
+ if (r.length === 0) return;
39
+ if (r.length !== 1) throw Error("Storage reference has ambiguous operation ownership");
40
+ let i = r[0], a = S.decodeUnknownSync(A)(i.identity);
41
+ if (a.storageInstance !== n.storageInstance || a.objectNamespace !== n.objectNamespace) throw Error("Storage put intent does not match its bound storage scope");
42
+ if (typeof i.ref != "object" || i.ref === null || Array.isArray(i.ref)) throw Error("Storage operation reference is unreadable");
43
+ let o = y(i.ref);
44
+ if (o.id !== t || o.bucket !== a.bucket || o.tenantId !== a.tenantId || o.checksum !== a.checksum || !Number.isSafeInteger(o.size) || o.size < 0 || !Number.isFinite(o.createdAt.getTime())) throw Error("Storage operation reference does not match its identity");
45
+ return {
46
+ identity: a,
47
+ ref: o
48
+ };
49
+ }, M = async (e, t) => {
50
+ let n = h(t), r = await e.query({
51
+ table: O,
52
+ predicate: w("id", n),
53
+ order: [],
54
+ take: 1,
55
+ skip: void 0,
56
+ projection: void 0
57
+ });
58
+ if (r.length === 0) return;
59
+ if (typeof r[0].refId != "string") throw Error("Storage operation has no reference identity");
60
+ let i = await j(e, r[0].refId, t);
61
+ if (i === void 0 || h(i.identity) !== n) throw Error("Storage operation intent does not match its requested scope");
62
+ let a = await f(e, i.identity);
63
+ if (a === void 0 || a.refId !== i.ref.id) throw Error("Storage operation intent lost its operation");
64
+ return {
65
+ ...i,
66
+ state: a.state
67
+ };
68
+ }, N = async (e, t) => {
69
+ let n = await M(e, t);
70
+ return n === void 0 ? { state: "missing" } : g(e, n.identity, async (e) => {
71
+ let n = await M(e, t);
72
+ if (n === void 0) throw Error("Storage operation disappeared before abandonment");
73
+ if (n.state === "ready") return {
74
+ state: "ready",
75
+ refId: n.ref.id
76
+ };
77
+ let r = v(e, t);
78
+ if (n.state === "reserved" && await x.runPromise(r.getById(n.ref.id)) !== null) throw Error("An unconfirmed operation unexpectedly has a readable reference");
79
+ let a = await i(e, n.identity);
80
+ return n.state === "reserved" && await x.runPromise(r.releaseUsage(n.identity.tenantId, {
81
+ bytes: n.ref.size,
82
+ count: 1
83
+ })), {
84
+ state: "retired",
85
+ identity: n.identity,
86
+ operation: a
87
+ };
88
+ });
89
+ }, P = (t, r, i) => {
90
+ let b = Object.freeze({ ...r });
91
+ e(b);
92
+ let S = (e) => ({
93
+ ...e,
94
+ ...b
95
+ });
96
+ return {
97
+ scope: b,
98
+ operationStatus: (e) => t.transactional(async (t) => {
99
+ let n = {
100
+ ...e,
101
+ ...b
102
+ }, r = await d(t, n);
103
+ if (!r) return { state: "absent" };
104
+ let i = await j(t, r.refId, b);
105
+ if (!i || i.identity.bucket !== e.bucket || i.identity.tenantId !== e.tenantId || i.identity.operationId !== e.operationId || h(i.identity) !== r.id || i.ref.key !== r.key) throw Error("Storage operation lost its matching put intent");
106
+ let a = await f(t, i.identity);
107
+ if (!a || a.refId !== r.refId || a.key !== r.key) throw Error("Storage operation identity changed during observation");
108
+ if (a.state !== "ready") return { state: a.state };
109
+ let o = await x.runPromise(v(t, b).getById(a.refId));
110
+ if (!o || o.id !== i.ref.id || o.bucket !== e.bucket || o.tenantId !== e.tenantId || o.key !== a.key || o.checksum !== i.identity.checksum || o.size !== i.ref.size) throw Error("Ready storage operation has no matching readable reference");
111
+ let s = await f(t, i.identity);
112
+ if (!s || s.state !== "ready" || s.key !== o.key || s.refId !== o.id) throw Error("Storage operation changed during observation");
113
+ return {
114
+ state: "ready",
115
+ ref: o
116
+ };
117
+ }),
118
+ intent: (e) => j(t, e, b),
119
+ lookup: async (e, n) => {
120
+ if (typeof n != "string" || !n.trim() || n.length > 200) throw Error("Storage operation lookup requires an explicit bounded claim");
121
+ let r = Object.freeze({
122
+ ...b,
123
+ tenantId: e.tenantId,
124
+ bucket: e.bucket,
125
+ operationId: e.operationId
126
+ }), i = await d(t, r);
127
+ if (!i) return;
128
+ let a = await j(t, i.refId, b);
129
+ if (!a || a.identity.tenantId !== r.tenantId || a.identity.bucket !== r.bucket || a.identity.operationId !== r.operationId) throw Error("Storage operation lookup has unrelated durable intent");
130
+ return g(t, a.identity, async (e) => {
131
+ let t = await f(e, a.identity);
132
+ if (!t) throw Error("Storage operation lookup lost its durable identity");
133
+ let r = await j(e, t.refId, b);
134
+ if (!r) throw Error("Storage operation lookup lost its put intent");
135
+ return {
136
+ state: t.state,
137
+ ref: r.ref,
138
+ held: await u(e, t.id, n)
139
+ };
140
+ });
141
+ },
142
+ operation: (e) => M(t, {
143
+ ...e,
144
+ ...b
145
+ }),
146
+ reserve: (e, r, a, s) => g(t, S(e), async (t) => {
147
+ if (await i?.(t, e, "reserve"), r.tenantId !== e.tenantId || r.bucket !== e.bucket || r.checksum !== e.checksum || !Number.isSafeInteger(r.size) || r.size < 0) throw Error("Storage put metadata does not match its identity");
148
+ let c = await f(t, S(e));
149
+ if (c) {
150
+ if (c.state === "deleting" || c.state === "deleted") throw Error("Storage put identity has already been deleted");
151
+ let e = await j(t, c.refId, b);
152
+ if (!e) throw Error("Storage operation lost its put intent");
153
+ let n = c.state === "ready";
154
+ return n && s !== void 0 && await o(t, c.id, s), {
155
+ ref: e.ref,
156
+ ready: n,
157
+ outcome: n ? "joined" : "resumed"
158
+ };
159
+ }
160
+ let l = await m(t, S(e)), u = v(t, b);
161
+ if (!(await x.runPromise(u.consumeUsage(e.tenantId, {
162
+ bytes: r.size,
163
+ count: 1
164
+ }, a))).allowed) throw new n({
165
+ reason: "quota-exceeded",
166
+ detail: "Storage operation exceeds tenant quota"
167
+ });
168
+ let d = y({
169
+ ...r,
170
+ id: l.refId,
171
+ key: l.key
172
+ });
173
+ return await t.insert(O, {
174
+ id: l.id,
175
+ refId: d.id,
176
+ ...b,
177
+ identity: S(e),
178
+ ref: d
179
+ }), {
180
+ ref: d,
181
+ ready: !1,
182
+ outcome: "created"
183
+ };
184
+ }),
185
+ confirm: (e, n) => g(t, S(e), async (t) => {
186
+ await i?.(t, e, "confirm");
187
+ let r = await f(t, S(e));
188
+ if (!r) throw Error("Storage put operation is missing");
189
+ let a = await j(t, r.refId, b);
190
+ if (!a) throw Error("Storage put intent is missing");
191
+ if (n !== void 0 && await o(t, r.id, n), r.state === "ready") {
192
+ let n = await x.runPromise(v(t, b).getById(r.refId));
193
+ if (!n || n.key !== r.key || n.checksum !== e.checksum) throw Error("Confirmed storage operation lost its reference");
194
+ return n;
195
+ }
196
+ return await l(t, S(e)), await x.runPromise(v(t, b).insert(a.ref)), a.ref;
197
+ }),
198
+ beginDelete: async (e, r, i) => {
199
+ let o = await j(t, e, b);
200
+ if (!o) throw Error("Storage delete operation is missing");
201
+ if (r !== void 0 && o.identity.tenantId !== r) throw Error("Storage delete tenant mismatch");
202
+ return g(t, o.identity, async (t) => {
203
+ let r = await j(t, e, b);
204
+ if (!r) throw Error("Storage delete intent disappeared");
205
+ let o = await f(t, r.identity);
206
+ if (!o) throw Error("Storage delete lost its operation");
207
+ let c = o.state === "ready", l = o.state !== "deleting" && o.state !== "deleted";
208
+ if (i === void 0) l && await s(t, o.id);
209
+ else if (l) {
210
+ let a = await p(t, o.id, i);
211
+ if (a.others) return {
212
+ released: !0,
213
+ identity: r.identity
214
+ };
215
+ if (!a.held) throw new n({
216
+ reason: "claim-not-held",
217
+ detail: `claim '${i}' is not held on storage reference '${e}'; a reference put without a claim is deleted as a whole by a delete that names none`
218
+ });
219
+ }
220
+ let u = await a(t, r.identity);
221
+ if (c) {
222
+ let n = v(t, b);
223
+ if (await x.runPromise(_(t, b).deleteByRef(e)), !await x.runPromise(n.delete(e))) throw Error("Storage deletion lost its confirmed reference");
224
+ await x.runPromise(n.releaseUsage(r.identity.tenantId, {
225
+ bytes: r.ref.size,
226
+ count: 1
227
+ }));
228
+ }
229
+ return u.deleteKey !== null && (await t.query({
230
+ table: "_voltro_storage_refs",
231
+ predicate: C(w("objectNamespace", b.objectNamespace), w("key", u.deleteKey)),
232
+ order: [],
233
+ take: 1,
234
+ skip: void 0,
235
+ projection: ["id"]
236
+ })).length > 0 && (await t.update("_voltro_storage_operations", u.id, { deleteKey: null }), u = {
237
+ ...u,
238
+ deleteKey: null
239
+ }), {
240
+ released: !0,
241
+ operation: u,
242
+ identity: r.identity
243
+ };
244
+ });
245
+ },
246
+ confirmDelete: (e) => g(t, S(e), (t) => c(t, S(e)))
247
+ };
248
+ }, F = (n, i, a) => {
249
+ let o = Object.freeze({ ...i });
250
+ if (!o.storageInstance.trim()) throw Error("Storage operation metadata requires an explicit instance");
251
+ "resolveNamespace" in o || e(o);
252
+ let s = async (e) => {
253
+ if (!("resolveNamespace" in o)) return o;
254
+ if ("refId" in e) {
255
+ let t = await l(e.refId);
256
+ if (!t) throw Error("Storage delete operation is missing");
257
+ return {
258
+ storageInstance: t.identity.storageInstance,
259
+ objectNamespace: t.identity.objectNamespace
260
+ };
261
+ }
262
+ return x.runPromise(t(o, {
263
+ destination: e.bucket,
264
+ tenantId: e.tenantId,
265
+ key: "_namespace"
266
+ }));
267
+ }, c = async (e) => P(n, await s(e), a), l = async (e) => {
268
+ if (!("resolveNamespace" in o)) return P(n, o, a).intent(e);
269
+ let i = await n.query({
270
+ table: O,
271
+ predicate: C(w("storageInstance", o.storageInstance), w("refId", e)),
272
+ order: [],
273
+ take: 2,
274
+ skip: void 0,
275
+ projection: void 0
276
+ });
277
+ if (i.length === 0) return;
278
+ if (i.length !== 1) throw Error("Storage reference has ambiguous operation ownership");
279
+ let s = S.decodeUnknownSync(A)(i[0].identity), c = y(i[0].ref);
280
+ S.decodeUnknownSync(b)(r(c));
281
+ let l = await x.runPromise(t(o, r(c)));
282
+ if (s.storageInstance !== l.storageInstance || s.objectNamespace !== l.objectNamespace) throw Error("Storage put intent belongs to a different physical object namespace");
283
+ return P(n, l, a).intent(e);
284
+ };
285
+ return {
286
+ scopeFor: s,
287
+ intent: l,
288
+ operationStatus: async (e) => {
289
+ let t = await s(e);
290
+ return {
291
+ observation: await P(n, t, a).operationStatus(e),
292
+ scope: t
293
+ };
294
+ },
295
+ lookup: async (e, t) => (await c(e)).lookup(e, t),
296
+ operation: async (e) => (await c(e)).operation(e),
297
+ reserve: async (e, t, n, r) => (await c(e)).reserve(e, t, n, r),
298
+ confirm: async (e, t) => (await c(e)).confirm(e, t),
299
+ beginDelete: async (e, t, r) => {
300
+ let i = await l(e);
301
+ if (!i) throw Error("Storage delete operation is missing");
302
+ return P(n, i.identity, a).beginDelete(e, t, r);
303
+ },
304
+ confirmDelete: async (e) => (await c(e)).confirmDelete(e)
305
+ };
306
+ }, I = (e, t, n) => F(e, t, n);
307
+ //#endregion
308
+ export { N as beginStorageObjectAbandon, I as makeAdmittedStorageObjectMetadata, F as makeStorageObjectMetadata, k as storagePutIntentsTable };