@classytic/arc 2.43.0 → 2.45.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/dist/{EventTransport-tzA7CAB4.mjs → EventTransport-Ci6hGO1Y.mjs} +2 -2
- package/dist/{HookSystem-B6UaKRbF.mjs → HookSystem-CtnnYHME.mjs} +2 -2
- package/dist/{ResourceRegistry-CuCARu2B.mjs → ResourceRegistry-BNoHOx-D.mjs} +2 -2
- package/dist/acquire-BW_2Dt60.mjs +35 -0
- package/dist/{actionPermissions-BotX1YOa.mjs → actionPermissions-TAc_6LCw.mjs} +13 -17
- package/dist/audit/index.d.mts +6 -6
- package/dist/audit/index.mjs +4 -4
- package/dist/auth/audit.d.mts +8 -8
- package/dist/auth/audit.mjs +1 -1
- package/dist/auth/index.d.mts +5 -5
- package/dist/auth/index.mjs +14 -12
- package/dist/auth/redis-session.d.mts +4 -5
- package/dist/auth/redis-session.mjs +1 -1
- package/dist/{authorizationDecision-DQYrkl5f.mjs → authorizationDecision-BixzgirP.mjs} +4 -4
- package/dist/{boundedMap-BULzfXYU.mjs → boundedMap-DQfXgxMo.mjs} +1 -1
- package/dist/{buildHandler-CRQ8EcX5.mjs → buildHandler-mEUmO2_u.mjs} +4 -4
- package/dist/cache/index.d.mts +9 -9
- package/dist/cache/index.mjs +4 -4
- package/dist/{caching-Cc2M1DwO.mjs → caching-TQfW2QX7.mjs} +2 -2
- package/dist/{claimed-B10RTfkM.mjs → claimed-CnEEOHuL.mjs} +1 -1
- package/dist/cleanup/index.d.mts +14 -14
- package/dist/cleanup/index.mjs +4 -4
- package/dist/cli/commands/describe.d.mts +5 -5
- package/dist/cli/commands/describe.mjs +3 -3
- package/dist/cli/commands/docs.d.mts +2 -3
- package/dist/cli/commands/docs.mjs +3 -3
- package/dist/cli/commands/doctor.d.mts +2 -3
- package/dist/cli/commands/doctor.mjs +1 -1
- package/dist/cli/commands/generate.mjs +2 -3
- package/dist/cli/commands/init.mjs +2 -3
- package/dist/cli/commands/introspect.d.mts +2 -3
- package/dist/cli/commands/introspect.mjs +2 -2
- package/dist/cli/index.mjs +3 -3
- package/dist/{constants-Cu7Mx7_U.mjs → constants-B90SnSQn.mjs} +1 -1
- package/dist/context/index.d.mts +9 -9
- package/dist/context/index.mjs +5 -5
- package/dist/core/index.d.mts +3 -3
- package/dist/core/index.mjs +8 -8
- package/dist/{core-Cb0LjccA.mjs → core-DV9PSXtr.mjs} +13 -4
- package/dist/{createActionRouter-xjqonMRO.mjs → createActionRouter-BgPCYU2U.mjs} +18 -8
- package/dist/{createAggregationRouter-zRYWw_5D.mjs → createAggregationRouter-lNCkDwKe.mjs} +7 -7
- package/dist/{createApp-D-953ZAq.mjs → createApp-BSBPntOQ.mjs} +34 -32
- package/dist/{createMcpServer-C9cxS8zt.d.mts → createMcpServer-DSztofa9.d.mts} +1 -1
- package/dist/{defineAggregation-Bm8RjMbq.mjs → defineAggregation-CwD8_XNd.mjs} +1 -1
- package/dist/{defineResource-DIC7JZGU.mjs → defineResource-CRkhRRSj.mjs} +7 -7
- package/dist/discovery/index.d.mts +6 -7
- package/dist/discovery/index.mjs +1 -1
- package/dist/docs/index.d.mts +3 -3
- package/dist/docs/index.mjs +3 -3
- package/dist/{elevation-DG8SrLN-.mjs → elevation-BAfsnnO0.mjs} +5 -5
- package/dist/encryption/index.d.mts +5 -5
- package/dist/encryption/index.mjs +3 -3
- package/dist/{errorHandler-BnfDviL1.mjs → errorHandler-DbHGwrQM.mjs} +3 -3
- package/dist/{errors-CtrywMHP.mjs → errors-C9G4A8cN.mjs} +1 -1
- package/dist/{eventPlugin-Q6BhzHzs.mjs → eventPlugin-Dghr7iL5.mjs} +8 -8
- package/dist/{eventTypes-Cdhm6ZlV.mjs → eventTypes-DDy7BMAn.mjs} +2 -2
- package/dist/events/index.d.mts +14 -14
- package/dist/events/index.mjs +7 -7
- package/dist/events/transports/redis-stream-entry.mjs +4 -4
- package/dist/events/transports/redis.d.mts +4 -5
- package/dist/events/transports/redis.mjs +2 -2
- package/dist/factory/index.d.mts +16 -16
- package/dist/factory/index.mjs +6 -6
- package/dist/{fastify-augmentation-DhUJ-mvo.d.mts → fastify-augmentation-DRlCIWE9.d.mts} +2 -2
- package/dist/{fields-ToPYpMqS.mjs → fields-Da--1DNS.mjs} +1 -1
- package/dist/{filter-merge-IpGywvym.mjs → filter-merge-BYKBa9b2.mjs} +1 -1
- package/dist/{generate-DRTkLlIl.mjs → generate-Cm5Ct81v.mjs} +2 -2
- package/dist/{headers-BbkIF6vA.mjs → headers-B6DRXXzT.mjs} +2 -2
- package/dist/{health-D-Ft6JM6.mjs → health-hRGgxnOC.mjs} +1 -1
- package/dist/{health-DqbsG-_w.mjs → health-pLbfckGB.mjs} +1 -1
- package/dist/hooks/index.d.mts +1 -1
- package/dist/hooks/index.mjs +2 -3
- package/dist/idempotency/index.d.mts +8 -6
- package/dist/idempotency/index.mjs +108 -46
- package/dist/idempotency/redis.d.mts +1 -1
- package/dist/idempotency/redis.mjs +30 -2
- package/dist/{index-CRoPtISf.d.mts → index-Beg3aNnK.d.mts} +3 -31
- package/dist/{index-JdbZAIsm.d.mts → index-CUJvoyw3.d.mts} +1 -1
- package/dist/{index-mqaqZNpe.d.mts → index-WH7xgvxS.d.mts} +52 -1
- package/dist/{index-C8zVGYsk.d.mts → index-uhkUA5-U.d.mts} +4 -4
- package/dist/index.d.mts +5 -5
- package/dist/index.mjs +11 -11
- package/dist/{init-B_oUYDXI.mjs → init-lpaUB-Ph.mjs} +1 -1
- package/dist/integrations/event-gateway.d.mts +3 -4
- package/dist/integrations/event-gateway.mjs +2 -2
- package/dist/integrations/index.d.mts +1 -1
- package/dist/integrations/index.mjs +1 -1
- package/dist/integrations/jobs/index.mjs +3 -3
- package/dist/integrations/mcp/index.d.mts +36 -36
- package/dist/integrations/mcp/index.mjs +2 -2
- package/dist/integrations/mcp/testing.d.mts +8 -9
- package/dist/integrations/mcp/testing.mjs +2 -2
- package/dist/integrations/streamline.d.mts +12 -13
- package/dist/integrations/streamline.mjs +18 -4
- package/dist/integrations/webhooks.d.mts +23 -23
- package/dist/integrations/webhooks.mjs +3 -3
- package/dist/integrations/websocket-pushref-redis.d.mts +4 -5
- package/dist/integrations/websocket-pushref-redis.mjs +1 -1
- package/dist/integrations/websocket-redis.d.mts +4 -5
- package/dist/integrations/websocket-redis.mjs +1 -1
- package/dist/integrations/websocket.mjs +2 -2
- package/dist/{interface-C0395yUN.d.mts → interface-JJzwH4Ro.d.mts} +22 -2
- package/dist/{jsonBody-B4YVGcql.mjs → jsonBody-CzKHE-Fg.mjs} +2 -2
- package/dist/{keys-B2KtgMLJ.mjs → keys-BoZKnBel.mjs} +1 -1
- package/dist/{loadResources-Dn4lalw2.mjs → loadResources-BEKG6bP9.mjs} +3 -3
- package/dist/{loadResourcesFromEntry-3sLYbuse.mjs → loadResourcesFromEntry-BEPA0ptL.mjs} +2 -2
- package/dist/logger/index.d.mts +9 -10
- package/dist/logger/index.mjs +2 -3
- package/dist/{logger-DXjfIqjV.mjs → logger-vxu0DXf_.mjs} +1 -1
- package/dist/{mcpPlugin-C08HalN5.mjs → mcpPlugin-DP_UB0LK.mjs} +42 -29
- package/dist/{memory-9Cp7611C.mjs → memory-DJN6kyC8.mjs} +3 -3
- package/dist/{metrics-CWI11eRu.mjs → metrics-wfr7XFE7.mjs} +3 -3
- package/dist/middleware/index.d.mts +5 -5
- package/dist/middleware/index.mjs +3 -3
- package/dist/migrations/index.d.mts +13 -13
- package/dist/migrations/index.mjs +2 -2
- package/dist/{module-BSvOQC7E.mjs → module-BtdcGn_E.mjs} +1 -1
- package/dist/mongodb-memory-server-Cn57YIsc.mjs +35539 -0
- package/dist/mongoose-DzFjTtBN.mjs +67451 -0
- package/dist/{multiTenant-cY0FkDiA.d.mts → multiTenant-CAtYlW6H.d.mts} +1 -1
- package/dist/{multipartBody-CXM2a-Dy.mjs → multipartBody-NHGOuUnG.mjs} +1 -1
- package/dist/node-C0HB_V6E.mjs +41236 -0
- package/dist/{openapi-DT_G4VhY.mjs → openapi-BCOaGAgE.mjs} +6 -6
- package/dist/outbox-admin/index.d.mts +2 -2
- package/dist/outbox-admin/index.mjs +5 -5
- package/dist/{outbox-module-Bjgzl6tg.mjs → outbox-module-BVDiMwXb.mjs} +9 -9
- package/dist/permissions/index.mjs +7 -7
- package/dist/{permissions-Cm0uYHvd.mjs → permissions-IdHJ0_5V.mjs} +9 -9
- package/dist/{pipe-BqeGT6UO.mjs → pipe-BPJPifhi.mjs} +2 -2
- package/dist/pipeline/index.d.mts +7 -7
- package/dist/pipeline/index.mjs +2 -2
- package/dist/{plan-FVR6LP59.mjs → plan-CEedaMlr.mjs} +1 -1
- package/dist/{plugin-BccET1tL.mjs → plugin-BDBOS3-c.mjs} +39 -27
- package/dist/plugins/index.d.mts +8 -8
- package/dist/plugins/index.mjs +17 -17
- package/dist/plugins/response-cache.d.mts +5 -6
- package/dist/plugins/response-cache.mjs +4 -4
- package/dist/plugins/tracing-entry.mjs +2 -2
- package/dist/{pluralize-CVIOcgMF.mjs → pluralize-B4FcZEyI.mjs} +1 -1
- package/dist/presets/filesUpload.d.mts +7 -7
- package/dist/presets/filesUpload.mjs +5 -5
- package/dist/presets/index.d.mts +14 -14
- package/dist/presets/index.mjs +2 -2
- package/dist/presets/multiTenant.d.mts +1 -1
- package/dist/presets/multiTenant.mjs +5 -5
- package/dist/presets/search.d.mts +8 -9
- package/dist/presets/search.mjs +2 -2
- package/dist/{presets-Cpvj6fGO.mjs → presets-BPjNc-Np.mjs} +4 -4
- package/dist/{projection-Ce4aQhQk.mjs → projection-BXUOYosj.mjs} +2 -2
- package/dist/{queryCachePlugin-CFWNH8aT.mjs → queryCachePlugin-s4pBvjFF.mjs} +6 -6
- package/dist/{rateLimitKey-C4O-kPm0.mjs → rateLimitKey-C4mkCwQ-.mjs} +1 -1
- package/dist/{realtime-DmPE9S54.mjs → realtime-MPj6eIoV.mjs} +11 -11
- package/dist/{redis-vLvtcGy_.d.mts → redis-BDgv9Glw.d.mts} +5 -1
- package/dist/registry/index.d.mts +9 -9
- package/dist/registry/index.mjs +3 -3
- package/dist/{registry-Bcz9G1bh.mjs → registry-DIdh6mWE.mjs} +5 -4
- package/dist/{renewingLease-qODa7KJQ.mjs → renewingLease-boGRXWCr.mjs} +1 -1
- package/dist/{replyHelpers-CG_VtVgS.mjs → replyHelpers-BW_p67QD.mjs} +2 -2
- package/dist/{requestContext-Dsu9P1bV.mjs → requestContext-B8JKbeb7.mjs} +1 -1
- package/dist/{requirement-KDdoRcOP.mjs → requirement-tXpcD56f.mjs} +1 -1
- package/dist/{resourceRateLimit-dSjVr1pk.mjs → resourceRateLimit-DWob9nQ8.mjs} +2 -2
- package/dist/rolldown-runtime-AD16t29l.mjs +45 -0
- package/dist/{routeValidator-D36SW8qt.mjs → routeValidator-CnmenC4Y.mjs} +1 -1
- package/dist/{runtimeCapabilities-0tccjRlj.mjs → runtimeCapabilities-C7gAbIxC.mjs} +1 -1
- package/dist/{schedules-C-OpmHBq.mjs → schedules-Dr9gNFzx.mjs} +5 -5
- package/dist/{schemaConverter-BORek3O-.mjs → schemaConverter-rzBovk00.mjs} +2 -2
- package/dist/{schemaIR-C7Vbp71I.mjs → schemaIR-GrOK1JO4.mjs} +2 -2
- package/dist/schemas/index.d.mts +10 -10
- package/dist/schemas/index.mjs +1 -1
- package/dist/scim/index.d.mts +13 -13
- package/dist/scim/index.mjs +2 -2
- package/dist/scope/index.d.mts +3 -3
- package/dist/scope/index.mjs +5 -5
- package/dist/{scope-DQthe88b.mjs → scope-DpOpxyHT.mjs} +4 -4
- package/dist/{shutdown-MqA81z_P.mjs → shutdown-BW8qwgpx.mjs} +1 -1
- package/dist/{simpleEqualityMatcher-auW8QjXN.mjs → simpleEqualityMatcher-WdZw6GOt.mjs} +1 -1
- package/dist/sse-D8AgoUN3.mjs +212 -0
- package/dist/{sseStream-B5_Afiqn.mjs → sseStream-B7rPhIQw.mjs} +2 -2
- package/dist/{store-helpers-BOzk-CuX.mjs → store-helpers-Bxk7TDgG.mjs} +1 -1
- package/dist/{streaming-DjTQhZrN.mjs → streaming-BLg1buwL.mjs} +1 -1
- package/dist/{subscriberIdentity-CW39uA8G.mjs → subscriberIdentity-Cxp19Ked.mjs} +1 -1
- package/dist/{tenancy--ed9eH_z.mjs → tenancy-D7jo78AP.mjs} +2 -2
- package/dist/{tenantPreparation-BKon6Yox.mjs → tenantPreparation-DqJnokDW.mjs} +4 -4
- package/dist/testing/cleanupStoreContract.d.mts +4 -5
- package/dist/testing/cleanupStoreContract.mjs +1 -1
- package/dist/testing/index.d.mts +35 -35
- package/dist/testing/index.mjs +16 -15
- package/dist/testing/outboxStoreContract.d.mts +4 -5
- package/dist/testing/outboxStoreContract.mjs +2 -2
- package/dist/testing/requiredPorts.d.mts +4 -5
- package/dist/testing/requiredPorts.mjs +2 -2
- package/dist/testing/storageContract.d.mts +4 -5
- package/dist/testing/storageContract.mjs +1 -1
- package/dist/{timing-qczZ0YC-.mjs → timing-Y6_ZpoYG.mjs} +1 -1
- package/dist/{transactionContext-DjFkrNG6.mjs → transactionContext-BWp0MBGL.mjs} +1 -1
- package/dist/{typeGuards-CySF12G-.mjs → typeGuards-CtZJypJO.mjs} +1 -1
- package/dist/types/index.d.mts +1 -1
- package/dist/types/index.mjs +1 -1
- package/dist/types/storage.mjs +1 -1
- package/dist/{types-Bk9NOgOC.mjs → types-4JKkSvds.mjs} +4 -4
- package/dist/{types-B4Aq4Sdj.d.mts → types-D3Ixsh00.d.mts} +1 -1
- package/dist/usage/index.d.mts +4 -4
- package/dist/usage/index.mjs +4 -4
- package/dist/{userHelpers-aklawRaK.mjs → userHelpers-Nc5ePCsf.mjs} +1 -1
- package/dist/utils/index.d.mts +47 -47
- package/dist/utils/index.mjs +12 -12
- package/dist/{utils-ec1oTo1n.mjs → utils-QWSIKqAk.mjs} +4 -4
- package/dist/{validate-9yzHC1e2.mjs → validate-CT4umNhp.mjs} +3 -3
- package/dist/{versioning-Bsb51gGT.d.mts → versioning-Bqm_57Qt.d.mts} +23 -1
- package/dist/{versioning-fhhWHV74.mjs → versioning-JIqxO64K.mjs} +3 -3
- package/dist/{workScope-zpPyge4t.mjs → workScope-BDjGXwU9.mjs} +2 -2
- package/package.json +47 -52
- package/dist/rolldown-runtime-D1w9Y1VJ.mjs +0 -15
- package/dist/sse-CYzQBVFe.mjs +0 -89
package/dist/scim/index.d.mts
CHANGED
|
@@ -33,15 +33,15 @@ interface ScimResourceMapping {
|
|
|
33
33
|
/** Custom outbound transform — runs after attribute mapping. */
|
|
34
34
|
toScim?: (resource: Record<string, unknown>, mapped: Record<string, unknown>) => Record<string, unknown>;
|
|
35
35
|
}
|
|
36
|
-
declare const SCIM_USER_SCHEMA = "urn:ietf:params:scim:schemas:core:2.0:User";
|
|
37
|
-
declare const SCIM_GROUP_SCHEMA = "urn:ietf:params:scim:schemas:core:2.0:Group";
|
|
38
|
-
declare const SCIM_ENTERPRISE_USER_SCHEMA = "urn:ietf:params:scim:schemas:extension:enterprise:2.0:User";
|
|
39
|
-
declare const DEFAULT_USER_MAPPING: ScimResourceMapping;
|
|
40
|
-
declare const DEFAULT_GROUP_MAPPING: ScimResourceMapping;
|
|
36
|
+
export declare const SCIM_USER_SCHEMA = "urn:ietf:params:scim:schemas:core:2.0:User";
|
|
37
|
+
export declare const SCIM_GROUP_SCHEMA = "urn:ietf:params:scim:schemas:core:2.0:Group";
|
|
38
|
+
export declare const SCIM_ENTERPRISE_USER_SCHEMA = "urn:ietf:params:scim:schemas:extension:enterprise:2.0:User";
|
|
39
|
+
export declare const DEFAULT_USER_MAPPING: ScimResourceMapping;
|
|
40
|
+
export declare const DEFAULT_GROUP_MAPPING: ScimResourceMapping;
|
|
41
41
|
/** Translate inbound SCIM JSON → resource shape. */
|
|
42
|
-
declare function scimToResource(scim: Record<string, unknown>, mapping: ScimResourceMapping): Record<string, unknown>;
|
|
42
|
+
export declare function scimToResource(scim: Record<string, unknown>, mapping: ScimResourceMapping): Record<string, unknown>;
|
|
43
43
|
/** Translate resource → SCIM JSON. */
|
|
44
|
-
declare function resourceToScim(resource: Record<string, unknown>, mapping: ScimResourceMapping, baseUrl: string): Record<string, unknown>;
|
|
44
|
+
export declare function resourceToScim(resource: Record<string, unknown>, mapping: ScimResourceMapping, baseUrl: string): Record<string, unknown>;
|
|
45
45
|
//#endregion
|
|
46
46
|
//#region src/scim/types.d.ts
|
|
47
47
|
/**
|
|
@@ -138,7 +138,7 @@ interface ScimObservedEvent {
|
|
|
138
138
|
* ```
|
|
139
139
|
*/
|
|
140
140
|
type ScimType = "invalidFilter" | "tooMany" | "uniqueness" | "mutability" | "invalidSyntax" | "invalidPath" | "noTarget" | "invalidValue" | "invalidVers" | "sensitive";
|
|
141
|
-
declare class ScimError extends Error {
|
|
141
|
+
export declare class ScimError extends Error {
|
|
142
142
|
readonly statusCode: number;
|
|
143
143
|
readonly scimType?: ScimType;
|
|
144
144
|
constructor(statusCode: number, scimType: ScimType | undefined, detail: string);
|
|
@@ -197,9 +197,9 @@ type FilterNode = {
|
|
|
197
197
|
* `undefined` to deny (yields 400 invalidFilter). Use `IDENTITY_MAP` when
|
|
198
198
|
* the resource exposes SCIM-named attributes directly.
|
|
199
199
|
*/
|
|
200
|
-
declare function parseScimFilter(filter: string, mapAttr: (scimAttr: string) => string | undefined): Record<string, unknown>;
|
|
200
|
+
export declare function parseScimFilter(filter: string, mapAttr: (scimAttr: string) => string | undefined): Record<string, unknown>;
|
|
201
201
|
/** Pass-through mapper for resources that already use SCIM attribute names. */
|
|
202
|
-
declare const IDENTITY_MAP: (a: string) => string;
|
|
202
|
+
export declare const IDENTITY_MAP: (a: string) => string;
|
|
203
203
|
//#endregion
|
|
204
204
|
//#region src/scim/patch.d.ts
|
|
205
205
|
/**
|
|
@@ -248,17 +248,17 @@ interface ScimUpdate {
|
|
|
248
248
|
/** Field unset (remove without filter). */
|
|
249
249
|
$unset: Record<string, true>;
|
|
250
250
|
}
|
|
251
|
-
declare function parseScimPatch(req: ScimPatchRequest): ScimUpdate;
|
|
251
|
+
export declare function parseScimPatch(req: ScimPatchRequest): ScimUpdate;
|
|
252
252
|
/**
|
|
253
253
|
* Flatten a {@link ScimUpdate} into a plain `{ field: value }` object suitable
|
|
254
254
|
* for arc resource `PATCH` handlers that expect a partial document. Drops
|
|
255
255
|
* `$push` / `$pull` / `$unset` semantics — use {@link parseScimPatch} directly
|
|
256
256
|
* when the host needs the full op stream (e.g. to issue array mutations).
|
|
257
257
|
*/
|
|
258
|
-
declare function scimUpdateToFlatPatch(update: ScimUpdate): Record<string, unknown>;
|
|
258
|
+
export declare function scimUpdateToFlatPatch(update: ScimUpdate): Record<string, unknown>;
|
|
259
259
|
//#endregion
|
|
260
260
|
//#region src/scim/index.d.ts
|
|
261
261
|
declare const scimPlugin: FastifyPluginAsync<ScimPluginOptions>;
|
|
262
262
|
declare const _default: FastifyPluginAsync<ScimPluginOptions>;
|
|
263
263
|
//#endregion
|
|
264
|
-
export {
|
|
264
|
+
export { type FilterNode, type ScimObservedEvent, type ScimPatchRequest, type ScimPluginOptions, type ScimResourceBinding, type ScimResourceMapping, type ScimType, type ScimUpdate, _default as default, scimPlugin };
|
package/dist/scim/index.mjs
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
/*! @classytic/arc v2.
|
|
2
|
-
import { t as parseJsonBody } from "../jsonBody-
|
|
1
|
+
/*! @classytic/arc v2.45.0 | MIT | https://classytic.com */
|
|
2
|
+
import { t as parseJsonBody } from "../jsonBody-CzKHE-Fg.mjs";
|
|
3
3
|
import fp from "fastify-plugin";
|
|
4
4
|
//#region src/scim/errors.ts
|
|
5
5
|
var ScimError = class extends Error {
|
package/dist/scope/index.d.mts
CHANGED
|
@@ -11,7 +11,7 @@ interface TenantKeyGeneratorOptions {
|
|
|
11
11
|
/** Custom strategy — overrides default scope-based logic */
|
|
12
12
|
strategy?: (ctx: RateLimitKeyContext) => string;
|
|
13
13
|
}
|
|
14
|
-
declare function createTenantKeyGenerator(opts?: TenantKeyGeneratorOptions): (ctx: RateLimitKeyContext) => string;
|
|
14
|
+
export declare function createTenantKeyGenerator(opts?: TenantKeyGeneratorOptions): (ctx: RateLimitKeyContext) => string;
|
|
15
15
|
//#endregion
|
|
16
16
|
//#region src/scope/resolveOrgFromHeader.d.ts
|
|
17
17
|
interface ResolveOrgFromHeaderOptions {
|
|
@@ -28,6 +28,6 @@ interface ResolveOrgFromHeaderOptions {
|
|
|
28
28
|
* If the header is present and user is a member, sets `request.scope` to `member`.
|
|
29
29
|
* If the header is absent, scope stays as-is (typically `authenticated`).
|
|
30
30
|
*/
|
|
31
|
-
declare function resolveOrgFromHeader(options: ResolveOrgFromHeaderOptions): (request: FastifyRequest, reply: FastifyReply) => Promise<void>;
|
|
31
|
+
export declare function resolveOrgFromHeader(options: ResolveOrgFromHeaderOptions): (request: FastifyRequest, reply: FastifyReply) => Promise<void>;
|
|
32
32
|
//#endregion
|
|
33
|
-
export { AUTHENTICATED_SCOPE, type ElevationEvent, type ElevationOptions, type Mandate, PUBLIC_SCOPE, type RateLimitKeyContext, type RequestScope, type ResolveOrgFromHeaderOptions, type ScopeFirstCtx, type ScopeFirstCtxOptions, type ScopeFirstCtxRequest, type TenantKeyGeneratorOptions,
|
|
33
|
+
export { AUTHENTICATED_SCOPE, type ElevationEvent, type ElevationOptions, type Mandate, PUBLIC_SCOPE, type RateLimitKeyContext, type RequestScope, type ResolveOrgFromHeaderOptions, type ScopeFirstCtx, type ScopeFirstCtxOptions, type ScopeFirstCtxRequest, type TenantKeyGeneratorOptions, _default as elevationPlugin, getAncestorOrgIds, getClientId, getDPoPJkt, getMandate, getOrgContext, getOrgId, getOrgRoles, getRequestScope, getScopeContext, getScopeContextMap, getServiceScopes, getTeamId, getTenantFromRequest, getUserId, getUserRoles, hasOrgAccess, isAuthenticated, isElevated, isMember, isOrgInScope, isService, requireClientId, requireOrgId, requireTeamId, requireUserId, scopeFirstCtx };
|
package/dist/scope/index.mjs
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
/*! @classytic/arc v2.
|
|
2
|
-
import { C as isService, D as requireUserId, E as requireTeamId, O as scopeFirstCtx, S as isOrgInScope, T as requireOrgId, _ as getUserRoles, a as getDPoPJkt, b as isElevated, c as getOrgId, d as getScopeContext, f as getScopeContextMap, g as getUserId, h as getTenantFromRequest, i as getClientId, l as getOrgRoles, m as getTeamId, n as PUBLIC_SCOPE, o as getMandate, p as getServiceScopes, r as getAncestorOrgIds, s as getOrgContext, t as AUTHENTICATED_SCOPE, u as getRequestScope, v as hasOrgAccess, w as requireClientId, x as isMember, y as isAuthenticated } from "../types-
|
|
3
|
-
import { t as createTenantKeyGenerator } from "../rateLimitKey-
|
|
4
|
-
import { t as elevation_default } from "../elevation-
|
|
5
|
-
import { t as resolveOrgFromHeader } from "../scope-
|
|
1
|
+
/*! @classytic/arc v2.45.0 | MIT | https://classytic.com */
|
|
2
|
+
import { C as isService, D as requireUserId, E as requireTeamId, O as scopeFirstCtx, S as isOrgInScope, T as requireOrgId, _ as getUserRoles, a as getDPoPJkt, b as isElevated, c as getOrgId, d as getScopeContext, f as getScopeContextMap, g as getUserId, h as getTenantFromRequest, i as getClientId, l as getOrgRoles, m as getTeamId, n as PUBLIC_SCOPE, o as getMandate, p as getServiceScopes, r as getAncestorOrgIds, s as getOrgContext, t as AUTHENTICATED_SCOPE, u as getRequestScope, v as hasOrgAccess, w as requireClientId, x as isMember, y as isAuthenticated } from "../types-4JKkSvds.mjs";
|
|
3
|
+
import { t as createTenantKeyGenerator } from "../rateLimitKey-C4mkCwQ-.mjs";
|
|
4
|
+
import { t as elevation_default } from "../elevation-BAfsnnO0.mjs";
|
|
5
|
+
import { t as resolveOrgFromHeader } from "../scope-DpOpxyHT.mjs";
|
|
6
6
|
export { AUTHENTICATED_SCOPE, PUBLIC_SCOPE, createTenantKeyGenerator, elevation_default as elevationPlugin, getAncestorOrgIds, getClientId, getDPoPJkt, getMandate, getOrgContext, getOrgId, getOrgRoles, getRequestScope, getScopeContext, getScopeContextMap, getServiceScopes, getTeamId, getTenantFromRequest, getUserId, getUserRoles, hasOrgAccess, isAuthenticated, isElevated, isMember, isOrgInScope, isService, requireClientId, requireOrgId, requireTeamId, requireUserId, resolveOrgFromHeader, scopeFirstCtx };
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
/*! @classytic/arc v2.
|
|
2
|
-
import { a as OrgAccessDeniedError, l as UnauthorizedError } from "./errors-
|
|
3
|
-
import { n as requireSingleHeaderValue } from "./headers-
|
|
4
|
-
import { n as getUserRoles } from "./userHelpers-
|
|
1
|
+
/*! @classytic/arc v2.45.0 | MIT | https://classytic.com */
|
|
2
|
+
import { a as OrgAccessDeniedError, l as UnauthorizedError } from "./errors-C9G4A8cN.mjs";
|
|
3
|
+
import { n as requireSingleHeaderValue } from "./headers-B6DRXXzT.mjs";
|
|
4
|
+
import { n as getUserRoles } from "./userHelpers-Nc5ePCsf.mjs";
|
|
5
5
|
//#region src/scope/resolveOrgFromHeader.ts
|
|
6
6
|
/**
|
|
7
7
|
* Create a preHandler hook that resolves org scope from a header.
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/*! @classytic/arc v2.
|
|
1
|
+
/*! @classytic/arc v2.45.0 | MIT | https://classytic.com */
|
|
2
2
|
import { AsyncLocalStorage } from "node:async_hooks";
|
|
3
3
|
//#region src/utils/shutdown.ts
|
|
4
4
|
/** Stop admissions across every runtime before draining work and disposing domain engines. */
|
|
@@ -0,0 +1,212 @@
|
|
|
1
|
+
/*! @classytic/arc v2.45.0 | MIT | https://classytic.com */
|
|
2
|
+
import { r as __exportAll } from "./rolldown-runtime-AD16t29l.mjs";
|
|
3
|
+
import { t as arcLog } from "./logger-vxu0DXf_.mjs";
|
|
4
|
+
import { g as getUserId, n as PUBLIC_SCOPE } from "./types-4JKkSvds.mjs";
|
|
5
|
+
import { n as isEventVisible, t as eventAudienceOf } from "./tenancy-D7jo78AP.mjs";
|
|
6
|
+
import { a as promoteStreamTokenToHeader } from "./streaming-BLg1buwL.mjs";
|
|
7
|
+
import { t as openSseStream } from "./sseStream-B7rPhIQw.mjs";
|
|
8
|
+
import fp from "fastify-plugin";
|
|
9
|
+
//#region src/plugins/sse.ts
|
|
10
|
+
var sse_exports = /* @__PURE__ */ __exportAll({
|
|
11
|
+
default: () => sse_default,
|
|
12
|
+
ssePlugin: () => ssePlugin
|
|
13
|
+
});
|
|
14
|
+
const log = arcLog("sse");
|
|
15
|
+
/** Per-registration stats providers behind one `sseStats` decorator. */
|
|
16
|
+
const statsProviders = /* @__PURE__ */ new WeakMap();
|
|
17
|
+
function registerStats(fastify, provider) {
|
|
18
|
+
if (fastify.hasDecorator("sseStats")) {
|
|
19
|
+
statsProviders.get(fastify.sseStats)?.add(provider);
|
|
20
|
+
return;
|
|
21
|
+
}
|
|
22
|
+
const providers = /* @__PURE__ */ new Set([provider]);
|
|
23
|
+
const sseStats = () => {
|
|
24
|
+
const total = {
|
|
25
|
+
connections: 0,
|
|
26
|
+
keys: 0
|
|
27
|
+
};
|
|
28
|
+
for (const p of providers) {
|
|
29
|
+
const s = p();
|
|
30
|
+
total.connections += s.connections;
|
|
31
|
+
total.keys += s.keys;
|
|
32
|
+
}
|
|
33
|
+
return total;
|
|
34
|
+
};
|
|
35
|
+
statsProviders.set(sseStats, providers);
|
|
36
|
+
fastify.decorate("sseStats", sseStats);
|
|
37
|
+
}
|
|
38
|
+
const serializeEvent = (event) => JSON.stringify({
|
|
39
|
+
type: event.type,
|
|
40
|
+
payload: event.payload,
|
|
41
|
+
meta: {
|
|
42
|
+
id: event.meta.id,
|
|
43
|
+
timestamp: event.meta.timestamp
|
|
44
|
+
}
|
|
45
|
+
});
|
|
46
|
+
const ssePlugin = async (fastify, opts = {}) => {
|
|
47
|
+
const { path = "/events/stream", requireAuth = true, patterns = ["*"], heartbeat = 3e4, orgScoped = true, filter: customFilter, tokenQueryParam = "token", audience: resolveAudience, connectionKey = (request) => getUserId(request.scope ?? PUBLIC_SCOPE) } = opts;
|
|
48
|
+
if (!fastify.hasDecorator("events")) {
|
|
49
|
+
log.warn("Events plugin (arc-events) not registered. SSE plugin will not function. Register eventPlugin before ssePlugin.");
|
|
50
|
+
return;
|
|
51
|
+
}
|
|
52
|
+
const activeConnections = /* @__PURE__ */ new Set();
|
|
53
|
+
const connections = /* @__PURE__ */ new Set();
|
|
54
|
+
const byKey = /* @__PURE__ */ new Map();
|
|
55
|
+
const sharedUnsubs = [];
|
|
56
|
+
let sharedSubscription;
|
|
57
|
+
const visibleTo = (conn, event) => (!orgScoped || isEventVisible(event.meta?.organizationId, conn.orgAudience)) && (!customFilter || customFilter(event, conn.request));
|
|
58
|
+
const dispatch = (event) => {
|
|
59
|
+
let keys;
|
|
60
|
+
try {
|
|
61
|
+
keys = resolveAudience?.(event);
|
|
62
|
+
if (keys != null && !Array.isArray(keys)) throw new TypeError("audience must return an array");
|
|
63
|
+
} catch (error) {
|
|
64
|
+
log.error(`audience resolver failed for '${event.type}'; event not delivered`, error);
|
|
65
|
+
return;
|
|
66
|
+
}
|
|
67
|
+
let data;
|
|
68
|
+
let filterFailed = false;
|
|
69
|
+
const deliver = (conn) => {
|
|
70
|
+
try {
|
|
71
|
+
if (!visibleTo(conn, event)) return;
|
|
72
|
+
} catch (error) {
|
|
73
|
+
if (!filterFailed) log.error(`filter threw for '${event.type}'`, error);
|
|
74
|
+
filterFailed = true;
|
|
75
|
+
return;
|
|
76
|
+
}
|
|
77
|
+
data ??= serializeEvent(event);
|
|
78
|
+
conn.stream.write(event.type, data);
|
|
79
|
+
};
|
|
80
|
+
if (keys == null) {
|
|
81
|
+
for (const conn of connections) deliver(conn);
|
|
82
|
+
return;
|
|
83
|
+
}
|
|
84
|
+
for (const key of new Set(keys)) {
|
|
85
|
+
const set = byKey.get(key);
|
|
86
|
+
if (set) for (const conn of set) deliver(conn);
|
|
87
|
+
}
|
|
88
|
+
};
|
|
89
|
+
const ensureSharedSubscription = () => {
|
|
90
|
+
sharedSubscription ??= (async () => {
|
|
91
|
+
for (const pattern of patterns) sharedUnsubs.push(await fastify.events.subscribe(pattern, dispatch));
|
|
92
|
+
})().catch((error) => {
|
|
93
|
+
for (const unsub of sharedUnsubs.splice(0)) unsub();
|
|
94
|
+
sharedSubscription = void 0;
|
|
95
|
+
throw error;
|
|
96
|
+
});
|
|
97
|
+
return sharedSubscription;
|
|
98
|
+
};
|
|
99
|
+
registerStats(fastify, () => resolveAudience ? {
|
|
100
|
+
connections: connections.size,
|
|
101
|
+
keys: byKey.size
|
|
102
|
+
} : {
|
|
103
|
+
connections: activeConnections.size,
|
|
104
|
+
keys: 0
|
|
105
|
+
});
|
|
106
|
+
const routeOpts = {
|
|
107
|
+
method: "GET",
|
|
108
|
+
url: path,
|
|
109
|
+
schema: {
|
|
110
|
+
tags: ["Events"],
|
|
111
|
+
summary: "SSE event stream",
|
|
112
|
+
description: "Server-Sent Events stream for real-time domain events",
|
|
113
|
+
response: { 200: {
|
|
114
|
+
type: "string",
|
|
115
|
+
description: "text/event-stream"
|
|
116
|
+
} }
|
|
117
|
+
},
|
|
118
|
+
handler: async (request, reply) => {
|
|
119
|
+
const stream = openSseStream(request, reply, { heartbeatMs: heartbeat });
|
|
120
|
+
stream.onCleanup(() => activeConnections.delete(stream.close));
|
|
121
|
+
const scope = request.scope ?? PUBLIC_SCOPE;
|
|
122
|
+
const audience = eventAudienceOf(scope);
|
|
123
|
+
if (resolveAudience) {
|
|
124
|
+
const key = connectionKey(request) || void 0;
|
|
125
|
+
const conn = {
|
|
126
|
+
request,
|
|
127
|
+
stream,
|
|
128
|
+
orgAudience: audience,
|
|
129
|
+
key
|
|
130
|
+
};
|
|
131
|
+
let closed = false;
|
|
132
|
+
stream.onCleanup(() => {
|
|
133
|
+
closed = true;
|
|
134
|
+
activeConnections.delete(stream.close);
|
|
135
|
+
connections.delete(conn);
|
|
136
|
+
const set = key === void 0 ? void 0 : byKey.get(key);
|
|
137
|
+
if (set?.delete(conn) && set.size === 0) byKey.delete(key);
|
|
138
|
+
});
|
|
139
|
+
await ensureSharedSubscription();
|
|
140
|
+
if (closed) return;
|
|
141
|
+
connections.add(conn);
|
|
142
|
+
if (key !== void 0) {
|
|
143
|
+
const set = byKey.get(key) ?? /* @__PURE__ */ new Set();
|
|
144
|
+
set.add(conn);
|
|
145
|
+
byKey.set(key, set);
|
|
146
|
+
}
|
|
147
|
+
activeConnections.add(stream.close);
|
|
148
|
+
return;
|
|
149
|
+
}
|
|
150
|
+
let closed = false;
|
|
151
|
+
const unsubs = [];
|
|
152
|
+
stream.onCleanup(() => {
|
|
153
|
+
closed = true;
|
|
154
|
+
for (const unsub of unsubs.splice(0)) unsub();
|
|
155
|
+
});
|
|
156
|
+
for (const pattern of patterns) {
|
|
157
|
+
const unsub = await fastify.events.subscribe(pattern, async (event) => {
|
|
158
|
+
if (orgScoped && !isEventVisible(event.meta?.organizationId, audience)) return;
|
|
159
|
+
if (customFilter && !customFilter(event, request)) return;
|
|
160
|
+
const data = JSON.stringify({
|
|
161
|
+
type: event.type,
|
|
162
|
+
payload: event.payload,
|
|
163
|
+
meta: {
|
|
164
|
+
id: event.meta.id,
|
|
165
|
+
timestamp: event.meta.timestamp
|
|
166
|
+
}
|
|
167
|
+
});
|
|
168
|
+
stream.write(event.type, data);
|
|
169
|
+
});
|
|
170
|
+
if (closed) {
|
|
171
|
+
unsub();
|
|
172
|
+
return;
|
|
173
|
+
}
|
|
174
|
+
unsubs.push(unsub);
|
|
175
|
+
}
|
|
176
|
+
activeConnections.add(stream.close);
|
|
177
|
+
}
|
|
178
|
+
};
|
|
179
|
+
if (requireAuth) {
|
|
180
|
+
routeOpts.preHandler = (request, reply) => {
|
|
181
|
+
if (tokenQueryParam) promoteStreamTokenToHeader(request, tokenQueryParam);
|
|
182
|
+
const authenticate = fastify.authenticate;
|
|
183
|
+
if (typeof authenticate !== "function") {
|
|
184
|
+
reply.code(401).send({ error: "Unauthorized" });
|
|
185
|
+
return Promise.resolve();
|
|
186
|
+
}
|
|
187
|
+
return authenticate(request, reply);
|
|
188
|
+
};
|
|
189
|
+
fastify.addHook("onReady", async () => {
|
|
190
|
+
if (!fastify.hasDecorator("authenticate")) throw new Error("[arc-sse] requireAuth is true but no `authenticate` decorator was registered by the time the app was ready. Register an auth plugin, or set requireAuth: false.");
|
|
191
|
+
});
|
|
192
|
+
}
|
|
193
|
+
fastify.route(routeOpts);
|
|
194
|
+
fastify.addHook("onClose", async () => {
|
|
195
|
+
for (const cleanup of activeConnections) cleanup();
|
|
196
|
+
activeConnections.clear();
|
|
197
|
+
for (const unsub of sharedUnsubs.splice(0)) unsub();
|
|
198
|
+
});
|
|
199
|
+
log.debug("Plugin registered", {
|
|
200
|
+
path,
|
|
201
|
+
patterns,
|
|
202
|
+
orgScoped,
|
|
203
|
+
keyed: Boolean(resolveAudience)
|
|
204
|
+
});
|
|
205
|
+
};
|
|
206
|
+
var sse_default = fp(ssePlugin, {
|
|
207
|
+
name: "arc-sse",
|
|
208
|
+
fastify: "5.x",
|
|
209
|
+
dependencies: ["arc-events"]
|
|
210
|
+
});
|
|
211
|
+
//#endregion
|
|
212
|
+
export { sse_exports as n, sse_default as t };
|
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
/*! @classytic/arc v2.
|
|
2
|
-
import { n as forwardedStreamHeaders } from "./streaming-
|
|
1
|
+
/*! @classytic/arc v2.45.0 | MIT | https://classytic.com */
|
|
2
|
+
import { n as forwardedStreamHeaders } from "./streaming-BLg1buwL.mjs";
|
|
3
3
|
//#region src/utils/sseStream.ts
|
|
4
4
|
/**
|
|
5
5
|
* Take over the reply socket and open an SSE stream. Call ONLY after every
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/*! @classytic/arc v2.
|
|
1
|
+
/*! @classytic/arc v2.45.0 | MIT | https://classytic.com */
|
|
2
2
|
//#region src/events/subscriberIdentity.ts
|
|
3
3
|
const SUBSCRIBER_ID = Symbol.for("@classytic/arc/subscriber-id");
|
|
4
4
|
/** Assign a deployment-stable identity for durable per-handler progress; never use an index. */
|
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
/*! @classytic/arc v2.
|
|
2
|
-
import { b as isElevated, c as getOrgId } from "./types-
|
|
1
|
+
/*! @classytic/arc v2.45.0 | MIT | https://classytic.com */
|
|
2
|
+
import { b as isElevated, c as getOrgId } from "./types-4JKkSvds.mjs";
|
|
3
3
|
//#region src/core/tenancy.ts
|
|
4
4
|
function eventAudienceOf(scope) {
|
|
5
5
|
const tenancy = resolveTenancy({ _scope: scope }, "organizationId");
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
/*! @classytic/arc v2.
|
|
2
|
-
import { t as conjoinPolicyFilters } from "./filter-merge-
|
|
3
|
-
import { d as createDomainError } from "./errors-
|
|
4
|
-
import { b as isElevated, c as getOrgId, d as getScopeContext, m as getTeamId, v as hasOrgAccess } from "./types-
|
|
1
|
+
/*! @classytic/arc v2.45.0 | MIT | https://classytic.com */
|
|
2
|
+
import { t as conjoinPolicyFilters } from "./filter-merge-BYKBa9b2.mjs";
|
|
3
|
+
import { d as createDomainError } from "./errors-C9G4A8cN.mjs";
|
|
4
|
+
import { b as isElevated, c as getOrgId, d as getScopeContext, m as getTeamId, v as hasOrgAccess } from "./types-4JKkSvds.mjs";
|
|
5
5
|
//#region src/permissions/tenantPreparation.ts
|
|
6
6
|
/** Tenant preparation shared by HTTP middleware and direct transport invocation. */
|
|
7
7
|
const PREPARATION = Symbol.for("arc.tenantPreparation");
|
|
@@ -1,11 +1,10 @@
|
|
|
1
1
|
|
|
2
2
|
import { D as CleanupRunStore } from "../types-DVLddu2q.mjs";
|
|
3
3
|
//#region src/testing/cleanupStoreContract.d.ts
|
|
4
|
-
interface CleanupRunStoreContractSetupResult {
|
|
4
|
+
export interface CleanupRunStoreContractSetupResult {
|
|
5
5
|
store: CleanupRunStore;
|
|
6
6
|
teardown?: () => Promise<void>;
|
|
7
7
|
}
|
|
8
|
-
type CleanupRunStoreContractSetup = () => Promise<CleanupRunStoreContractSetupResult>;
|
|
9
|
-
declare function runCleanupRunStoreContract(name: string, setup: CleanupRunStoreContractSetup): void;
|
|
10
|
-
//#endregion
|
|
11
|
-
export { CleanupRunStoreContractSetup, CleanupRunStoreContractSetupResult, runCleanupRunStoreContract };
|
|
8
|
+
export type CleanupRunStoreContractSetup = () => Promise<CleanupRunStoreContractSetupResult>;
|
|
9
|
+
export declare function runCleanupRunStoreContract(name: string, setup: CleanupRunStoreContractSetup): void;
|
|
10
|
+
//#endregion
|