@bedrock-rbx/ocale 0.1.0-beta.9 → 0.1.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (82) hide show
  1. package/README.md +182 -0
  2. package/dist/badges.d.mts +33 -2
  3. package/dist/badges.d.mts.map +1 -1
  4. package/dist/badges.mjs +16 -4
  5. package/dist/badges.mjs.map +1 -1
  6. package/dist/{data.generated-Cb6g6asv.d.mts → data.generated-B2ceLfSn.d.mts} +9 -1
  7. package/dist/data.generated-B2ceLfSn.d.mts.map +1 -0
  8. package/dist/developer-products.d.mts +38 -2
  9. package/dist/developer-products.d.mts.map +1 -1
  10. package/dist/developer-products.mjs +32 -8
  11. package/dist/developer-products.mjs.map +1 -1
  12. package/dist/game-passes.d.mts +40 -2
  13. package/dist/game-passes.d.mts.map +1 -1
  14. package/dist/game-passes.mjs +30 -6
  15. package/dist/game-passes.mjs.map +1 -1
  16. package/dist/index.d.mts +21 -12
  17. package/dist/index.d.mts.map +1 -1
  18. package/dist/index.mjs +5 -5
  19. package/dist/locales.d.mts +1 -1
  20. package/dist/locales.mjs +2 -0
  21. package/dist/locales.mjs.map +1 -1
  22. package/dist/luau-execution.d.mts +22 -3
  23. package/dist/luau-execution.d.mts.map +1 -1
  24. package/dist/luau-execution.mjs +29 -13
  25. package/dist/luau-execution.mjs.map +1 -1
  26. package/dist/places.d.mts +20 -2
  27. package/dist/places.d.mts.map +1 -1
  28. package/dist/places.mjs +34 -14
  29. package/dist/places.mjs.map +1 -1
  30. package/dist/{poll-timeout-Dg_QFEqi.mjs → poll-timeout-BfxUWWCZ.mjs} +6 -2
  31. package/dist/poll-timeout-BfxUWWCZ.mjs.map +1 -0
  32. package/dist/{polling-helpers-CS00apdU.mjs → polling-helpers-DCw9LyJM.mjs} +225 -78
  33. package/dist/polling-helpers-DCw9LyJM.mjs.map +1 -0
  34. package/dist/{polling-BMrYajok.d.mts → polling-rj0dGREg.d.mts} +73 -14
  35. package/dist/polling-rj0dGREg.d.mts.map +1 -0
  36. package/dist/{price-information-DIrvwCmd.mjs → price-information-C4gC2CMZ.mjs} +2 -2
  37. package/dist/{price-information-DIrvwCmd.mjs.map → price-information-C4gC2CMZ.mjs.map} +1 -1
  38. package/dist/{rate-limit-D1q2Js-z.mjs → rate-limit-Dh2leqaB.mjs} +49 -3
  39. package/dist/rate-limit-Dh2leqaB.mjs.map +1 -0
  40. package/dist/resource-client-CIAkS2xQ.mjs +960 -0
  41. package/dist/resource-client-CIAkS2xQ.mjs.map +1 -0
  42. package/dist/retry-Bh2nNjBV.d.mts +234 -0
  43. package/dist/retry-Bh2nNjBV.d.mts.map +1 -0
  44. package/dist/retry-BvZRZDXs.mjs +380 -0
  45. package/dist/retry-BvZRZDXs.mjs.map +1 -0
  46. package/dist/{signatures-B5Fojgn0.mjs → signatures-JF-7Psce.mjs} +1 -1
  47. package/dist/{signatures-B5Fojgn0.mjs.map → signatures-JF-7Psce.mjs.map} +1 -1
  48. package/dist/storage.d.mts +30 -27
  49. package/dist/storage.d.mts.map +1 -1
  50. package/dist/storage.mjs +46 -31
  51. package/dist/storage.mjs.map +1 -1
  52. package/dist/testing.d.mts +24 -9
  53. package/dist/testing.d.mts.map +1 -1
  54. package/dist/testing.mjs +2 -2
  55. package/dist/testing.mjs.map +1 -1
  56. package/dist/{to-blob-B27VhoRp.mjs → to-blob-RPqMBuft.mjs} +1 -1
  57. package/dist/{to-blob-B27VhoRp.mjs.map → to-blob-RPqMBuft.mjs.map} +1 -1
  58. package/dist/{types-CwtZT1ek.d.mts → types-CRiJg5EQ.d.mts} +46 -4
  59. package/dist/types-CRiJg5EQ.d.mts.map +1 -0
  60. package/dist/universes.d.mts +47 -5
  61. package/dist/universes.d.mts.map +1 -1
  62. package/dist/universes.mjs +31 -15
  63. package/dist/universes.mjs.map +1 -1
  64. package/dist/{validation-DkL5KQqz.mjs → validation-xJZRa8tX.mjs} +4 -2
  65. package/dist/validation-xJZRa8tX.mjs.map +1 -0
  66. package/dist/{wire-CeL6W_V7.d.mts → wire-D3K-a-UP.d.mts} +3 -1
  67. package/dist/wire-D3K-a-UP.d.mts.map +1 -0
  68. package/package.json +6 -5
  69. package/dist/data.generated-Cb6g6asv.d.mts.map +0 -1
  70. package/dist/permission-error-DOVtNq3A.mjs +0 -46
  71. package/dist/permission-error-DOVtNq3A.mjs.map +0 -1
  72. package/dist/poll-timeout-Dg_QFEqi.mjs.map +0 -1
  73. package/dist/polling-BMrYajok.d.mts.map +0 -1
  74. package/dist/polling-helpers-CS00apdU.mjs.map +0 -1
  75. package/dist/rate-limit-BYuizHoD.d.mts +0 -92
  76. package/dist/rate-limit-BYuizHoD.d.mts.map +0 -1
  77. package/dist/rate-limit-D1q2Js-z.mjs.map +0 -1
  78. package/dist/resource-client-D6Efj9fU.mjs +0 -732
  79. package/dist/resource-client-D6Efj9fU.mjs.map +0 -1
  80. package/dist/types-CwtZT1ek.d.mts.map +0 -1
  81. package/dist/validation-DkL5KQqz.mjs.map +0 -1
  82. package/dist/wire-CeL6W_V7.d.mts.map +0 -1
@@ -0,0 +1,380 @@
1
+ import { n as NetworkError, r as ApiError, t as RateLimitError } from "./rate-limit-Dh2leqaB.mjs";
2
+ //#region src/errors/permission-error.ts
3
+ /**
4
+ * Thrown when the Roblox Open Cloud API returns a 401 or 403 for an operation
5
+ * whose required scopes are known. Subclass of {@link ApiError} carrying the
6
+ * scope strings the caller's credential is missing plus the operation key, so
7
+ * a CLI consumer can tell the user exactly which scope to grant on their API
8
+ * key.
9
+ *
10
+ * @since 0.1.0
11
+ *
12
+ * @example
13
+ *
14
+ * ```ts
15
+ * import { PermissionError } from "@bedrock-rbx/ocale";
16
+ *
17
+ * const error = new PermissionError("HTTP 403", {
18
+ * operationKey: "developer-products.create",
19
+ * requiredScopes: ["creator-store-product:write"],
20
+ * statusCode: 403,
21
+ * });
22
+ *
23
+ * expect(error).toBeInstanceOf(PermissionError);
24
+ * expect(error.requiredScopes).toStrictEqual(["creator-store-product:write"]);
25
+ * expect(error.operationKey).toBe("developer-products.create");
26
+ * ```
27
+ */
28
+ var PermissionError = class extends ApiError {
29
+ name = "PermissionError";
30
+ operationKey;
31
+ requiredScopes;
32
+ /**
33
+ * Creates a new PermissionError.
34
+ *
35
+ * @param message - Human-readable error description.
36
+ * @param options - Error options including status code, the operation key,
37
+ * and the scopes the caller's credential must carry.
38
+ */
39
+ constructor(message, options) {
40
+ super(message, options);
41
+ this.operationKey = options.operationKey;
42
+ this.requiredScopes = options.requiredScopes;
43
+ }
44
+ };
45
+ //#endregion
46
+ //#region src/internal/utils/find-error-code.ts
47
+ /**
48
+ * Maximum cause-chain depth walked by {@link findErrorCode}. Caps pathological
49
+ * self-referential or deeply nested chains; transport failures surface as
50
+ * `NetworkError → TypeError("fetch failed") → OS Error{code}`, so three
51
+ * levels is the expected shape and five leaves headroom.
52
+ */
53
+ const MAX_DEPTH = 5;
54
+ /**
55
+ * Walks an error's `cause` chain and returns the first node-style string
56
+ * `code` it finds (for example `"ECONNRESET"`, `"ETIMEDOUT"`). Native `fetch`
57
+ * surfaces a transport reset as a `NetworkError` wrapping a
58
+ * `TypeError("fetch failed")` whose own cause carries the OS-level `code`, so
59
+ * the code lives several links down the chain.
60
+ *
61
+ * @example
62
+ *
63
+ * ```ts
64
+ * import { findErrorCode } from "./find-error-code";
65
+ *
66
+ * const root = Object.assign(new Error("read ECONNRESET"), { code: "ECONNRESET" });
67
+ * const outer = new Error("Network request failed", {
68
+ * cause: new TypeError("fetch failed", { cause: root }),
69
+ * });
70
+ *
71
+ * expect(findErrorCode(outer)).toBe("ECONNRESET");
72
+ * ```
73
+ *
74
+ * @param error - The error to inspect; typically a `NetworkError`.
75
+ * @returns The first string `code` in the chain, or `undefined` if none.
76
+ */
77
+ function findErrorCode(error) {
78
+ let current = error;
79
+ for (let depth = 0; depth < MAX_DEPTH && current instanceof Error; depth += 1) {
80
+ const code = readCode(current);
81
+ if (code !== void 0) return code;
82
+ current = current.cause;
83
+ }
84
+ }
85
+ function readCode(error) {
86
+ const code = Reflect.get(error, "code");
87
+ return typeof code === "string" ? code : void 0;
88
+ }
89
+ /**
90
+ * `DOMException.name` produced when an `AbortSignal.timeout` fires. This is the
91
+ * web-standard discriminator (stable across Node and Bun, unlike the
92
+ * runtime-specific message) and distinguishes the SDK's own request timeout
93
+ * from a caller-supplied cancellation, which surfaces as `"AbortError"`.
94
+ */
95
+ const TIMEOUT_ABORT_NAME = "TimeoutError";
96
+ /**
97
+ * Reports whether an error chain was produced by the SDK's own
98
+ * `AbortSignal.timeout` self-abort. Such a `DOMException` carries a numeric
99
+ * `code` (23), so {@link findErrorCode} (which only reads string codes)
100
+ * cannot classify it; this walk keys on `name` instead. A caller-supplied
101
+ * abort (`"AbortError"`) is deliberately not matched.
102
+ *
103
+ * @example
104
+ *
105
+ * ```ts
106
+ * import { isTimeoutAbort } from "./find-error-code";
107
+ *
108
+ * const error = new Error("Network request failed", {
109
+ * cause: new DOMException("timed out", "TimeoutError"),
110
+ * });
111
+ *
112
+ * expect(isTimeoutAbort(error)).toBe(true);
113
+ * expect(isTimeoutAbort(new DOMException("cancelled", "AbortError"))).toBe(false);
114
+ * ```
115
+ *
116
+ * @param error - The error to inspect; typically a `NetworkError`.
117
+ * @returns `true` when a `TimeoutError` abort sits within the cause chain.
118
+ */
119
+ function isTimeoutAbort(error) {
120
+ let current = error;
121
+ for (let depth = 0; depth < MAX_DEPTH && current instanceof Error; depth += 1) {
122
+ if (Reflect.get(current, "name") === TIMEOUT_ABORT_NAME) return true;
123
+ current = current.cause;
124
+ }
125
+ return false;
126
+ }
127
+ //#endregion
128
+ //#region src/internal/http/retry.ts
129
+ /**
130
+ * Transient transport error codes that are safe to retry for idempotent
131
+ * operations. Connection resets, timeouts, and DNS hiccups are recoverable on
132
+ * a retry. A self-aborted request timeout carries no OS-level `code`, so
133
+ * {@link shouldRetry} folds it into this set as `ETIMEDOUT` (via
134
+ * {@link isTimeoutAbort}) for idempotent methods; create methods retry no
135
+ * transport codes and so still never re-issue a timed-out write.
136
+ *
137
+ * @since 0.1.0
138
+ */
139
+ const TRANSIENT_TRANSPORT_CODES = Object.freeze([
140
+ "ECONNRESET",
141
+ "ECONNREFUSED",
142
+ "ETIMEDOUT",
143
+ "EPIPE",
144
+ "ENETUNREACH",
145
+ "EHOSTDOWN",
146
+ "EAI_AGAIN",
147
+ "UND_ERR_SOCKET"
148
+ ]);
149
+ /**
150
+ * Default retry policy for idempotent operations (read, list, update,
151
+ * delete). Safe to retry on rate limits, transient server errors, and
152
+ * transient transport failures.
153
+ */
154
+ const IDEMPOTENT_METHOD_DEFAULTS = Object.freeze({
155
+ retryableStatuses: Object.freeze([
156
+ 429,
157
+ 500,
158
+ 502,
159
+ 503,
160
+ 504
161
+ ]),
162
+ retryableTransportCodes: TRANSIENT_TRANSPORT_CODES
163
+ });
164
+ /**
165
+ * Default retry policy for create operations. Retries rate limits only (no
166
+ * 5xx and no transport-error retries) to prevent duplicate resources, since
167
+ * Roblox Open Cloud has no idempotency-key support. Consumers who can tolerate
168
+ * a duplicate opt in per request.
169
+ */
170
+ const CREATE_METHOD_DEFAULTS = Object.freeze({
171
+ retryableStatuses: Object.freeze([429]),
172
+ retryableTransportCodes: Object.freeze([])
173
+ });
174
+ /**
175
+ * Default exponential backoff: 1s → 2s → 4s → 8s → 16s → 30s (capped).
176
+ *
177
+ * @example
178
+ *
179
+ * ```ts
180
+ * import { defaultRetryDelay } from "./retry";
181
+ *
182
+ * expect(defaultRetryDelay(0)).toBe(1000);
183
+ * expect(defaultRetryDelay(4)).toBe(16_000);
184
+ * expect(defaultRetryDelay(10)).toBe(30_000);
185
+ * ```
186
+ *
187
+ * @param attempt - Zero-indexed retry attempt number.
188
+ * @returns Wait duration in milliseconds.
189
+ */
190
+ function defaultRetryDelay(attempt) {
191
+ return Math.min(1e3 * 2 ** attempt, 3e4);
192
+ }
193
+ /**
194
+ * Computes how long to wait before the next retry. Prefers the server's
195
+ * suggested delay when the error is a {@link RateLimitError} with a positive
196
+ * `retryAfterSeconds`; otherwise falls through to `retryDelay(attempt)`.
197
+ *
198
+ * @example
199
+ *
200
+ * ```ts
201
+ * import { RateLimitError } from "../../errors/rate-limit.ts";
202
+ * import { computeRetryWaitMs, defaultRetryDelay } from "./retry";
203
+ *
204
+ * const error = new RateLimitError("slow down", { retryAfterSeconds: 3 });
205
+ *
206
+ * expect(computeRetryWaitMs(error, { attempt: 0, retryDelay: defaultRetryDelay })).toBe(
207
+ * 3000,
208
+ * );
209
+ * ```
210
+ *
211
+ * @example
212
+ *
213
+ * ```ts
214
+ * import { ApiError } from "../../errors/api-error.ts";
215
+ * import { computeRetryWaitMs, defaultRetryDelay } from "./retry";
216
+ *
217
+ * const error = new ApiError("server error", { statusCode: 503 });
218
+ *
219
+ * expect(computeRetryWaitMs(error, { attempt: 2, retryDelay: defaultRetryDelay })).toBe(
220
+ * 4000,
221
+ * );
222
+ * ```
223
+ *
224
+ * @param error - The error returned by the failing request.
225
+ * @param options - Retry attempt index and fallback delay function.
226
+ * @returns Wait duration in milliseconds before the next attempt.
227
+ */
228
+ function computeRetryWaitMs(error, options) {
229
+ if (error instanceof RateLimitError && error.retryAfterSeconds > 0) return error.retryAfterSeconds * 1e3;
230
+ return options.retryDelay(options.attempt);
231
+ }
232
+ /**
233
+ * Decides whether a failed request is eligible for retry. {@link RateLimitError}
234
+ * (checked against 429) and {@link ApiError} (checked against its `statusCode`)
235
+ * are retryable when their status is in `retryableStatuses`. A
236
+ * {@link NetworkError} is retryable when its transport code
237
+ * ({@link findErrorCode}) is in `retryableTransportCodes`. This is how
238
+ * transient connection resets recover. A self-aborted request timeout
239
+ * ({@link isTimeoutAbort}) carries no transport code, so it is classified as
240
+ * `ETIMEDOUT`: recovered for idempotent methods, never for creates (whose
241
+ * list is empty). All other failures return `false`.
242
+ *
243
+ * @example
244
+ *
245
+ * ```ts
246
+ * import { RateLimitError } from "../../errors/rate-limit.ts";
247
+ * import { shouldRetry } from "./retry";
248
+ *
249
+ * const error = new RateLimitError("", { retryAfterSeconds: 1 });
250
+ *
251
+ * expect(shouldRetry(error, { retryableStatuses: [429], retryableTransportCodes: [] })).toBe(
252
+ * true,
253
+ * );
254
+ * ```
255
+ *
256
+ * @example
257
+ *
258
+ * ```ts
259
+ * import { NetworkError } from "../../errors/network-error.ts";
260
+ * import { shouldRetry } from "./retry";
261
+ *
262
+ * const reset = Object.assign(new Error("read ECONNRESET"), { code: "ECONNRESET" });
263
+ * const error = new NetworkError("Network request failed", { cause: reset });
264
+ *
265
+ * expect(
266
+ * shouldRetry(error, { retryableStatuses: [], retryableTransportCodes: ["ECONNRESET"] }),
267
+ * ).toBe(true);
268
+ * ```
269
+ *
270
+ * @param error - The error returned by the failing request.
271
+ * @param config - Object carrying the retry-eligible status and transport-code lists.
272
+ * @returns `true` if the error should be retried, `false` otherwise.
273
+ */
274
+ function shouldRetry(error, config) {
275
+ if (error instanceof RateLimitError) return config.retryableStatuses.includes(429);
276
+ if (error instanceof ApiError) return config.retryableStatuses.includes(error.statusCode);
277
+ if (error instanceof NetworkError) {
278
+ const code = findErrorCode(error) ?? (isTimeoutAbort(error) ? "ETIMEDOUT" : void 0);
279
+ return code !== void 0 && config.retryableTransportCodes.includes(code);
280
+ }
281
+ return false;
282
+ }
283
+ /**
284
+ * Resolves the effective config for a single request by shallow-merging the
285
+ * client config, method defaults, and per-request options. Precedence depends
286
+ * on `methodKind`:
287
+ *
288
+ * - `"create"`: method defaults override client config, so client-level
289
+ * settings cannot silently relax create-method safety. Only explicit
290
+ * per-request `requestOptions` can.
291
+ * - `"idempotent"`: client config overrides method defaults, so consumers
292
+ * can loosen or tighten retry policy globally. `requestOptions` still wins
293
+ * when provided.
294
+ *
295
+ * Array-valued fields like `retryableStatuses` are *replaced*, not extended.
296
+ *
297
+ * @template T - Concrete `RetryResolvable` subtype being merged.
298
+ *
299
+ * @example
300
+ *
301
+ * ```ts
302
+ * import {
303
+ * CREATE_METHOD_DEFAULTS,
304
+ * defaultRetryDelay,
305
+ * mergeConfig,
306
+ * type RetryResolvable,
307
+ * } from "./retry";
308
+ *
309
+ * const clientConfig: RetryResolvable = {
310
+ * apiKey: "k",
311
+ * baseUrl: "https://apis.roblox.com",
312
+ * maxRetries: 3,
313
+ * retryableStatuses: [429, 500],
314
+ * retryableTransportCodes: [],
315
+ * retryDelay: defaultRetryDelay,
316
+ * timeout: 30_000,
317
+ * };
318
+ *
319
+ * const merged = mergeConfig(clientConfig, {
320
+ * methodDefaults: CREATE_METHOD_DEFAULTS,
321
+ * methodKind: "create",
322
+ * });
323
+ *
324
+ * expect(merged.retryableStatuses).toStrictEqual([429]);
325
+ * ```
326
+ *
327
+ * @example
328
+ *
329
+ * ```ts
330
+ * import {
331
+ * defaultRetryDelay,
332
+ * IDEMPOTENT_METHOD_DEFAULTS,
333
+ * mergeConfig,
334
+ * type RetryResolvable,
335
+ * } from "./retry";
336
+ *
337
+ * const clientConfig: RetryResolvable = {
338
+ * apiKey: "k",
339
+ * baseUrl: "https://apis.roblox.com",
340
+ * maxRetries: 3,
341
+ * retryableStatuses: [429],
342
+ * retryableTransportCodes: [],
343
+ * retryDelay: defaultRetryDelay,
344
+ * timeout: 30_000,
345
+ * };
346
+ *
347
+ * const merged = mergeConfig(clientConfig, {
348
+ * methodDefaults: IDEMPOTENT_METHOD_DEFAULTS,
349
+ * methodKind: "idempotent",
350
+ * requestOptions: { timeout: 10_000 },
351
+ * });
352
+ *
353
+ * expect(merged.retryableStatuses).toStrictEqual([429]);
354
+ * expect(merged.timeout).toBe(10_000);
355
+ * ```
356
+ *
357
+ * @param clientConfig - Config frozen at client construction.
358
+ * @param options - Method defaults, method kind, and optional per-request overrides.
359
+ * @returns A new merged config object. Inputs are not mutated.
360
+ */
361
+ function mergeConfig(clientConfig, options) {
362
+ const { methodDefaults, methodKind, requestOptions } = options;
363
+ switch (methodKind) {
364
+ case "create": return {
365
+ ...clientConfig,
366
+ ...methodDefaults,
367
+ ...requestOptions
368
+ };
369
+ case "idempotent": return {
370
+ ...methodDefaults,
371
+ ...clientConfig,
372
+ ...requestOptions
373
+ };
374
+ default: throw new Error(`Unexpected methodKind: ${String(methodKind)}`);
375
+ }
376
+ }
377
+ //#endregion
378
+ export { defaultRetryDelay as a, findErrorCode as c, computeRetryWaitMs as i, PermissionError as l, IDEMPOTENT_METHOD_DEFAULTS as n, mergeConfig as o, TRANSIENT_TRANSPORT_CODES as r, shouldRetry as s, CREATE_METHOD_DEFAULTS as t };
379
+
380
+ //# sourceMappingURL=retry-BvZRZDXs.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"retry-BvZRZDXs.mjs","names":["exhaustive"],"sources":["../src/errors/permission-error.ts","../src/internal/utils/find-error-code.ts","../src/internal/http/retry.ts"],"sourcesContent":["import { ApiError, type ApiErrorOptions } from \"./api-error.ts\";\n\n/**\n * Options for constructing a {@link PermissionError}.\n *\n * @since 0.1.0\n */\nexport interface PermissionErrorOptions extends ApiErrorOptions {\n\t/**\n\t * Stable identifier of the Open Cloud operation that returned the\n\t * permission failure (matches `OperationLimit.operationKey`, e.g.\n\t * `\"developer-products.create\"`).\n\t */\n\toperationKey: string;\n\t/**\n\t * Scope strings the API key or OAuth token must carry for the failing\n\t * operation, sourced from the vendored OpenAPI schema's `x-roblox-scopes`\n\t * for that operationId.\n\t */\n\trequiredScopes: ReadonlyArray<string>;\n}\n\n/**\n * Thrown when the Roblox Open Cloud API returns a 401 or 403 for an operation\n * whose required scopes are known. Subclass of {@link ApiError} carrying the\n * scope strings the caller's credential is missing plus the operation key, so\n * a CLI consumer can tell the user exactly which scope to grant on their API\n * key.\n *\n * @since 0.1.0\n *\n * @example\n *\n * ```ts\n * import { PermissionError } from \"@bedrock-rbx/ocale\";\n *\n * const error = new PermissionError(\"HTTP 403\", {\n * operationKey: \"developer-products.create\",\n * requiredScopes: [\"creator-store-product:write\"],\n * statusCode: 403,\n * });\n *\n * expect(error).toBeInstanceOf(PermissionError);\n * expect(error.requiredScopes).toStrictEqual([\"creator-store-product:write\"]);\n * expect(error.operationKey).toBe(\"developer-products.create\");\n * ```\n */\nexport class PermissionError extends ApiError {\n\tpublic override readonly name: string = \"PermissionError\";\n\tpublic readonly operationKey: string;\n\tpublic readonly requiredScopes: ReadonlyArray<string>;\n\n\t/**\n\t * Creates a new PermissionError.\n\t *\n\t * @param message - Human-readable error description.\n\t * @param options - Error options including status code, the operation key,\n\t * and the scopes the caller's credential must carry.\n\t */\n\tconstructor(message: string, options: PermissionErrorOptions) {\n\t\tsuper(message, options);\n\t\tthis.operationKey = options.operationKey;\n\t\tthis.requiredScopes = options.requiredScopes;\n\t}\n}\n","/**\n * Maximum cause-chain depth walked by {@link findErrorCode}. Caps pathological\n * self-referential or deeply nested chains; transport failures surface as\n * `NetworkError → TypeError(\"fetch failed\") → OS Error{code}`, so three\n * levels is the expected shape and five leaves headroom.\n */\nconst MAX_DEPTH = 5;\n\n/**\n * Walks an error's `cause` chain and returns the first node-style string\n * `code` it finds (for example `\"ECONNRESET\"`, `\"ETIMEDOUT\"`). Native `fetch`\n * surfaces a transport reset as a `NetworkError` wrapping a\n * `TypeError(\"fetch failed\")` whose own cause carries the OS-level `code`, so\n * the code lives several links down the chain.\n *\n * @example\n *\n * ```ts\n * import { findErrorCode } from \"./find-error-code\";\n *\n * const root = Object.assign(new Error(\"read ECONNRESET\"), { code: \"ECONNRESET\" });\n * const outer = new Error(\"Network request failed\", {\n * cause: new TypeError(\"fetch failed\", { cause: root }),\n * });\n *\n * expect(findErrorCode(outer)).toBe(\"ECONNRESET\");\n * ```\n *\n * @param error - The error to inspect; typically a `NetworkError`.\n * @returns The first string `code` in the chain, or `undefined` if none.\n */\nexport function findErrorCode(error: unknown): string | undefined {\n\tlet current: unknown = error;\n\tfor (let depth = 0; depth < MAX_DEPTH && current instanceof Error; depth += 1) {\n\t\tconst code = readCode(current);\n\t\tif (code !== undefined) {\n\t\t\treturn code;\n\t\t}\n\n\t\tcurrent = current.cause;\n\t}\n\n\treturn undefined;\n}\n\nfunction readCode(error: Error): string | undefined {\n\tconst code = Reflect.get(error, \"code\");\n\treturn typeof code === \"string\" ? code : undefined;\n}\n\n/**\n * `DOMException.name` produced when an `AbortSignal.timeout` fires. This is the\n * web-standard discriminator (stable across Node and Bun, unlike the\n * runtime-specific message) and distinguishes the SDK's own request timeout\n * from a caller-supplied cancellation, which surfaces as `\"AbortError\"`.\n */\nconst TIMEOUT_ABORT_NAME = \"TimeoutError\";\n\n/**\n * Reports whether an error chain was produced by the SDK's own\n * `AbortSignal.timeout` self-abort. Such a `DOMException` carries a numeric\n * `code` (23), so {@link findErrorCode} (which only reads string codes)\n * cannot classify it; this walk keys on `name` instead. A caller-supplied\n * abort (`\"AbortError\"`) is deliberately not matched.\n *\n * @example\n *\n * ```ts\n * import { isTimeoutAbort } from \"./find-error-code\";\n *\n * const error = new Error(\"Network request failed\", {\n * cause: new DOMException(\"timed out\", \"TimeoutError\"),\n * });\n *\n * expect(isTimeoutAbort(error)).toBe(true);\n * expect(isTimeoutAbort(new DOMException(\"cancelled\", \"AbortError\"))).toBe(false);\n * ```\n *\n * @param error - The error to inspect; typically a `NetworkError`.\n * @returns `true` when a `TimeoutError` abort sits within the cause chain.\n */\nexport function isTimeoutAbort(error: unknown): boolean {\n\tlet current: unknown = error;\n\tfor (let depth = 0; depth < MAX_DEPTH && current instanceof Error; depth += 1) {\n\t\tif (Reflect.get(current, \"name\") === TIMEOUT_ABORT_NAME) {\n\t\t\treturn true;\n\t\t}\n\n\t\tcurrent = current.cause;\n\t}\n\n\treturn false;\n}\n","import { ApiError } from \"../../errors/api-error.ts\";\nimport { NetworkError } from \"../../errors/network-error.ts\";\nimport { RateLimitError } from \"../../errors/rate-limit.ts\";\nimport { findErrorCode, isTimeoutAbort } from \"../utils/find-error-code.ts\";\n\n/**\n * Fully-resolved retry config shape that {@link mergeConfig} and\n * {@link shouldRetry} operate on. Fields are required because this represents\n * the post-defaulting, internal view; callers should supply every field (or\n * resolve them via a test factory / client constructor). The partial,\n * user-facing type lives on client construction options; method defaults and\n * per-request overrides use `Partial<RetryResolvable>`.\n */\nexport interface RetryResolvable {\n\t/** Roblox Open Cloud API key. */\n\treadonly apiKey: string;\n\t/** Base URL for the Open Cloud API. */\n\treadonly baseUrl: string;\n\t/** Maximum retry attempts before giving up. */\n\treadonly maxRetries: number;\n\t/** Status codes that are eligible for retry. */\n\treadonly retryableStatuses: ReadonlyArray<number>;\n\t/**\n\t * Node-style transport error codes ({@link findErrorCode}) eligible for\n\t * retry when surfaced as a {@link NetworkError}. Empty for create\n\t * operations by default; consumers opt a create in via a per-request\n\t * override.\n\t */\n\treadonly retryableTransportCodes: ReadonlyArray<string>;\n\t/** Fallback delay function when no server hint is available. */\n\treadonly retryDelay: (attempt: number) => number;\n\t/** Per-request timeout in milliseconds. */\n\treadonly timeout: number;\n}\n\n/**\n * Transient transport error codes that are safe to retry for idempotent\n * operations. Connection resets, timeouts, and DNS hiccups are recoverable on\n * a retry. A self-aborted request timeout carries no OS-level `code`, so\n * {@link shouldRetry} folds it into this set as `ETIMEDOUT` (via\n * {@link isTimeoutAbort}) for idempotent methods; create methods retry no\n * transport codes and so still never re-issue a timed-out write.\n *\n * @since 0.1.0\n */\nexport const TRANSIENT_TRANSPORT_CODES: ReadonlyArray<string> = Object.freeze([\n\t\"ECONNRESET\",\n\t\"ECONNREFUSED\",\n\t\"ETIMEDOUT\",\n\t\"EPIPE\",\n\t\"ENETUNREACH\",\n\t\"EHOSTDOWN\",\n\t\"EAI_AGAIN\",\n\t\"UND_ERR_SOCKET\",\n]);\n\n/** Method-level retry defaults, keyed by {@link MethodKind}. */\ntype MethodDefaults = Readonly<\n\tPick<RetryResolvable, \"retryableStatuses\" | \"retryableTransportCodes\">\n>;\n\n/**\n * Default retry policy for idempotent operations (read, list, update,\n * delete). Safe to retry on rate limits, transient server errors, and\n * transient transport failures.\n */\nexport const IDEMPOTENT_METHOD_DEFAULTS: MethodDefaults = Object.freeze({\n\tretryableStatuses: Object.freeze([429, 500, 502, 503, 504] as const),\n\tretryableTransportCodes: TRANSIENT_TRANSPORT_CODES,\n});\n\n/**\n * Default retry policy for create operations. Retries rate limits only (no\n * 5xx and no transport-error retries) to prevent duplicate resources, since\n * Roblox Open Cloud has no idempotency-key support. Consumers who can tolerate\n * a duplicate opt in per request.\n */\nexport const CREATE_METHOD_DEFAULTS: MethodDefaults = Object.freeze({\n\tretryableStatuses: Object.freeze([429] as const),\n\tretryableTransportCodes: Object.freeze([] as const),\n});\n\n/** Kind of HTTP method the merge is being performed for. */\nexport type MethodKind = \"create\" | \"idempotent\";\n\n/**\n * Options for {@link mergeConfig}.\n *\n * @template T - Concrete `RetryResolvable` subtype being merged.\n */\ninterface MergeConfigOptions<T> {\n\t/** Method-level defaults (e.g. {@link CREATE_METHOD_DEFAULTS}). */\n\treadonly methodDefaults: Partial<T>;\n\t/** Whether the method is a create or idempotent operation. */\n\treadonly methodKind: MethodKind;\n\t/** Optional per-request overrides; always win when provided. */\n\treadonly requestOptions?: Partial<T>;\n}\n\n/**\n * Options for {@link computeRetryWaitMs}.\n */\ninterface ComputeRetryWaitMsOptions {\n\t/** Zero-indexed retry attempt number. */\n\treadonly attempt: number;\n\t/** Fallback delay function when no server hint is available. */\n\treadonly retryDelay: (attempt: number) => number;\n}\n\n/**\n * Default exponential backoff: 1s → 2s → 4s → 8s → 16s → 30s (capped).\n *\n * @example\n *\n * ```ts\n * import { defaultRetryDelay } from \"./retry\";\n *\n * expect(defaultRetryDelay(0)).toBe(1000);\n * expect(defaultRetryDelay(4)).toBe(16_000);\n * expect(defaultRetryDelay(10)).toBe(30_000);\n * ```\n *\n * @param attempt - Zero-indexed retry attempt number.\n * @returns Wait duration in milliseconds.\n */\nexport function defaultRetryDelay(attempt: number): number {\n\treturn Math.min(1000 * 2 ** attempt, 30_000);\n}\n\n/**\n * Computes how long to wait before the next retry. Prefers the server's\n * suggested delay when the error is a {@link RateLimitError} with a positive\n * `retryAfterSeconds`; otherwise falls through to `retryDelay(attempt)`.\n *\n * @example\n *\n * ```ts\n * import { RateLimitError } from \"../../errors/rate-limit.ts\";\n * import { computeRetryWaitMs, defaultRetryDelay } from \"./retry\";\n *\n * const error = new RateLimitError(\"slow down\", { retryAfterSeconds: 3 });\n *\n * expect(computeRetryWaitMs(error, { attempt: 0, retryDelay: defaultRetryDelay })).toBe(\n * 3000,\n * );\n * ```\n *\n * @example\n *\n * ```ts\n * import { ApiError } from \"../../errors/api-error.ts\";\n * import { computeRetryWaitMs, defaultRetryDelay } from \"./retry\";\n *\n * const error = new ApiError(\"server error\", { statusCode: 503 });\n *\n * expect(computeRetryWaitMs(error, { attempt: 2, retryDelay: defaultRetryDelay })).toBe(\n * 4000,\n * );\n * ```\n *\n * @param error - The error returned by the failing request.\n * @param options - Retry attempt index and fallback delay function.\n * @returns Wait duration in milliseconds before the next attempt.\n */\nexport function computeRetryWaitMs(\n\terror: ApiError | NetworkError | RateLimitError,\n\toptions: ComputeRetryWaitMsOptions,\n): number {\n\tif (error instanceof RateLimitError && error.retryAfterSeconds > 0) {\n\t\treturn error.retryAfterSeconds * 1000;\n\t}\n\n\treturn options.retryDelay(options.attempt);\n}\n\n/**\n * Decides whether a failed request is eligible for retry. {@link RateLimitError}\n * (checked against 429) and {@link ApiError} (checked against its `statusCode`)\n * are retryable when their status is in `retryableStatuses`. A\n * {@link NetworkError} is retryable when its transport code\n * ({@link findErrorCode}) is in `retryableTransportCodes`. This is how\n * transient connection resets recover. A self-aborted request timeout\n * ({@link isTimeoutAbort}) carries no transport code, so it is classified as\n * `ETIMEDOUT`: recovered for idempotent methods, never for creates (whose\n * list is empty). All other failures return `false`.\n *\n * @example\n *\n * ```ts\n * import { RateLimitError } from \"../../errors/rate-limit.ts\";\n * import { shouldRetry } from \"./retry\";\n *\n * const error = new RateLimitError(\"\", { retryAfterSeconds: 1 });\n *\n * expect(shouldRetry(error, { retryableStatuses: [429], retryableTransportCodes: [] })).toBe(\n * true,\n * );\n * ```\n *\n * @example\n *\n * ```ts\n * import { NetworkError } from \"../../errors/network-error.ts\";\n * import { shouldRetry } from \"./retry\";\n *\n * const reset = Object.assign(new Error(\"read ECONNRESET\"), { code: \"ECONNRESET\" });\n * const error = new NetworkError(\"Network request failed\", { cause: reset });\n *\n * expect(\n * shouldRetry(error, { retryableStatuses: [], retryableTransportCodes: [\"ECONNRESET\"] }),\n * ).toBe(true);\n * ```\n *\n * @param error - The error returned by the failing request.\n * @param config - Object carrying the retry-eligible status and transport-code lists.\n * @returns `true` if the error should be retried, `false` otherwise.\n */\nexport function shouldRetry(\n\terror: unknown,\n\tconfig: {\n\t\treadonly retryableStatuses: ReadonlyArray<number>;\n\t\treadonly retryableTransportCodes: ReadonlyArray<string>;\n\t},\n): error is ApiError | NetworkError | RateLimitError {\n\tif (error instanceof RateLimitError) {\n\t\treturn config.retryableStatuses.includes(429);\n\t}\n\n\tif (error instanceof ApiError) {\n\t\treturn config.retryableStatuses.includes(error.statusCode);\n\t}\n\n\tif (error instanceof NetworkError) {\n\t\tconst code = findErrorCode(error) ?? (isTimeoutAbort(error) ? \"ETIMEDOUT\" : undefined);\n\t\treturn code !== undefined && config.retryableTransportCodes.includes(code);\n\t}\n\n\treturn false;\n}\n\n/**\n * Resolves the effective config for a single request by shallow-merging the\n * client config, method defaults, and per-request options. Precedence depends\n * on `methodKind`:\n *\n * - `\"create\"`: method defaults override client config, so client-level\n * settings cannot silently relax create-method safety. Only explicit\n * per-request `requestOptions` can.\n * - `\"idempotent\"`: client config overrides method defaults, so consumers\n * can loosen or tighten retry policy globally. `requestOptions` still wins\n * when provided.\n *\n * Array-valued fields like `retryableStatuses` are *replaced*, not extended.\n *\n * @template T - Concrete `RetryResolvable` subtype being merged.\n *\n * @example\n *\n * ```ts\n * import {\n * CREATE_METHOD_DEFAULTS,\n * defaultRetryDelay,\n * mergeConfig,\n * type RetryResolvable,\n * } from \"./retry\";\n *\n * const clientConfig: RetryResolvable = {\n * apiKey: \"k\",\n * baseUrl: \"https://apis.roblox.com\",\n * maxRetries: 3,\n * retryableStatuses: [429, 500],\n * retryableTransportCodes: [],\n * retryDelay: defaultRetryDelay,\n * timeout: 30_000,\n * };\n *\n * const merged = mergeConfig(clientConfig, {\n * methodDefaults: CREATE_METHOD_DEFAULTS,\n * methodKind: \"create\",\n * });\n *\n * expect(merged.retryableStatuses).toStrictEqual([429]);\n * ```\n *\n * @example\n *\n * ```ts\n * import {\n * defaultRetryDelay,\n * IDEMPOTENT_METHOD_DEFAULTS,\n * mergeConfig,\n * type RetryResolvable,\n * } from \"./retry\";\n *\n * const clientConfig: RetryResolvable = {\n * apiKey: \"k\",\n * baseUrl: \"https://apis.roblox.com\",\n * maxRetries: 3,\n * retryableStatuses: [429],\n * retryableTransportCodes: [],\n * retryDelay: defaultRetryDelay,\n * timeout: 30_000,\n * };\n *\n * const merged = mergeConfig(clientConfig, {\n * methodDefaults: IDEMPOTENT_METHOD_DEFAULTS,\n * methodKind: \"idempotent\",\n * requestOptions: { timeout: 10_000 },\n * });\n *\n * expect(merged.retryableStatuses).toStrictEqual([429]);\n * expect(merged.timeout).toBe(10_000);\n * ```\n *\n * @param clientConfig - Config frozen at client construction.\n * @param options - Method defaults, method kind, and optional per-request overrides.\n * @returns A new merged config object. Inputs are not mutated.\n */\nexport function mergeConfig<T extends RetryResolvable>(\n\tclientConfig: T,\n\toptions: MergeConfigOptions<T>,\n): T {\n\tconst { methodDefaults, methodKind, requestOptions } = options;\n\n\tswitch (methodKind) {\n\t\tcase \"create\": {\n\t\t\treturn { ...clientConfig, ...methodDefaults, ...requestOptions };\n\t\t}\n\t\tcase \"idempotent\": {\n\t\t\treturn { ...methodDefaults, ...clientConfig, ...requestOptions };\n\t\t}\n\t\tdefault: {\n\t\t\tconst exhaustive: never = methodKind;\n\t\t\tthrow new Error(`Unexpected methodKind: ${String(exhaustive)}`);\n\t\t}\n\t}\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;AA+CA,IAAa,kBAAb,cAAqC,SAAS;CAC7C,OAAwC;CACxC;CACA;;;;;;;;CASA,YAAY,SAAiB,SAAiC;EAC7D,MAAM,SAAS,OAAO;EACtB,KAAK,eAAe,QAAQ;EAC5B,KAAK,iBAAiB,QAAQ;CAC/B;AACD;;;;;;;;;AC1DA,MAAM,YAAY;;;;;;;;;;;;;;;;;;;;;;;;AAyBlB,SAAgB,cAAc,OAAoC;CACjE,IAAI,UAAmB;CACvB,KAAK,IAAI,QAAQ,GAAG,QAAQ,aAAa,mBAAmB,OAAO,SAAS,GAAG;EAC9E,MAAM,OAAO,SAAS,OAAO;EAC7B,IAAI,SAAS,KAAA,GACZ,OAAO;EAGR,UAAU,QAAQ;CACnB;AAGD;AAEA,SAAS,SAAS,OAAkC;CACnD,MAAM,OAAO,QAAQ,IAAI,OAAO,MAAM;CACtC,OAAO,OAAO,SAAS,WAAW,OAAO,KAAA;AAC1C;;;;;;;AAQA,MAAM,qBAAqB;;;;;;;;;;;;;;;;;;;;;;;;AAyB3B,SAAgB,eAAe,OAAyB;CACvD,IAAI,UAAmB;CACvB,KAAK,IAAI,QAAQ,GAAG,QAAQ,aAAa,mBAAmB,OAAO,SAAS,GAAG;EAC9E,IAAI,QAAQ,IAAI,SAAS,MAAM,MAAM,oBACpC,OAAO;EAGR,UAAU,QAAQ;CACnB;CAEA,OAAO;AACR;;;;;;;;;;;;;AC/CA,MAAa,4BAAmD,OAAO,OAAO;CAC7E;CACA;CACA;CACA;CACA;CACA;CACA;CACA;AACD,CAAC;;;;;;AAYD,MAAa,6BAA6C,OAAO,OAAO;CACvE,mBAAmB,OAAO,OAAO;EAAC;EAAK;EAAK;EAAK;EAAK;CAAG,CAAU;CACnE,yBAAyB;AAC1B,CAAC;;;;;;;AAQD,MAAa,yBAAyC,OAAO,OAAO;CACnE,mBAAmB,OAAO,OAAO,CAAC,GAAG,CAAU;CAC/C,yBAAyB,OAAO,OAAO,CAAC,CAAU;AACnD,CAAC;;;;;;;;;;;;;;;;;AA6CD,SAAgB,kBAAkB,SAAyB;CAC1D,OAAO,KAAK,IAAI,MAAO,KAAK,SAAS,GAAM;AAC5C;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAqCA,SAAgB,mBACf,OACA,SACS;CACT,IAAI,iBAAiB,kBAAkB,MAAM,oBAAoB,GAChE,OAAO,MAAM,oBAAoB;CAGlC,OAAO,QAAQ,WAAW,QAAQ,OAAO;AAC1C;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AA4CA,SAAgB,YACf,OACA,QAIoD;CACpD,IAAI,iBAAiB,gBACpB,OAAO,OAAO,kBAAkB,SAAS,GAAG;CAG7C,IAAI,iBAAiB,UACpB,OAAO,OAAO,kBAAkB,SAAS,MAAM,UAAU;CAG1D,IAAI,iBAAiB,cAAc;EAClC,MAAM,OAAO,cAAc,KAAK,MAAM,eAAe,KAAK,IAAI,cAAc,KAAA;EAC5E,OAAO,SAAS,KAAA,KAAa,OAAO,wBAAwB,SAAS,IAAI;CAC1E;CAEA,OAAO;AACR;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAgFA,SAAgB,YACf,cACA,SACI;CACJ,MAAM,EAAE,gBAAgB,YAAY,mBAAmB;CAEvD,QAAQ,YAAR;EACC,KAAK,UACJ,OAAO;GAAE,GAAG;GAAc,GAAG;GAAgB,GAAG;EAAe;EAEhE,KAAK,cACJ,OAAO;GAAE,GAAG;GAAgB,GAAG;GAAc,GAAG;EAAe;EAEhE,SAEC,MAAM,IAAI,MAAM,0BAA0B,OAAOA,UAAU,GAAG;CAEhE;AACD"}
@@ -56,4 +56,4 @@ function matchesSignature(body, signature) {
56
56
  //#endregion
57
57
  export { RBXL_SIGNATURE as n, matchesSignature as r, RBXLX_SIGNATURE as t };
58
58
 
59
- //# sourceMappingURL=signatures-B5Fojgn0.mjs.map
59
+ //# sourceMappingURL=signatures-JF-7Psce.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"signatures-B5Fojgn0.mjs","names":[],"sources":["../src/domains/universes/places/signatures.ts"],"sourcesContent":["/**\n * Magic-byte prefix every Roblox binary place file (`.rbxl`) starts with.\n * The first 8 bytes spell out `<roblox!` in ASCII; the remaining 6 bytes\n * (`\\x89\\xff\\r\\n\\x1a\\n`) are the binary-format marker that distinguishes a\n * binary place file from the XML form (`.rbxlx`), whose ASCII-only header\n * begins with `<roblox `.\n */\nexport const RBXL_SIGNATURE: Readonly<Uint8Array<ArrayBuffer>> = new Uint8Array([\n\t0x3c, 0x72, 0x6f, 0x62, 0x6c, 0x6f, 0x78, 0x21, 0x89, 0xff, 0x0d, 0x0a, 0x1a, 0x0a,\n]);\n\n/**\n * Magic-byte prefix every Roblox XML place file (`.rbxlx`) starts with.\n * Equivalent to the ASCII string `<roblox ` (note the trailing space): a\n * well-formed rbxlx file opens with `<roblox` followed by attributes, while\n * an rbxl file uses `<roblox!` (exclamation mark) as the eighth byte. The\n * trailing space is what proves the file is the XML variant rather than\n * the binary one.\n */\nexport const RBXLX_SIGNATURE: Readonly<Uint8Array<ArrayBuffer>> = new Uint8Array([\n\t0x3c, 0x72, 0x6f, 0x62, 0x6c, 0x6f, 0x78, 0x20,\n]);\n\n/**\n * Reports whether `body` begins with `signature`. A pure byte-prefix check\n * with no allocation; used by the place builder to disambiguate `.rbxl` and\n * `.rbxlx` payloads against their declared `format`.\n *\n * @param body - The caller-supplied place file bytes.\n * @param signature - One of the frozen signature constants from this module.\n * @returns `true` if every byte of `signature` matches `body[0..signature.length]`.\n */\nexport function matchesSignature(\n\tbody: Uint8Array,\n\tsignature: Readonly<Uint8Array<ArrayBuffer>>,\n): boolean {\n\tfor (const [index, expected] of signature.entries()) {\n\t\tif (body[index] !== expected) {\n\t\t\treturn false;\n\t\t}\n\t}\n\n\treturn true;\n}\n"],"mappings":";;;;;;;;AAOA,MAAa,iBAAoD,IAAI,WAAW;CAC/E;CAAM;CAAM;CAAM;CAAM;CAAM;CAAM;CAAM;CAAM;CAAM;CAAM;CAAM;CAAM;CAAM;CAC9E,CAAC;;;;;;;;;AAUF,MAAa,kBAAqD,IAAI,WAAW;CAChF;CAAM;CAAM;CAAM;CAAM;CAAM;CAAM;CAAM;CAC1C,CAAC;;;;;;;;;;AAWF,SAAgB,iBACf,MACA,WACU;AACV,MAAK,MAAM,CAAC,OAAO,aAAa,UAAU,SAAS,CAClD,KAAI,KAAK,WAAW,SACnB,QAAO;AAIT,QAAO"}
1
+ {"version":3,"file":"signatures-JF-7Psce.mjs","names":[],"sources":["../src/domains/universes/places/signatures.ts"],"sourcesContent":["/**\n * Magic-byte prefix every Roblox binary place file (`.rbxl`) starts with.\n * The first 8 bytes spell out `<roblox!` in ASCII; the remaining 6 bytes\n * (`\\x89\\xff\\r\\n\\x1a\\n`) are the binary-format marker that distinguishes a\n * binary place file from the XML form (`.rbxlx`), whose ASCII-only header\n * begins with `<roblox `.\n */\nexport const RBXL_SIGNATURE: Readonly<Uint8Array<ArrayBuffer>> = new Uint8Array([\n\t0x3c, 0x72, 0x6f, 0x62, 0x6c, 0x6f, 0x78, 0x21, 0x89, 0xff, 0x0d, 0x0a, 0x1a, 0x0a,\n]);\n\n/**\n * Magic-byte prefix every Roblox XML place file (`.rbxlx`) starts with.\n * Equivalent to the ASCII string `<roblox ` (note the trailing space): a\n * well-formed rbxlx file opens with `<roblox` followed by attributes, while\n * an rbxl file uses `<roblox!` (exclamation mark) as the eighth byte. The\n * trailing space is what proves the file is the XML variant rather than\n * the binary one.\n */\nexport const RBXLX_SIGNATURE: Readonly<Uint8Array<ArrayBuffer>> = new Uint8Array([\n\t0x3c, 0x72, 0x6f, 0x62, 0x6c, 0x6f, 0x78, 0x20,\n]);\n\n/**\n * Reports whether `body` begins with `signature`. A pure byte-prefix check\n * with no allocation; used by the place builder to disambiguate `.rbxl` and\n * `.rbxlx` payloads against their declared `format`.\n *\n * @param body - The caller-supplied place file bytes.\n * @param signature - One of the frozen signature constants from this module.\n * @returns `true` if every byte of `signature` matches `body[0..signature.length]`.\n */\nexport function matchesSignature(\n\tbody: Uint8Array,\n\tsignature: Readonly<Uint8Array<ArrayBuffer>>,\n): boolean {\n\tfor (const [index, expected] of signature.entries()) {\n\t\tif (body[index] !== expected) {\n\t\t\treturn false;\n\t\t}\n\t}\n\n\treturn true;\n}\n"],"mappings":";;;;;;;;AAOA,MAAa,iBAAoD,IAAI,WAAW;CAC/E;CAAM;CAAM;CAAM;CAAM;CAAM;CAAM;CAAM;CAAM;CAAM;CAAM;CAAM;CAAM;CAAM;AAC/E,CAAC;;;;;;;;;AAUD,MAAa,kBAAqD,IAAI,WAAW;CAChF;CAAM;CAAM;CAAM;CAAM;CAAM;CAAM;CAAM;AAC3C,CAAC;;;;;;;;;;AAWD,SAAgB,iBACf,MACA,WACU;CACV,KAAK,MAAM,CAAC,OAAO,aAAa,UAAU,QAAQ,GACjD,IAAI,KAAK,WAAW,UACnB,OAAO;CAIT,OAAO;AACR"}
@@ -1,9 +1,12 @@
1
- import { d as OpenCloudError, i as OpenCloudClientOptions, l as Result, n as HttpRequest, r as HttpResponse, s as RequestOptions, u as SleepFunc } from "./types-CwtZT1ek.mjs";
1
+ import { d as OpenCloudError, i as OpenCloudClientOptions, l as Result, n as HttpRequest, r as HttpResponse, s as RequestOptions, u as SleepFunc } from "./types-CRiJg5EQ.mjs";
2
+ import { n as RetryResolvable, t as MethodKind } from "./retry-Bh2nNjBV.mjs";
2
3
 
3
4
  //#region src/domains/cloud-v2/memory-store-queues/types.d.ts
4
5
  /**
5
6
  * Caller-supplied input for the `enqueue` method on `StorageClient.queues`.
6
7
  * Mirrors `Cloud_CreateMemoryStoreQueueItem` on the Open Cloud API.
8
+ *
9
+ * @since 0.1.0
7
10
  */
8
11
  interface EnqueueQueueItemParameters {
9
12
  /**
@@ -34,6 +37,8 @@ interface EnqueueQueueItemParameters {
34
37
  * Parsed representation of a memory-store queue item, as returned by the
35
38
  * Open Cloud `Cloud_CreateMemoryStoreQueueItem` and (inside the array)
36
39
  * `Cloud_ReadMemoryStoreQueueItems` endpoints.
40
+ *
41
+ * @since 0.1.0
37
42
  */
38
43
  interface QueueItem {
39
44
  /** Server-generated item identifier, parsed from the wire `path`. */
@@ -55,6 +60,8 @@ interface QueueItem {
55
60
  /**
56
61
  * Caller-supplied input for the `dequeue` method on
57
62
  * `StorageClient.queues`. Mirrors `Cloud_ReadMemoryStoreQueueItems`.
63
+ *
64
+ * @since 0.1.0
58
65
  */
59
66
  interface DequeueQueueItemsParameters {
60
67
  /**
@@ -84,6 +91,8 @@ interface DequeueQueueItemsParameters {
84
91
  * response. The `readId` value must be passed to a subsequent
85
92
  * `discard` call to acknowledge the items; otherwise the items reappear
86
93
  * once the invisibility window elapses.
94
+ *
95
+ * @since 0.1.0
87
96
  */
88
97
  interface DequeueResult {
89
98
  /** Items dequeued from the front of the queue, in dequeue order. */
@@ -100,6 +109,8 @@ interface DequeueResult {
100
109
  * Acknowledging a `readId` removes the dequeued batch from the queue
101
110
  * permanently; without `discard`, the items reappear once their
102
111
  * invisibility window elapses.
112
+ *
113
+ * @since 0.1.0
103
114
  */
104
115
  interface DiscardQueueItemsParameters {
105
116
  /** Stringified queue identifier. */
@@ -116,6 +127,8 @@ interface DiscardQueueItemsParameters {
116
127
  * server contract requires at most one of `stringSortKey` or
117
128
  * `numericSortKey`; the union surfaces that constraint at the type
118
129
  * level so callers cannot accidentally set both.
130
+ *
131
+ * @since 0.1.0
119
132
  */
120
133
  type SortKey = {
121
134
  readonly kind: "numeric";
@@ -128,6 +141,8 @@ type SortKey = {
128
141
  * Caller-supplied input for the `create` method on
129
142
  * `StorageClient.sortedMaps`. Mirrors
130
143
  * `Cloud_CreateMemoryStoreSortedMapItem` on the Open Cloud API.
144
+ *
145
+ * @since 0.1.0
131
146
  */
132
147
  interface CreateSortedMapItemParameters {
133
148
  /**
@@ -159,6 +174,8 @@ interface CreateSortedMapItemParameters {
159
174
  * `Cloud_ListMemoryStoreSortedMapItems` on the Open Cloud API. All
160
175
  * paging and filtering parameters are optional; omitting them returns
161
176
  * up to one item server-side (`maxPageSize` defaults to `1`).
177
+ *
178
+ * @since 0.1.0
162
179
  */
163
180
  interface ListSortedMapItemsParameters {
164
181
  /**
@@ -190,6 +207,8 @@ interface ListSortedMapItemsParameters {
190
207
  /**
191
208
  * Parsed representation of a sorted-map item, as returned by every
192
209
  * sorted-map operation that yields a single item.
210
+ *
211
+ * @since 0.1.0
193
212
  */
194
213
  interface SortedMapItem {
195
214
  /** Item identifier, parsed from the wire `path`. */
@@ -221,6 +240,8 @@ interface SortedMapItem {
221
240
  /**
222
241
  * Parsed result of a successful `Cloud_ListMemoryStoreSortedMapItems`
223
242
  * response.
243
+ *
244
+ * @since 0.1.0
224
245
  */
225
246
  interface ListSortedMapItemsResult {
226
247
  /** Items returned in the current page, ordered per `orderBy`. */
@@ -235,6 +256,8 @@ interface ListSortedMapItemsResult {
235
256
  * Caller-supplied input for the `delete` method on
236
257
  * `StorageClient.sortedMaps`. Mirrors
237
258
  * `Cloud_DeleteMemoryStoreSortedMapItem` on the Open Cloud API.
259
+ *
260
+ * @since 0.1.0
238
261
  */
239
262
  interface DeleteSortedMapItemParameters {
240
263
  /** Caller-supplied item identifier. URL-encoded by the builder. */
@@ -248,6 +271,8 @@ interface DeleteSortedMapItemParameters {
248
271
  * Caller-supplied input for the `get` method on
249
272
  * `StorageClient.sortedMaps`. Mirrors
250
273
  * `Cloud_GetMemoryStoreSortedMapItem` on the Open Cloud API.
274
+ *
275
+ * @since 0.1.0
251
276
  */
252
277
  interface GetSortedMapItemParameters {
253
278
  /** Caller-supplied item identifier. URL-encoded by the builder. */
@@ -263,6 +288,8 @@ interface GetSortedMapItemParameters {
263
288
  * `Cloud_UpdateMemoryStoreSortedMapItem` on the Open Cloud API. Body
264
289
  * fields (`value`, `ttl`, `sortKey`) are optional under PATCH
265
290
  * semantics; omitted fields are left unchanged on the server.
291
+ *
292
+ * @since 0.1.0
266
293
  */
267
294
  interface UpdateSortedMapItemParameters {
268
295
  /**
@@ -308,32 +335,6 @@ interface OperationLimit {
308
335
  readonly operationKey: string;
309
336
  }
310
337
  //#endregion
311
- //#region src/internal/http/retry.d.ts
312
- /**
313
- * Fully-resolved retry config shape that {@link mergeConfig} and
314
- * {@link shouldRetry} operate on. Fields are required because this represents
315
- * the post-defaulting, internal view — callers should supply every field (or
316
- * resolve them via a test factory / client constructor). The partial,
317
- * user-facing type lives on client construction options; method defaults and
318
- * per-request overrides use `Partial<RetryResolvable>`.
319
- */
320
- interface RetryResolvable {
321
- /** Roblox Open Cloud API key. */
322
- readonly apiKey: string;
323
- /** Base URL for the Open Cloud API. */
324
- readonly baseUrl: string;
325
- /** Maximum retry attempts before giving up. */
326
- readonly maxRetries: number;
327
- /** Status codes that are eligible for retry. */
328
- readonly retryableStatuses: ReadonlyArray<number>;
329
- /** Fallback delay function when no server hint is available. */
330
- readonly retryDelay: (attempt: number) => number;
331
- /** Per-request timeout in milliseconds. */
332
- readonly timeout: number;
333
- }
334
- /** Kind of HTTP method the merge is being performed for. */
335
- type MethodKind = "create" | "idempotent";
336
- //#endregion
337
338
  //#region src/internal/resource-client.d.ts
338
339
  /**
339
340
  * Describes a single resource method's shape for dispatch through
@@ -635,6 +636,8 @@ declare class MemoryStoreSortedMapsGroup {
635
636
  * Every method returns a `Result` so callers handle failure
636
637
  * explicitly; no thrown error ever escapes the client.
637
638
  *
639
+ * @since 0.1.0
640
+ *
638
641
  * @example
639
642
  *
640
643
  * ```ts
@@ -1 +1 @@
1
- {"version":3,"file":"storage.d.mts","names":[],"sources":["../src/domains/cloud-v2/memory-store-queues/types.ts","../src/domains/cloud-v2/memory-store-sorted-maps/types.ts","../src/internal/http/rate-limit-queue.ts","../src/internal/http/retry.ts","../src/internal/resource-client.ts","../src/resources/storage/queues-group.ts","../src/resources/storage/sorted-maps-group.ts","../src/resources/storage/client.ts"],"mappings":"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"}
1
+ {"version":3,"file":"storage.d.mts","names":[],"sources":["../src/domains/cloud-v2/memory-store-queues/types.ts","../src/domains/cloud-v2/memory-store-sorted-maps/types.ts","../src/internal/http/rate-limit-queue.ts","../src/internal/resource-client.ts","../src/resources/storage/queues-group.ts","../src/resources/storage/sorted-maps-group.ts","../src/resources/storage/client.ts"],"mappings":"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"}