@burdenoff/be-sdk 2026.715.1 → 2026.716.2

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 (43) hide show
  1. package/dist/EventQueueFactory-BDOT45WD.js +6 -0
  2. package/dist/{EventQueueFactory-AG6LQF77.js.map → EventQueueFactory-BDOT45WD.js.map} +1 -1
  3. package/dist/cache/index.d.ts +1 -1
  4. package/dist/cache/index.js +1 -1
  5. package/dist/{chunk-NKLJMTAT.js → chunk-5ORHPLOA.js} +3 -3
  6. package/dist/{chunk-NKLJMTAT.js.map → chunk-5ORHPLOA.js.map} +1 -1
  7. package/dist/{chunk-GVZ5BDER.js → chunk-A4TGVW5V.js} +3 -3
  8. package/dist/{chunk-GVZ5BDER.js.map → chunk-A4TGVW5V.js.map} +1 -1
  9. package/dist/{chunk-OIBCAEQJ.js → chunk-A6WNRJZF.js} +5 -5
  10. package/dist/{chunk-OIBCAEQJ.js.map → chunk-A6WNRJZF.js.map} +1 -1
  11. package/dist/{chunk-CAI5GJJ6.js → chunk-CJCO3OWF.js} +138 -14
  12. package/dist/chunk-CJCO3OWF.js.map +1 -0
  13. package/dist/{chunk-LHLOJS52.js → chunk-DBIWNA72.js} +2 -2
  14. package/dist/{chunk-LHLOJS52.js.map → chunk-DBIWNA72.js.map} +1 -1
  15. package/dist/{chunk-Y7X5AYKY.js → chunk-IMMJMVP7.js} +3 -3
  16. package/dist/{chunk-Y7X5AYKY.js.map → chunk-IMMJMVP7.js.map} +1 -1
  17. package/dist/{chunk-3XJUXXES.js → chunk-M5JYRRI6.js} +4 -4
  18. package/dist/{chunk-3XJUXXES.js.map → chunk-M5JYRRI6.js.map} +1 -1
  19. package/dist/{chunk-HDB3UKUN.js → chunk-OQ62HA7Z.js} +3 -3
  20. package/dist/{chunk-HDB3UKUN.js.map → chunk-OQ62HA7Z.js.map} +1 -1
  21. package/dist/{chunk-MHNA7IS7.js → chunk-S7LWYERE.js} +4 -2
  22. package/dist/chunk-S7LWYERE.js.map +1 -0
  23. package/dist/{chunk-X4NELQLV.js → chunk-UM32ZA3G.js} +3 -3
  24. package/dist/{chunk-X4NELQLV.js.map → chunk-UM32ZA3G.js.map} +1 -1
  25. package/dist/{chunk-GCY2FTHD.js → chunk-X5FPXATC.js} +3 -3
  26. package/dist/{chunk-GCY2FTHD.js.map → chunk-X5FPXATC.js.map} +1 -1
  27. package/dist/{chunk-3YZWPBKP.js → chunk-YKY24YLZ.js} +3 -3
  28. package/dist/{chunk-3YZWPBKP.js.map → chunk-YKY24YLZ.js.map} +1 -1
  29. package/dist/event-queue/index.js +4 -4
  30. package/dist/export/index.js +3 -3
  31. package/dist/gateway/index.js +2 -2
  32. package/dist/gateway/security/index.js +1 -1
  33. package/dist/graph/index.js +5 -5
  34. package/dist/graphql/index.js +2 -2
  35. package/dist/{index-Mr2ATGnY.d.ts → index-Zh4KQBM1.d.ts} +5 -0
  36. package/dist/index.d.ts +1 -1
  37. package/dist/index.js +15 -15
  38. package/dist/init/index.js +3 -3
  39. package/dist/prisma/index.js +4 -4
  40. package/package.json +1 -1
  41. package/dist/EventQueueFactory-AG6LQF77.js +0 -6
  42. package/dist/chunk-CAI5GJJ6.js.map +0 -1
  43. package/dist/chunk-MHNA7IS7.js.map +0 -1
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/gateway/index.ts","../src/gateway/types.ts","../src/gateway/client.ts"],"names":["CircuitState","GatewayErrorType","GatewayError","Error","type","gatewayUrl","statusCode","graphqlErrors","cause","message","options","name","Object","setPrototypeOf","prototype","uuidv4","crypto","randomUUID","hasAuthorizationHeader","headers","key","keys","toLowerCase","resolveBypassPermissionValue","token","process","env","normalizedToken","trim","CircuitBreaker","state","CLOSED","failures","successes","consecutiveFailures","lastFailureTime","lastSuccessTime","openedAt","failureTimestamps","config","getState","checkStateTransition","recordSuccess","Date","now","HALF_OPEN","logger","info","recordFailure","push","windowStart","failureWindow","filter","t","length","failureThreshold","OPEN","warn","threshold","allowRequest","forceOpen","forceClose","getStats","elapsed","resetTimeout","GatewayClient","layerManager","internalCircuitBreaker","crossLayerCircuitBreaker","retryConfig","defaultHeaders","timeout","enableLogging","LayerManager","layer","serviceName","serviceIdentity","internalGatewayUrl","crossLayerGatewayUrl","cbConfig","DEFAULT_CIRCUIT_BREAKER_CONFIG","circuitBreaker","DEFAULT_GATEWAY_RETRY_CONFIG","retry","getServiceIdentity","debug","internalUrl","getInternalUrl","crossLayerUrl","getCrossLayerUrl","getInternalGatewayUrl","getCrossLayerGatewayUrl","internalQuery","context","createRequestContext","executeWithRetry","bypassPermission","crossLayerQuery","query","getInternalCircuitBreaker","getCrossLayerCircuitBreaker","getHealthStatus","internal","url","circuitState","stats","crossLayer","updateDefaultHeaders","callType","requestId","actorId","workspaceId","startTime","shouldRetryError","error","GRAPHQL_ERROR","CIRCUIT_OPEN","calculateRetryDelay","attempt","Math","min","initialDelay","pow","backoffMultiplier","maxDelay","logRetryAttempt","maxAttempts","delay","settings","skipCircuitBreaker","skipRetry","lastError","result","executeRequest","String","sleep","UNKNOWN_ERROR","buildRequestHeaders","cfHeaders","ContextManager","getCfAccessHeaders","assign","value","entries","undefined","toString","cfCookie","existing","split","some","c","handleGraphQLErrors","duration","errors","errorMessages","map","e","join","handleFetchError","TIMEOUT_ERROR","NETWORK_ERROR","serviceActorId","serviceJwt","signServiceJwt","body","JSON","stringify","variables","operationName","controller","AbortController","timeoutId","setTimeout","abort","response","fetch","method","signal","clearTimeout","ok","status","statusText","json","hasData","data","ms","Promise","resolve","createGatewayClient","createGatewayClientFromEnv"],"mappings":"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","file":"chunk-GVZ5BDER.js","sourcesContent":["/**\n * Gateway Module\n *\n * Provides unified gateway client for layer-aware M2M communication\n * with circuit breaker and retry logic.\n *\n * @module gateway\n * @category Gateway\n *\n * @example\n * ```typescript\n * import { GatewayClient, createGatewayClientFromEnv } from '@burdenoff/be-sdk/gateway';\n *\n * // Create from environment variables\n * const client = createGatewayClientFromEnv();\n *\n * // Or create manually\n * const client = new GatewayClient({\n * layer: 'wspace',\n * serviceName: 'wspace-tags-svc',\n * });\n *\n * // Internal call (same layer, uses int-gateway with bypass)\n * const internalResult = await client.internalQuery({\n * query: `query { getTag(id: \"123\") { id name } }`,\n * });\n *\n * // Cross-layer call (via public gateway)\n * const crossLayerResult = await client.crossLayerQuery({\n * query: `query { getCurrentUser { id email } }`,\n * });\n * ```\n */\n\n// Client exports\nexport { GatewayClient, createGatewayClient, createGatewayClientFromEnv } from './client.js';\n\n// Service-JWT minting for cross-layer M2M auth. Exposed so non-GatewayClient\n// callers (e.g. bespoke graphql-request clients) can authenticate identically.\nexport { signServiceJwt } from './service-jwt.js';\n\n// Type exports\nexport {\n CircuitState,\n GatewayErrorType,\n GatewayError,\n type GatewayClientConfig,\n type GraphQLRequestOptions,\n type GraphQLResponse,\n type GraphQLError,\n type IGatewayClient,\n type ICircuitBreaker,\n type CircuitBreakerStats,\n type GatewayClientHealth,\n type RequestContext,\n} from './types.js';\n\n// Gateway-side security plugin stack (for public gateways).\n// Imported by consumers as `@burdenoff/be-sdk/gateway/security` — this\n// re-export lets `@burdenoff/be-sdk/gateway` also resolve the namespace.\nexport * as Security from './security/index.js';\n","/**\n * Gateway Client Types\n *\n * Type definitions for the unified gateway client with\n * circuit breaker and retry logic.\n *\n * @module gateway/types\n * @category Gateway\n */\n\nimport type { ServiceLayer, CircuitBreakerConfig, GatewayRetryConfig, GatewayRequestHeaders } from '../types/layer.js';\n\n/**\n * Gateway client configuration\n */\nexport interface GatewayClientConfig {\n /**\n * Layer this client belongs to\n */\n layer: ServiceLayer;\n\n /**\n * Service name (for logging and headers)\n */\n serviceName: string;\n\n /**\n * Service identity for bypass headers\n * @default serviceName\n */\n serviceIdentity?: string;\n\n /**\n * Internal gateway URL (same layer M2M)\n * @default Resolved from layer defaults or environment\n */\n internalGatewayUrl?: string;\n\n /**\n * Cross-layer gateway URL (cross layer via public gateway)\n * @default Resolved from layer defaults or environment\n */\n crossLayerGatewayUrl?: string;\n\n /**\n * Request timeout in milliseconds\n * @default 30000 (30 seconds)\n */\n timeout?: number;\n\n /**\n * Circuit breaker configuration\n */\n circuitBreaker?: Partial<CircuitBreakerConfig>;\n\n /**\n * Retry configuration\n */\n retry?: Partial<GatewayRetryConfig>;\n\n /**\n * Enable request logging\n * @default true\n */\n enableLogging?: boolean;\n\n /**\n * Default headers to include in all requests\n */\n defaultHeaders?: GatewayRequestHeaders;\n}\n\n/**\n * Circuit breaker states\n */\nexport enum CircuitState {\n CLOSED = 'CLOSED',\n OPEN = 'OPEN',\n HALF_OPEN = 'HALF_OPEN',\n}\n\n/**\n * Circuit breaker instance interface\n */\nexport interface ICircuitBreaker {\n /**\n * Get current circuit state\n */\n getState(): CircuitState;\n\n /**\n * Record a successful call\n */\n recordSuccess(): void;\n\n /**\n * Record a failed call\n */\n recordFailure(): void;\n\n /**\n * Check if circuit allows calls\n */\n allowRequest(): boolean;\n\n /**\n * Force open the circuit\n */\n forceOpen(): void;\n\n /**\n * Force close the circuit\n */\n forceClose(): void;\n\n /**\n * Get circuit statistics\n */\n getStats(): CircuitBreakerStats;\n}\n\n/**\n * Circuit breaker statistics\n */\nexport interface CircuitBreakerStats {\n state: CircuitState;\n failures: number;\n successes: number;\n consecutiveFailures: number;\n lastFailureTime: number | null;\n lastSuccessTime: number | null;\n openedAt: number | null;\n}\n\n/**\n * GraphQL request options\n */\nexport interface GraphQLRequestOptions {\n /**\n * GraphQL query or mutation string\n */\n query: string;\n\n /**\n * GraphQL variables\n */\n variables?: Record<string, unknown>;\n\n /**\n * Operation name (for multi-operation documents)\n */\n operationName?: string;\n\n /**\n * Additional headers for this request\n */\n headers?: GatewayRequestHeaders;\n\n /**\n * Override timeout for this request\n */\n timeout?: number;\n\n /**\n * Skip circuit breaker for this request\n * @default false\n */\n skipCircuitBreaker?: boolean;\n\n /**\n * Skip retry logic for this request\n * @default false\n */\n skipRetry?: boolean;\n}\n\n/**\n * GraphQL response\n */\nexport interface GraphQLResponse<T = unknown> {\n /**\n * Response data\n */\n data?: T;\n\n /**\n * GraphQL errors\n */\n errors?: GraphQLError[];\n}\n\n/**\n * GraphQL error structure\n */\nexport interface GraphQLError {\n message: string;\n locations?: Array<{ line: number; column: number }>;\n path?: Array<string | number>;\n extensions?: Record<string, unknown>;\n}\n\n/**\n * Gateway client interface\n */\nexport interface IGatewayClient {\n /**\n * Execute internal (same layer) GraphQL query/mutation\n *\n * Uses internal gateway with bypass headers for M2M communication.\n *\n * @param options - Request options\n * @returns GraphQL response\n */\n internalQuery<T = unknown>(options: GraphQLRequestOptions): Promise<GraphQLResponse<T>>;\n\n /**\n * Execute cross-layer GraphQL query/mutation\n *\n * Uses public gateway for cross-layer communication.\n *\n * @param options - Request options\n * @returns GraphQL response\n */\n crossLayerQuery<T = unknown>(options: GraphQLRequestOptions): Promise<GraphQLResponse<T>>;\n\n /**\n * Execute GraphQL query/mutation with explicit gateway URL\n *\n * @param gatewayUrl - Gateway URL to use\n * @param options - Request options\n * @returns GraphQL response\n */\n query<T = unknown>(gatewayUrl: string, options: GraphQLRequestOptions): Promise<GraphQLResponse<T>>;\n\n /**\n * Get internal gateway circuit breaker\n */\n getInternalCircuitBreaker(): ICircuitBreaker;\n\n /**\n * Get cross-layer gateway circuit breaker\n */\n getCrossLayerCircuitBreaker(): ICircuitBreaker;\n\n /**\n * Get client health status\n */\n getHealthStatus(): GatewayClientHealth;\n\n /**\n * Update default headers\n */\n updateDefaultHeaders(headers: Partial<GatewayRequestHeaders>): void;\n}\n\n/**\n * Gateway client health status\n */\nexport interface GatewayClientHealth {\n /**\n * Internal gateway status\n */\n internal: {\n url: string;\n circuitState: CircuitState;\n stats: CircuitBreakerStats;\n };\n\n /**\n * Cross-layer gateway status\n */\n crossLayer: {\n url: string;\n circuitState: CircuitState;\n stats: CircuitBreakerStats;\n };\n}\n\n/**\n * Gateway error types\n */\nexport enum GatewayErrorType {\n NETWORK_ERROR = 'NETWORK_ERROR',\n TIMEOUT_ERROR = 'TIMEOUT_ERROR',\n CIRCUIT_OPEN = 'CIRCUIT_OPEN',\n GRAPHQL_ERROR = 'GRAPHQL_ERROR',\n UNKNOWN_ERROR = 'UNKNOWN_ERROR',\n}\n\n/**\n * Gateway error class\n */\nexport class GatewayError extends Error {\n type: GatewayErrorType;\n gatewayUrl: string;\n statusCode?: number;\n graphqlErrors?: GraphQLError[];\n override cause?: Error;\n\n constructor(\n message: string,\n type: GatewayErrorType,\n gatewayUrl: string,\n options?: {\n statusCode?: number;\n graphqlErrors?: GraphQLError[];\n cause?: Error;\n }\n ) {\n super(message);\n this.name = 'GatewayError';\n this.type = type;\n this.gatewayUrl = gatewayUrl;\n this.statusCode = options?.statusCode;\n this.graphqlErrors = options?.graphqlErrors;\n this.cause = options?.cause;\n Object.setPrototypeOf(this, GatewayError.prototype);\n }\n}\n\n/**\n * Request context for logging and tracing\n */\nexport interface RequestContext {\n /**\n * Request ID for tracing\n */\n requestId: string;\n\n /**\n * Actor ID making the request\n */\n actorId?: string;\n\n /**\n * Workspace ID context\n */\n workspaceId?: string;\n\n /**\n * Timestamp when request started\n */\n startTime: number;\n\n /**\n * Call type\n */\n callType: 'internal' | 'cross-layer' | 'direct';\n}\n","/**\n * Unified Gateway Client\n *\n * Provides a layer-aware GraphQL client with circuit breaker,\n * retry logic, and automatic header management for M2M communication.\n *\n * @module gateway/client\n * @category Gateway\n *\n * @example\n * ```typescript\n * import { GatewayClient } from '@burdenoff/be-sdk/gateway';\n *\n * const client = new GatewayClient({\n * layer: 'wspace',\n * serviceName: 'wspace-tags-svc',\n * });\n *\n * // Internal call (same layer)\n * const result = await client.internalQuery({\n * query: `query { getTag(id: \"123\") { id name } }`,\n * });\n *\n * // Cross-layer call\n * const authResult = await client.crossLayerQuery({\n * query: `query { getCurrentUser { id email } }`,\n * });\n * ```\n */\n\nimport { ContextManager } from '../context/index.js';\nimport { LayerManager } from '../layer/index.js';\nimport { logger } from '../logger/index.js';\nimport { signServiceJwt } from './service-jwt.js';\nimport {\n DEFAULT_CIRCUIT_BREAKER_CONFIG,\n DEFAULT_GATEWAY_RETRY_CONFIG,\n type CircuitBreakerConfig,\n type GatewayRequestHeaders,\n type GatewayRetryConfig,\n type ServiceLayer,\n} from '../types/layer.js';\nimport {\n CircuitState,\n GatewayError,\n GatewayErrorType,\n type CircuitBreakerStats,\n type GatewayClientConfig,\n type GatewayClientHealth,\n type GraphQLError,\n type GraphQLRequestOptions,\n type GraphQLResponse,\n type ICircuitBreaker,\n type IGatewayClient,\n type RequestContext,\n} from './types.js';\n\nconst uuidv4 = (): string => crypto.randomUUID();\n\n/**\n * Case-insensitive presence check for the `Authorization` header. HTTP header\n * names are case-insensitive (RFC 7230), and while the outbound `fetch` will\n * preserve whatever casing the caller supplies, callers may legitimately set\n * `authorization` / `Authorization` / even `AUTHORIZATION` via defaultHeaders\n * or options.headers. We must not overwrite an already-supplied token.\n */\nfunction hasAuthorizationHeader(headers: Record<string, string>): boolean {\n for (const key of Object.keys(headers)) {\n if (key.toLowerCase() === 'authorization') return true;\n }\n return false;\n}\n\nexport function resolveBypassPermissionValue(\n token: string | undefined = process.env['INTERNAL_SERVICE_TOKEN']\n): string {\n const normalizedToken = token?.trim();\n\n if (!normalizedToken) {\n throw new Error('INTERNAL_SERVICE_TOKEN must be configured for bypass-enabled gateway calls');\n }\n\n return normalizedToken;\n}\n\n/**\n * Circuit Breaker Implementation\n */\nclass CircuitBreaker implements ICircuitBreaker {\n private state: CircuitState = CircuitState.CLOSED;\n private failures = 0;\n private successes = 0;\n private consecutiveFailures = 0;\n private lastFailureTime: number | null = null;\n private lastSuccessTime: number | null = null;\n private openedAt: number | null = null;\n private failureTimestamps: number[] = [];\n private config: CircuitBreakerConfig;\n\n constructor(config: CircuitBreakerConfig) {\n this.config = config;\n }\n\n getState(): CircuitState {\n this.checkStateTransition();\n return this.state;\n }\n\n recordSuccess(): void {\n this.successes++;\n this.consecutiveFailures = 0;\n this.lastSuccessTime = Date.now();\n\n if (this.state === CircuitState.HALF_OPEN) {\n this.state = CircuitState.CLOSED;\n this.failures = 0;\n this.failureTimestamps = [];\n this.openedAt = null;\n logger.info('[CircuitBreaker] Circuit closed after successful test');\n }\n }\n\n recordFailure(): void {\n this.failures++;\n this.consecutiveFailures++;\n this.lastFailureTime = Date.now();\n this.failureTimestamps.push(Date.now());\n\n // Clean up old timestamps\n const windowStart = Date.now() - this.config.failureWindow;\n this.failureTimestamps = this.failureTimestamps.filter((t) => t > windowStart);\n\n // Check if we should open the circuit\n if (this.state === CircuitState.CLOSED && this.failureTimestamps.length >= this.config.failureThreshold) {\n this.state = CircuitState.OPEN;\n this.openedAt = Date.now();\n logger.warn('[CircuitBreaker] Circuit opened due to failures', {\n failures: this.failureTimestamps.length,\n threshold: this.config.failureThreshold,\n });\n }\n\n // If we're half-open and fail, go back to open\n if (this.state === CircuitState.HALF_OPEN) {\n this.state = CircuitState.OPEN;\n this.openedAt = Date.now();\n logger.warn('[CircuitBreaker] Circuit re-opened after failed test');\n }\n }\n\n allowRequest(): boolean {\n this.checkStateTransition();\n\n switch (this.state) {\n case CircuitState.CLOSED:\n return true;\n case CircuitState.OPEN:\n return false;\n case CircuitState.HALF_OPEN:\n // Allow one test request\n return true;\n default:\n return true;\n }\n }\n\n forceOpen(): void {\n this.state = CircuitState.OPEN;\n this.openedAt = Date.now();\n logger.info('[CircuitBreaker] Circuit force-opened');\n }\n\n forceClose(): void {\n this.state = CircuitState.CLOSED;\n this.failures = 0;\n this.consecutiveFailures = 0;\n this.failureTimestamps = [];\n this.openedAt = null;\n logger.info('[CircuitBreaker] Circuit force-closed');\n }\n\n getStats(): CircuitBreakerStats {\n return {\n state: this.state,\n failures: this.failures,\n successes: this.successes,\n consecutiveFailures: this.consecutiveFailures,\n lastFailureTime: this.lastFailureTime,\n lastSuccessTime: this.lastSuccessTime,\n openedAt: this.openedAt,\n };\n }\n\n private checkStateTransition(): void {\n if (this.state === CircuitState.OPEN && this.openedAt) {\n const elapsed = Date.now() - this.openedAt;\n if (elapsed >= this.config.resetTimeout) {\n this.state = CircuitState.HALF_OPEN;\n logger.info('[CircuitBreaker] Circuit transitioning to half-open');\n }\n }\n }\n}\n\n/**\n * Unified Gateway Client\n */\nexport class GatewayClient implements IGatewayClient {\n private config: GatewayClientConfig;\n private layerManager: LayerManager;\n private internalCircuitBreaker: CircuitBreaker;\n private crossLayerCircuitBreaker: CircuitBreaker;\n private retryConfig: GatewayRetryConfig;\n private defaultHeaders: GatewayRequestHeaders;\n\n constructor(config: GatewayClientConfig) {\n this.config = {\n timeout: 30000,\n enableLogging: true,\n ...config,\n };\n\n // Initialize layer manager\n this.layerManager = new LayerManager({\n layer: config.layer,\n serviceName: config.serviceName,\n serviceIdentity: config.serviceIdentity,\n });\n\n // Override URLs if provided\n if (config.internalGatewayUrl) {\n // Use getter internally, but we'll store the override\n }\n if (config.crossLayerGatewayUrl) {\n // Use getter internally, but we'll store the override\n }\n\n // Initialize circuit breakers\n const cbConfig: CircuitBreakerConfig = {\n ...DEFAULT_CIRCUIT_BREAKER_CONFIG,\n ...config.circuitBreaker,\n };\n this.internalCircuitBreaker = new CircuitBreaker(cbConfig);\n this.crossLayerCircuitBreaker = new CircuitBreaker(cbConfig);\n\n // Initialize retry config\n this.retryConfig = {\n ...DEFAULT_GATEWAY_RETRY_CONFIG,\n ...config.retry,\n };\n\n // Initialize default headers\n this.defaultHeaders = {\n 'x-service-identity': this.layerManager.getServiceIdentity(),\n 'x-actor-type': 'service',\n ...config.defaultHeaders,\n };\n\n logger.debug('[GatewayClient] Initialized', {\n layer: config.layer,\n serviceName: config.serviceName,\n internalUrl: this.getInternalUrl(),\n crossLayerUrl: this.getCrossLayerUrl(),\n });\n }\n\n private getInternalUrl(): string {\n return this.config.internalGatewayUrl || this.layerManager.getInternalGatewayUrl();\n }\n\n private getCrossLayerUrl(): string {\n return this.config.crossLayerGatewayUrl || this.layerManager.getCrossLayerGatewayUrl();\n }\n\n /**\n * Execute internal (same layer) GraphQL query/mutation\n */\n async internalQuery<T = unknown>(options: GraphQLRequestOptions): Promise<GraphQLResponse<T>> {\n const context = this.createRequestContext('internal', options);\n\n return this.executeWithRetry(this.getInternalUrl(), options, this.internalCircuitBreaker, context, {\n bypassPermission: true,\n });\n }\n\n /**\n * Execute cross-layer GraphQL query/mutation\n */\n async crossLayerQuery<T = unknown>(options: GraphQLRequestOptions): Promise<GraphQLResponse<T>> {\n const context = this.createRequestContext('cross-layer', options);\n\n return this.executeWithRetry(\n this.getCrossLayerUrl(),\n options,\n this.crossLayerCircuitBreaker,\n context,\n { bypassPermission: false } // Cross-layer calls go through public gateway\n );\n }\n\n /**\n * Execute GraphQL query/mutation with explicit gateway URL\n */\n async query<T = unknown>(gatewayUrl: string, options: GraphQLRequestOptions): Promise<GraphQLResponse<T>> {\n const context = this.createRequestContext('direct', options);\n\n // Use internal circuit breaker for direct calls\n return this.executeWithRetry(gatewayUrl, options, this.internalCircuitBreaker, context, {\n bypassPermission: false,\n });\n }\n\n getInternalCircuitBreaker(): ICircuitBreaker {\n return this.internalCircuitBreaker;\n }\n\n getCrossLayerCircuitBreaker(): ICircuitBreaker {\n return this.crossLayerCircuitBreaker;\n }\n\n getHealthStatus(): GatewayClientHealth {\n return {\n internal: {\n url: this.getInternalUrl(),\n circuitState: this.internalCircuitBreaker.getState(),\n stats: this.internalCircuitBreaker.getStats(),\n },\n crossLayer: {\n url: this.getCrossLayerUrl(),\n circuitState: this.crossLayerCircuitBreaker.getState(),\n stats: this.crossLayerCircuitBreaker.getStats(),\n },\n };\n }\n\n updateDefaultHeaders(headers: Partial<GatewayRequestHeaders>): void {\n this.defaultHeaders = { ...this.defaultHeaders, ...headers };\n }\n\n private createRequestContext(\n callType: 'internal' | 'cross-layer' | 'direct',\n options: GraphQLRequestOptions\n ): RequestContext {\n return {\n requestId: uuidv4(),\n actorId: options.headers?.['x-actor-id'] || this.defaultHeaders['x-actor-id'],\n workspaceId: options.headers?.['x-workspace-id'] || this.defaultHeaders['x-workspace-id'],\n startTime: Date.now(),\n callType,\n };\n }\n\n /**\n * Check if an error should be retried\n */\n private shouldRetryError(error: unknown): boolean {\n if (!(error instanceof GatewayError)) {\n return true;\n }\n // Don't retry GraphQL errors or circuit open errors\n return error.type !== GatewayErrorType.GRAPHQL_ERROR && error.type !== GatewayErrorType.CIRCUIT_OPEN;\n }\n\n /**\n * Calculate retry delay with exponential backoff\n */\n private calculateRetryDelay(attempt: number): number {\n return Math.min(\n this.retryConfig.initialDelay * Math.pow(this.retryConfig.backoffMultiplier, attempt - 1),\n this.retryConfig.maxDelay\n );\n }\n\n /**\n * Log retry attempt if logging is enabled\n */\n private logRetryAttempt(\n context: RequestContext,\n attempt: number,\n maxAttempts: number,\n delay: number,\n error: Error\n ): void {\n if (this.config.enableLogging) {\n logger.warn('[GatewayClient] Request failed, retrying', {\n requestId: context.requestId,\n attempt,\n maxAttempts,\n delay,\n error: error.message,\n });\n }\n }\n\n private async executeWithRetry<T>(\n gatewayUrl: string,\n options: GraphQLRequestOptions,\n circuitBreaker: CircuitBreaker,\n context: RequestContext,\n settings: { bypassPermission: boolean }\n ): Promise<GraphQLResponse<T>> {\n // Check circuit breaker\n if (!options.skipCircuitBreaker && !circuitBreaker.allowRequest()) {\n throw new GatewayError(`Circuit breaker is open for ${gatewayUrl}`, GatewayErrorType.CIRCUIT_OPEN, gatewayUrl);\n }\n\n const maxAttempts = options.skipRetry ? 1 : this.retryConfig.maxAttempts;\n let lastError: Error | null = null;\n\n for (let attempt = 1; attempt <= maxAttempts; attempt++) {\n try {\n const result = await this.executeRequest<T>(gatewayUrl, options, context, settings.bypassPermission);\n if (!options.skipCircuitBreaker) {\n circuitBreaker.recordSuccess();\n }\n return result;\n } catch (error) {\n lastError = error instanceof Error ? error : new Error(String(error));\n if (!options.skipCircuitBreaker) {\n circuitBreaker.recordFailure();\n }\n\n if (!this.shouldRetryError(error)) {\n throw error;\n }\n\n if (attempt < maxAttempts) {\n const delay = this.calculateRetryDelay(attempt);\n this.logRetryAttempt(context, attempt, maxAttempts, delay, lastError);\n await this.sleep(delay);\n }\n }\n }\n\n throw lastError || new GatewayError('Request failed after retries', GatewayErrorType.UNKNOWN_ERROR, gatewayUrl);\n }\n\n /**\n * Build headers for a request\n */\n private buildRequestHeaders(\n context: RequestContext,\n options: GraphQLRequestOptions,\n bypassPermission: boolean\n ): Record<string, string> {\n const headers: Record<string, string> = {\n 'Content-Type': 'application/json',\n 'x-request-id': context.requestId,\n 'x-call-type': context.callType,\n };\n\n // Cross-layer calls transit the peer layer's PUBLIC gateway, which on alpha\n // sits behind Cloudflare Access. Re-present the inbound request's CF creds\n // (service token and/or the CF_Authorization cookie) so the call passes the\n // CF edge. Added before default/request headers so a caller may still\n // override the non-cookie CF headers explicitly; the CF cookie is reconciled\n // after the merges below so it is never silently clobbered. No-op when the\n // inbound request carried no CF creds (local dev, production) — returns {}.\n const cfHeaders = context.callType === 'cross-layer' ? ContextManager.getCfAccessHeaders() : {};\n Object.assign(headers, cfHeaders);\n\n // Add default headers\n for (const [key, value] of Object.entries(this.defaultHeaders)) {\n if (value !== undefined) {\n headers[key] = String(value);\n }\n }\n\n // Add request-specific headers\n if (options.headers) {\n for (const [key, value] of Object.entries(options.headers)) {\n if (value !== undefined) {\n headers[key] = String(value);\n }\n }\n }\n\n // Add bypass headers for internal calls\n if (bypassPermission) {\n headers['x-bypass-permission'] = resolveBypassPermissionValue();\n headers['x-bypass-source'] = this.layerManager.getServiceIdentity();\n headers['x-bypass-timestamp'] = Date.now().toString();\n }\n\n // Reconcile the CF_Authorization cookie: the default/request-header merges\n // above may set their own `cookie`, which would otherwise clobber the CF\n // cookie applied earlier (or vice versa). Merge so both survive, without\n // duplicating if it's already present.\n const cfCookie = cfHeaders['cookie'];\n if (cfCookie) {\n const existing = headers['cookie'];\n if (!existing) {\n headers['cookie'] = cfCookie;\n } else if (!existing.split(';').some((c) => c.trim() === cfCookie)) {\n headers['cookie'] = `${existing}; ${cfCookie}`;\n }\n }\n\n return headers;\n }\n\n /**\n * Handle GraphQL errors in response\n */\n private handleGraphQLErrors<T>(\n result: GraphQLResponse<T>,\n context: RequestContext,\n gatewayUrl: string,\n duration: number\n ): void {\n if (!result.errors || result.errors.length === 0) {\n return;\n }\n\n const errorMessages = result.errors.map((e: GraphQLError) => e.message).join(', ');\n\n if (this.config.enableLogging) {\n logger.warn('[GatewayClient] GraphQL errors', {\n requestId: context.requestId,\n errors: result.errors,\n duration,\n });\n }\n\n throw new GatewayError(`GraphQL error: ${errorMessages}`, GatewayErrorType.GRAPHQL_ERROR, gatewayUrl, {\n graphqlErrors: result.errors,\n });\n }\n\n /**\n * Handle fetch errors\n */\n private handleFetchError(\n error: unknown,\n context: RequestContext,\n gatewayUrl: string,\n timeout: number,\n duration: number\n ): never {\n if (error instanceof GatewayError) {\n throw error;\n }\n\n if (error instanceof Error) {\n if (error.name === 'AbortError') {\n throw new GatewayError(`Request timed out after ${timeout}ms`, GatewayErrorType.TIMEOUT_ERROR, gatewayUrl, {\n cause: error,\n });\n }\n\n if (this.config.enableLogging) {\n logger.error('[GatewayClient] Request failed', {\n requestId: context.requestId,\n error: error.message,\n duration,\n });\n }\n\n throw new GatewayError(error.message, GatewayErrorType.NETWORK_ERROR, gatewayUrl, {\n cause: error,\n });\n }\n\n throw new GatewayError(String(error), GatewayErrorType.UNKNOWN_ERROR, gatewayUrl);\n }\n\n private async executeRequest<T>(\n gatewayUrl: string,\n options: GraphQLRequestOptions,\n context: RequestContext,\n bypassPermission: boolean\n ): Promise<GraphQLResponse<T>> {\n const timeout = options.timeout || this.config.timeout || 30000;\n const headers = this.buildRequestHeaders(context, options, bypassPermission);\n\n // Cross-layer calls transit the peer layer's PUBLIC gateway, which\n // requires JWT auth to propagate actor context. Mint a short-lived\n // service-actor JWT so the gateway admits the call and preserves\n // `x-actor-type: service` downstream. Skipped when the caller has\n // already supplied an Authorization header (e.g., user-originated\n // cross-layer flows) or when SERVICE_JWT_SECRET is unset.\n if (context.callType === 'cross-layer' && !hasAuthorizationHeader(headers)) {\n const serviceActorId = this.layerManager.getServiceIdentity();\n const serviceJwt = await signServiceJwt(serviceActorId);\n if (serviceJwt) {\n headers['Authorization'] = `Bearer ${serviceJwt}`;\n } else if (this.config.enableLogging) {\n // Subtle failure mode: without the JWT the public gateway strips\n // actor headers and the subgraph rejects with `authenticationRequired`.\n // Surface the root cause so operators rolling out a new caller don't\n // spend time debugging the downstream error.\n logger.debug(\n '[GatewayClient] SERVICE_JWT_SECRET not configured — cross-layer call will proceed without service JWT',\n { requestId: context.requestId, gatewayUrl }\n );\n }\n }\n\n const body = JSON.stringify({\n query: options.query,\n variables: options.variables || {},\n operationName: options.operationName,\n });\n\n if (this.config.enableLogging) {\n logger.debug('[GatewayClient] Executing request', {\n requestId: context.requestId,\n gatewayUrl,\n operationName: options.operationName,\n callType: context.callType,\n bypassPermission,\n });\n }\n\n try {\n const controller = new AbortController();\n const timeoutId = setTimeout(() => controller.abort(), timeout);\n\n const response = await fetch(gatewayUrl, {\n method: 'POST',\n headers,\n body,\n signal: controller.signal,\n });\n\n clearTimeout(timeoutId);\n const duration = Date.now() - context.startTime;\n\n if (!response.ok) {\n throw new GatewayError(\n `HTTP ${response.status}: ${response.statusText}`,\n GatewayErrorType.NETWORK_ERROR,\n gatewayUrl,\n { statusCode: response.status }\n );\n }\n\n const result = (await response.json()) as GraphQLResponse<T>;\n this.handleGraphQLErrors(result, context, gatewayUrl, duration);\n\n if (this.config.enableLogging) {\n logger.debug('[GatewayClient] Request completed', {\n requestId: context.requestId,\n duration,\n hasData: !!result.data,\n });\n }\n\n return result;\n } catch (error) {\n const duration = Date.now() - context.startTime;\n this.handleFetchError(error, context, gatewayUrl, timeout, duration);\n }\n }\n\n private sleep(ms: number): Promise<void> {\n return new Promise((resolve) => setTimeout(resolve, ms));\n }\n}\n\n/**\n * Create a gateway client for a specific layer\n */\nexport function createGatewayClient(config: GatewayClientConfig): GatewayClient {\n return new GatewayClient(config);\n}\n\n/**\n * Create a gateway client from environment variables\n *\n * Required environment variables:\n * - SERVICE_LAYER: 'wspace' | 'global'\n * - SERVICE_NAME: Service name\n *\n * Optional:\n * - SERVICE_IDENTITY: Service identity (defaults to SERVICE_NAME)\n * - {LAYER}_INT_GATEWAY_URL: Internal gateway URL\n * - {OPPOSITE_LAYER}_PUBLIC_GATEWAY_URL: Cross-layer gateway URL\n */\nexport function createGatewayClientFromEnv(): GatewayClient {\n const layer = process.env['SERVICE_LAYER'] as ServiceLayer;\n\n if (!layer || (layer !== 'wspace' && layer !== 'global')) {\n throw new Error(`[GatewayClient] Invalid or missing SERVICE_LAYER. Expected 'wspace' or 'global', got '${layer}'`);\n }\n\n const serviceName = process.env['SERVICE_NAME'];\n if (!serviceName) {\n throw new Error('[GatewayClient] SERVICE_NAME environment variable is required');\n }\n\n const serviceIdentity = process.env['SERVICE_IDENTITY'] || serviceName;\n\n return new GatewayClient({\n layer,\n serviceName,\n serviceIdentity,\n });\n}\n"]}
1
+ {"version":3,"sources":["../src/gateway/index.ts","../src/gateway/types.ts","../src/gateway/client.ts"],"names":["CircuitState","GatewayErrorType","GatewayError","Error","type","gatewayUrl","statusCode","graphqlErrors","cause","message","options","name","Object","setPrototypeOf","prototype","uuidv4","crypto","randomUUID","hasAuthorizationHeader","headers","key","keys","toLowerCase","resolveBypassPermissionValue","token","process","env","normalizedToken","trim","CircuitBreaker","state","CLOSED","failures","successes","consecutiveFailures","lastFailureTime","lastSuccessTime","openedAt","failureTimestamps","config","getState","checkStateTransition","recordSuccess","Date","now","HALF_OPEN","logger","info","recordFailure","push","windowStart","failureWindow","filter","t","length","failureThreshold","OPEN","warn","threshold","allowRequest","forceOpen","forceClose","getStats","elapsed","resetTimeout","GatewayClient","layerManager","internalCircuitBreaker","crossLayerCircuitBreaker","retryConfig","defaultHeaders","timeout","enableLogging","LayerManager","layer","serviceName","serviceIdentity","internalGatewayUrl","crossLayerGatewayUrl","cbConfig","DEFAULT_CIRCUIT_BREAKER_CONFIG","circuitBreaker","DEFAULT_GATEWAY_RETRY_CONFIG","retry","getServiceIdentity","debug","internalUrl","getInternalUrl","crossLayerUrl","getCrossLayerUrl","getInternalGatewayUrl","getCrossLayerGatewayUrl","internalQuery","context","createRequestContext","executeWithRetry","bypassPermission","crossLayerQuery","query","getInternalCircuitBreaker","getCrossLayerCircuitBreaker","getHealthStatus","internal","url","circuitState","stats","crossLayer","updateDefaultHeaders","callType","requestId","actorId","workspaceId","startTime","shouldRetryError","error","GRAPHQL_ERROR","CIRCUIT_OPEN","calculateRetryDelay","attempt","Math","min","initialDelay","pow","backoffMultiplier","maxDelay","logRetryAttempt","maxAttempts","delay","settings","skipCircuitBreaker","skipRetry","lastError","result","executeRequest","String","sleep","UNKNOWN_ERROR","buildRequestHeaders","cfHeaders","ContextManager","getCfAccessHeaders","assign","value","entries","undefined","toString","cfCookie","existing","split","some","c","handleGraphQLErrors","duration","errors","errorMessages","map","e","join","handleFetchError","TIMEOUT_ERROR","NETWORK_ERROR","serviceActorId","serviceJwt","signServiceJwt","body","JSON","stringify","variables","operationName","controller","AbortController","timeoutId","setTimeout","abort","response","fetch","method","signal","clearTimeout","ok","status","statusText","json","hasData","data","ms","Promise","resolve","createGatewayClient","createGatewayClientFromEnv"],"mappings":"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","file":"chunk-A4TGVW5V.js","sourcesContent":["/**\n * Gateway Module\n *\n * Provides unified gateway client for layer-aware M2M communication\n * with circuit breaker and retry logic.\n *\n * @module gateway\n * @category Gateway\n *\n * @example\n * ```typescript\n * import { GatewayClient, createGatewayClientFromEnv } from '@burdenoff/be-sdk/gateway';\n *\n * // Create from environment variables\n * const client = createGatewayClientFromEnv();\n *\n * // Or create manually\n * const client = new GatewayClient({\n * layer: 'wspace',\n * serviceName: 'wspace-tags-svc',\n * });\n *\n * // Internal call (same layer, uses int-gateway with bypass)\n * const internalResult = await client.internalQuery({\n * query: `query { getTag(id: \"123\") { id name } }`,\n * });\n *\n * // Cross-layer call (via public gateway)\n * const crossLayerResult = await client.crossLayerQuery({\n * query: `query { getCurrentUser { id email } }`,\n * });\n * ```\n */\n\n// Client exports\nexport { GatewayClient, createGatewayClient, createGatewayClientFromEnv } from './client.js';\n\n// Service-JWT minting for cross-layer M2M auth. Exposed so non-GatewayClient\n// callers (e.g. bespoke graphql-request clients) can authenticate identically.\nexport { signServiceJwt } from './service-jwt.js';\n\n// Type exports\nexport {\n CircuitState,\n GatewayErrorType,\n GatewayError,\n type GatewayClientConfig,\n type GraphQLRequestOptions,\n type GraphQLResponse,\n type GraphQLError,\n type IGatewayClient,\n type ICircuitBreaker,\n type CircuitBreakerStats,\n type GatewayClientHealth,\n type RequestContext,\n} from './types.js';\n\n// Gateway-side security plugin stack (for public gateways).\n// Imported by consumers as `@burdenoff/be-sdk/gateway/security` — this\n// re-export lets `@burdenoff/be-sdk/gateway` also resolve the namespace.\nexport * as Security from './security/index.js';\n","/**\n * Gateway Client Types\n *\n * Type definitions for the unified gateway client with\n * circuit breaker and retry logic.\n *\n * @module gateway/types\n * @category Gateway\n */\n\nimport type { ServiceLayer, CircuitBreakerConfig, GatewayRetryConfig, GatewayRequestHeaders } from '../types/layer.js';\n\n/**\n * Gateway client configuration\n */\nexport interface GatewayClientConfig {\n /**\n * Layer this client belongs to\n */\n layer: ServiceLayer;\n\n /**\n * Service name (for logging and headers)\n */\n serviceName: string;\n\n /**\n * Service identity for bypass headers\n * @default serviceName\n */\n serviceIdentity?: string;\n\n /**\n * Internal gateway URL (same layer M2M)\n * @default Resolved from layer defaults or environment\n */\n internalGatewayUrl?: string;\n\n /**\n * Cross-layer gateway URL (cross layer via public gateway)\n * @default Resolved from layer defaults or environment\n */\n crossLayerGatewayUrl?: string;\n\n /**\n * Request timeout in milliseconds\n * @default 30000 (30 seconds)\n */\n timeout?: number;\n\n /**\n * Circuit breaker configuration\n */\n circuitBreaker?: Partial<CircuitBreakerConfig>;\n\n /**\n * Retry configuration\n */\n retry?: Partial<GatewayRetryConfig>;\n\n /**\n * Enable request logging\n * @default true\n */\n enableLogging?: boolean;\n\n /**\n * Default headers to include in all requests\n */\n defaultHeaders?: GatewayRequestHeaders;\n}\n\n/**\n * Circuit breaker states\n */\nexport enum CircuitState {\n CLOSED = 'CLOSED',\n OPEN = 'OPEN',\n HALF_OPEN = 'HALF_OPEN',\n}\n\n/**\n * Circuit breaker instance interface\n */\nexport interface ICircuitBreaker {\n /**\n * Get current circuit state\n */\n getState(): CircuitState;\n\n /**\n * Record a successful call\n */\n recordSuccess(): void;\n\n /**\n * Record a failed call\n */\n recordFailure(): void;\n\n /**\n * Check if circuit allows calls\n */\n allowRequest(): boolean;\n\n /**\n * Force open the circuit\n */\n forceOpen(): void;\n\n /**\n * Force close the circuit\n */\n forceClose(): void;\n\n /**\n * Get circuit statistics\n */\n getStats(): CircuitBreakerStats;\n}\n\n/**\n * Circuit breaker statistics\n */\nexport interface CircuitBreakerStats {\n state: CircuitState;\n failures: number;\n successes: number;\n consecutiveFailures: number;\n lastFailureTime: number | null;\n lastSuccessTime: number | null;\n openedAt: number | null;\n}\n\n/**\n * GraphQL request options\n */\nexport interface GraphQLRequestOptions {\n /**\n * GraphQL query or mutation string\n */\n query: string;\n\n /**\n * GraphQL variables\n */\n variables?: Record<string, unknown>;\n\n /**\n * Operation name (for multi-operation documents)\n */\n operationName?: string;\n\n /**\n * Additional headers for this request\n */\n headers?: GatewayRequestHeaders;\n\n /**\n * Override timeout for this request\n */\n timeout?: number;\n\n /**\n * Skip circuit breaker for this request\n * @default false\n */\n skipCircuitBreaker?: boolean;\n\n /**\n * Skip retry logic for this request\n * @default false\n */\n skipRetry?: boolean;\n}\n\n/**\n * GraphQL response\n */\nexport interface GraphQLResponse<T = unknown> {\n /**\n * Response data\n */\n data?: T;\n\n /**\n * GraphQL errors\n */\n errors?: GraphQLError[];\n}\n\n/**\n * GraphQL error structure\n */\nexport interface GraphQLError {\n message: string;\n locations?: Array<{ line: number; column: number }>;\n path?: Array<string | number>;\n extensions?: Record<string, unknown>;\n}\n\n/**\n * Gateway client interface\n */\nexport interface IGatewayClient {\n /**\n * Execute internal (same layer) GraphQL query/mutation\n *\n * Uses internal gateway with bypass headers for M2M communication.\n *\n * @param options - Request options\n * @returns GraphQL response\n */\n internalQuery<T = unknown>(options: GraphQLRequestOptions): Promise<GraphQLResponse<T>>;\n\n /**\n * Execute cross-layer GraphQL query/mutation\n *\n * Uses public gateway for cross-layer communication.\n *\n * @param options - Request options\n * @returns GraphQL response\n */\n crossLayerQuery<T = unknown>(options: GraphQLRequestOptions): Promise<GraphQLResponse<T>>;\n\n /**\n * Execute GraphQL query/mutation with explicit gateway URL\n *\n * @param gatewayUrl - Gateway URL to use\n * @param options - Request options\n * @returns GraphQL response\n */\n query<T = unknown>(gatewayUrl: string, options: GraphQLRequestOptions): Promise<GraphQLResponse<T>>;\n\n /**\n * Get internal gateway circuit breaker\n */\n getInternalCircuitBreaker(): ICircuitBreaker;\n\n /**\n * Get cross-layer gateway circuit breaker\n */\n getCrossLayerCircuitBreaker(): ICircuitBreaker;\n\n /**\n * Get client health status\n */\n getHealthStatus(): GatewayClientHealth;\n\n /**\n * Update default headers\n */\n updateDefaultHeaders(headers: Partial<GatewayRequestHeaders>): void;\n}\n\n/**\n * Gateway client health status\n */\nexport interface GatewayClientHealth {\n /**\n * Internal gateway status\n */\n internal: {\n url: string;\n circuitState: CircuitState;\n stats: CircuitBreakerStats;\n };\n\n /**\n * Cross-layer gateway status\n */\n crossLayer: {\n url: string;\n circuitState: CircuitState;\n stats: CircuitBreakerStats;\n };\n}\n\n/**\n * Gateway error types\n */\nexport enum GatewayErrorType {\n NETWORK_ERROR = 'NETWORK_ERROR',\n TIMEOUT_ERROR = 'TIMEOUT_ERROR',\n CIRCUIT_OPEN = 'CIRCUIT_OPEN',\n GRAPHQL_ERROR = 'GRAPHQL_ERROR',\n UNKNOWN_ERROR = 'UNKNOWN_ERROR',\n}\n\n/**\n * Gateway error class\n */\nexport class GatewayError extends Error {\n type: GatewayErrorType;\n gatewayUrl: string;\n statusCode?: number;\n graphqlErrors?: GraphQLError[];\n override cause?: Error;\n\n constructor(\n message: string,\n type: GatewayErrorType,\n gatewayUrl: string,\n options?: {\n statusCode?: number;\n graphqlErrors?: GraphQLError[];\n cause?: Error;\n }\n ) {\n super(message);\n this.name = 'GatewayError';\n this.type = type;\n this.gatewayUrl = gatewayUrl;\n this.statusCode = options?.statusCode;\n this.graphqlErrors = options?.graphqlErrors;\n this.cause = options?.cause;\n Object.setPrototypeOf(this, GatewayError.prototype);\n }\n}\n\n/**\n * Request context for logging and tracing\n */\nexport interface RequestContext {\n /**\n * Request ID for tracing\n */\n requestId: string;\n\n /**\n * Actor ID making the request\n */\n actorId?: string;\n\n /**\n * Workspace ID context\n */\n workspaceId?: string;\n\n /**\n * Timestamp when request started\n */\n startTime: number;\n\n /**\n * Call type\n */\n callType: 'internal' | 'cross-layer' | 'direct';\n}\n","/**\n * Unified Gateway Client\n *\n * Provides a layer-aware GraphQL client with circuit breaker,\n * retry logic, and automatic header management for M2M communication.\n *\n * @module gateway/client\n * @category Gateway\n *\n * @example\n * ```typescript\n * import { GatewayClient } from '@burdenoff/be-sdk/gateway';\n *\n * const client = new GatewayClient({\n * layer: 'wspace',\n * serviceName: 'wspace-tags-svc',\n * });\n *\n * // Internal call (same layer)\n * const result = await client.internalQuery({\n * query: `query { getTag(id: \"123\") { id name } }`,\n * });\n *\n * // Cross-layer call\n * const authResult = await client.crossLayerQuery({\n * query: `query { getCurrentUser { id email } }`,\n * });\n * ```\n */\n\nimport { ContextManager } from '../context/index.js';\nimport { LayerManager } from '../layer/index.js';\nimport { logger } from '../logger/index.js';\nimport { signServiceJwt } from './service-jwt.js';\nimport {\n DEFAULT_CIRCUIT_BREAKER_CONFIG,\n DEFAULT_GATEWAY_RETRY_CONFIG,\n type CircuitBreakerConfig,\n type GatewayRequestHeaders,\n type GatewayRetryConfig,\n type ServiceLayer,\n} from '../types/layer.js';\nimport {\n CircuitState,\n GatewayError,\n GatewayErrorType,\n type CircuitBreakerStats,\n type GatewayClientConfig,\n type GatewayClientHealth,\n type GraphQLError,\n type GraphQLRequestOptions,\n type GraphQLResponse,\n type ICircuitBreaker,\n type IGatewayClient,\n type RequestContext,\n} from './types.js';\n\nconst uuidv4 = (): string => crypto.randomUUID();\n\n/**\n * Case-insensitive presence check for the `Authorization` header. HTTP header\n * names are case-insensitive (RFC 7230), and while the outbound `fetch` will\n * preserve whatever casing the caller supplies, callers may legitimately set\n * `authorization` / `Authorization` / even `AUTHORIZATION` via defaultHeaders\n * or options.headers. We must not overwrite an already-supplied token.\n */\nfunction hasAuthorizationHeader(headers: Record<string, string>): boolean {\n for (const key of Object.keys(headers)) {\n if (key.toLowerCase() === 'authorization') return true;\n }\n return false;\n}\n\nexport function resolveBypassPermissionValue(\n token: string | undefined = process.env['INTERNAL_SERVICE_TOKEN']\n): string {\n const normalizedToken = token?.trim();\n\n if (!normalizedToken) {\n throw new Error('INTERNAL_SERVICE_TOKEN must be configured for bypass-enabled gateway calls');\n }\n\n return normalizedToken;\n}\n\n/**\n * Circuit Breaker Implementation\n */\nclass CircuitBreaker implements ICircuitBreaker {\n private state: CircuitState = CircuitState.CLOSED;\n private failures = 0;\n private successes = 0;\n private consecutiveFailures = 0;\n private lastFailureTime: number | null = null;\n private lastSuccessTime: number | null = null;\n private openedAt: number | null = null;\n private failureTimestamps: number[] = [];\n private config: CircuitBreakerConfig;\n\n constructor(config: CircuitBreakerConfig) {\n this.config = config;\n }\n\n getState(): CircuitState {\n this.checkStateTransition();\n return this.state;\n }\n\n recordSuccess(): void {\n this.successes++;\n this.consecutiveFailures = 0;\n this.lastSuccessTime = Date.now();\n\n if (this.state === CircuitState.HALF_OPEN) {\n this.state = CircuitState.CLOSED;\n this.failures = 0;\n this.failureTimestamps = [];\n this.openedAt = null;\n logger.info('[CircuitBreaker] Circuit closed after successful test');\n }\n }\n\n recordFailure(): void {\n this.failures++;\n this.consecutiveFailures++;\n this.lastFailureTime = Date.now();\n this.failureTimestamps.push(Date.now());\n\n // Clean up old timestamps\n const windowStart = Date.now() - this.config.failureWindow;\n this.failureTimestamps = this.failureTimestamps.filter((t) => t > windowStart);\n\n // Check if we should open the circuit\n if (this.state === CircuitState.CLOSED && this.failureTimestamps.length >= this.config.failureThreshold) {\n this.state = CircuitState.OPEN;\n this.openedAt = Date.now();\n logger.warn('[CircuitBreaker] Circuit opened due to failures', {\n failures: this.failureTimestamps.length,\n threshold: this.config.failureThreshold,\n });\n }\n\n // If we're half-open and fail, go back to open\n if (this.state === CircuitState.HALF_OPEN) {\n this.state = CircuitState.OPEN;\n this.openedAt = Date.now();\n logger.warn('[CircuitBreaker] Circuit re-opened after failed test');\n }\n }\n\n allowRequest(): boolean {\n this.checkStateTransition();\n\n switch (this.state) {\n case CircuitState.CLOSED:\n return true;\n case CircuitState.OPEN:\n return false;\n case CircuitState.HALF_OPEN:\n // Allow one test request\n return true;\n default:\n return true;\n }\n }\n\n forceOpen(): void {\n this.state = CircuitState.OPEN;\n this.openedAt = Date.now();\n logger.info('[CircuitBreaker] Circuit force-opened');\n }\n\n forceClose(): void {\n this.state = CircuitState.CLOSED;\n this.failures = 0;\n this.consecutiveFailures = 0;\n this.failureTimestamps = [];\n this.openedAt = null;\n logger.info('[CircuitBreaker] Circuit force-closed');\n }\n\n getStats(): CircuitBreakerStats {\n return {\n state: this.state,\n failures: this.failures,\n successes: this.successes,\n consecutiveFailures: this.consecutiveFailures,\n lastFailureTime: this.lastFailureTime,\n lastSuccessTime: this.lastSuccessTime,\n openedAt: this.openedAt,\n };\n }\n\n private checkStateTransition(): void {\n if (this.state === CircuitState.OPEN && this.openedAt) {\n const elapsed = Date.now() - this.openedAt;\n if (elapsed >= this.config.resetTimeout) {\n this.state = CircuitState.HALF_OPEN;\n logger.info('[CircuitBreaker] Circuit transitioning to half-open');\n }\n }\n }\n}\n\n/**\n * Unified Gateway Client\n */\nexport class GatewayClient implements IGatewayClient {\n private config: GatewayClientConfig;\n private layerManager: LayerManager;\n private internalCircuitBreaker: CircuitBreaker;\n private crossLayerCircuitBreaker: CircuitBreaker;\n private retryConfig: GatewayRetryConfig;\n private defaultHeaders: GatewayRequestHeaders;\n\n constructor(config: GatewayClientConfig) {\n this.config = {\n timeout: 30000,\n enableLogging: true,\n ...config,\n };\n\n // Initialize layer manager\n this.layerManager = new LayerManager({\n layer: config.layer,\n serviceName: config.serviceName,\n serviceIdentity: config.serviceIdentity,\n });\n\n // Override URLs if provided\n if (config.internalGatewayUrl) {\n // Use getter internally, but we'll store the override\n }\n if (config.crossLayerGatewayUrl) {\n // Use getter internally, but we'll store the override\n }\n\n // Initialize circuit breakers\n const cbConfig: CircuitBreakerConfig = {\n ...DEFAULT_CIRCUIT_BREAKER_CONFIG,\n ...config.circuitBreaker,\n };\n this.internalCircuitBreaker = new CircuitBreaker(cbConfig);\n this.crossLayerCircuitBreaker = new CircuitBreaker(cbConfig);\n\n // Initialize retry config\n this.retryConfig = {\n ...DEFAULT_GATEWAY_RETRY_CONFIG,\n ...config.retry,\n };\n\n // Initialize default headers\n this.defaultHeaders = {\n 'x-service-identity': this.layerManager.getServiceIdentity(),\n 'x-actor-type': 'service',\n ...config.defaultHeaders,\n };\n\n logger.debug('[GatewayClient] Initialized', {\n layer: config.layer,\n serviceName: config.serviceName,\n internalUrl: this.getInternalUrl(),\n crossLayerUrl: this.getCrossLayerUrl(),\n });\n }\n\n private getInternalUrl(): string {\n return this.config.internalGatewayUrl || this.layerManager.getInternalGatewayUrl();\n }\n\n private getCrossLayerUrl(): string {\n return this.config.crossLayerGatewayUrl || this.layerManager.getCrossLayerGatewayUrl();\n }\n\n /**\n * Execute internal (same layer) GraphQL query/mutation\n */\n async internalQuery<T = unknown>(options: GraphQLRequestOptions): Promise<GraphQLResponse<T>> {\n const context = this.createRequestContext('internal', options);\n\n return this.executeWithRetry(this.getInternalUrl(), options, this.internalCircuitBreaker, context, {\n bypassPermission: true,\n });\n }\n\n /**\n * Execute cross-layer GraphQL query/mutation\n */\n async crossLayerQuery<T = unknown>(options: GraphQLRequestOptions): Promise<GraphQLResponse<T>> {\n const context = this.createRequestContext('cross-layer', options);\n\n return this.executeWithRetry(\n this.getCrossLayerUrl(),\n options,\n this.crossLayerCircuitBreaker,\n context,\n { bypassPermission: false } // Cross-layer calls go through public gateway\n );\n }\n\n /**\n * Execute GraphQL query/mutation with explicit gateway URL\n */\n async query<T = unknown>(gatewayUrl: string, options: GraphQLRequestOptions): Promise<GraphQLResponse<T>> {\n const context = this.createRequestContext('direct', options);\n\n // Use internal circuit breaker for direct calls\n return this.executeWithRetry(gatewayUrl, options, this.internalCircuitBreaker, context, {\n bypassPermission: false,\n });\n }\n\n getInternalCircuitBreaker(): ICircuitBreaker {\n return this.internalCircuitBreaker;\n }\n\n getCrossLayerCircuitBreaker(): ICircuitBreaker {\n return this.crossLayerCircuitBreaker;\n }\n\n getHealthStatus(): GatewayClientHealth {\n return {\n internal: {\n url: this.getInternalUrl(),\n circuitState: this.internalCircuitBreaker.getState(),\n stats: this.internalCircuitBreaker.getStats(),\n },\n crossLayer: {\n url: this.getCrossLayerUrl(),\n circuitState: this.crossLayerCircuitBreaker.getState(),\n stats: this.crossLayerCircuitBreaker.getStats(),\n },\n };\n }\n\n updateDefaultHeaders(headers: Partial<GatewayRequestHeaders>): void {\n this.defaultHeaders = { ...this.defaultHeaders, ...headers };\n }\n\n private createRequestContext(\n callType: 'internal' | 'cross-layer' | 'direct',\n options: GraphQLRequestOptions\n ): RequestContext {\n return {\n requestId: uuidv4(),\n actorId: options.headers?.['x-actor-id'] || this.defaultHeaders['x-actor-id'],\n workspaceId: options.headers?.['x-workspace-id'] || this.defaultHeaders['x-workspace-id'],\n startTime: Date.now(),\n callType,\n };\n }\n\n /**\n * Check if an error should be retried\n */\n private shouldRetryError(error: unknown): boolean {\n if (!(error instanceof GatewayError)) {\n return true;\n }\n // Don't retry GraphQL errors or circuit open errors\n return error.type !== GatewayErrorType.GRAPHQL_ERROR && error.type !== GatewayErrorType.CIRCUIT_OPEN;\n }\n\n /**\n * Calculate retry delay with exponential backoff\n */\n private calculateRetryDelay(attempt: number): number {\n return Math.min(\n this.retryConfig.initialDelay * Math.pow(this.retryConfig.backoffMultiplier, attempt - 1),\n this.retryConfig.maxDelay\n );\n }\n\n /**\n * Log retry attempt if logging is enabled\n */\n private logRetryAttempt(\n context: RequestContext,\n attempt: number,\n maxAttempts: number,\n delay: number,\n error: Error\n ): void {\n if (this.config.enableLogging) {\n logger.warn('[GatewayClient] Request failed, retrying', {\n requestId: context.requestId,\n attempt,\n maxAttempts,\n delay,\n error: error.message,\n });\n }\n }\n\n private async executeWithRetry<T>(\n gatewayUrl: string,\n options: GraphQLRequestOptions,\n circuitBreaker: CircuitBreaker,\n context: RequestContext,\n settings: { bypassPermission: boolean }\n ): Promise<GraphQLResponse<T>> {\n // Check circuit breaker\n if (!options.skipCircuitBreaker && !circuitBreaker.allowRequest()) {\n throw new GatewayError(`Circuit breaker is open for ${gatewayUrl}`, GatewayErrorType.CIRCUIT_OPEN, gatewayUrl);\n }\n\n const maxAttempts = options.skipRetry ? 1 : this.retryConfig.maxAttempts;\n let lastError: Error | null = null;\n\n for (let attempt = 1; attempt <= maxAttempts; attempt++) {\n try {\n const result = await this.executeRequest<T>(gatewayUrl, options, context, settings.bypassPermission);\n if (!options.skipCircuitBreaker) {\n circuitBreaker.recordSuccess();\n }\n return result;\n } catch (error) {\n lastError = error instanceof Error ? error : new Error(String(error));\n if (!options.skipCircuitBreaker) {\n circuitBreaker.recordFailure();\n }\n\n if (!this.shouldRetryError(error)) {\n throw error;\n }\n\n if (attempt < maxAttempts) {\n const delay = this.calculateRetryDelay(attempt);\n this.logRetryAttempt(context, attempt, maxAttempts, delay, lastError);\n await this.sleep(delay);\n }\n }\n }\n\n throw lastError || new GatewayError('Request failed after retries', GatewayErrorType.UNKNOWN_ERROR, gatewayUrl);\n }\n\n /**\n * Build headers for a request\n */\n private buildRequestHeaders(\n context: RequestContext,\n options: GraphQLRequestOptions,\n bypassPermission: boolean\n ): Record<string, string> {\n const headers: Record<string, string> = {\n 'Content-Type': 'application/json',\n 'x-request-id': context.requestId,\n 'x-call-type': context.callType,\n };\n\n // Cross-layer calls transit the peer layer's PUBLIC gateway, which on alpha\n // sits behind Cloudflare Access. Re-present the inbound request's CF creds\n // (service token and/or the CF_Authorization cookie) so the call passes the\n // CF edge. Added before default/request headers so a caller may still\n // override the non-cookie CF headers explicitly; the CF cookie is reconciled\n // after the merges below so it is never silently clobbered. No-op when the\n // inbound request carried no CF creds (local dev, production) — returns {}.\n const cfHeaders = context.callType === 'cross-layer' ? ContextManager.getCfAccessHeaders() : {};\n Object.assign(headers, cfHeaders);\n\n // Add default headers\n for (const [key, value] of Object.entries(this.defaultHeaders)) {\n if (value !== undefined) {\n headers[key] = String(value);\n }\n }\n\n // Add request-specific headers\n if (options.headers) {\n for (const [key, value] of Object.entries(options.headers)) {\n if (value !== undefined) {\n headers[key] = String(value);\n }\n }\n }\n\n // Add bypass headers for internal calls\n if (bypassPermission) {\n headers['x-bypass-permission'] = resolveBypassPermissionValue();\n headers['x-bypass-source'] = this.layerManager.getServiceIdentity();\n headers['x-bypass-timestamp'] = Date.now().toString();\n }\n\n // Reconcile the CF_Authorization cookie: the default/request-header merges\n // above may set their own `cookie`, which would otherwise clobber the CF\n // cookie applied earlier (or vice versa). Merge so both survive, without\n // duplicating if it's already present.\n const cfCookie = cfHeaders['cookie'];\n if (cfCookie) {\n const existing = headers['cookie'];\n if (!existing) {\n headers['cookie'] = cfCookie;\n } else if (!existing.split(';').some((c) => c.trim() === cfCookie)) {\n headers['cookie'] = `${existing}; ${cfCookie}`;\n }\n }\n\n return headers;\n }\n\n /**\n * Handle GraphQL errors in response\n */\n private handleGraphQLErrors<T>(\n result: GraphQLResponse<T>,\n context: RequestContext,\n gatewayUrl: string,\n duration: number\n ): void {\n if (!result.errors || result.errors.length === 0) {\n return;\n }\n\n const errorMessages = result.errors.map((e: GraphQLError) => e.message).join(', ');\n\n if (this.config.enableLogging) {\n logger.warn('[GatewayClient] GraphQL errors', {\n requestId: context.requestId,\n errors: result.errors,\n duration,\n });\n }\n\n throw new GatewayError(`GraphQL error: ${errorMessages}`, GatewayErrorType.GRAPHQL_ERROR, gatewayUrl, {\n graphqlErrors: result.errors,\n });\n }\n\n /**\n * Handle fetch errors\n */\n private handleFetchError(\n error: unknown,\n context: RequestContext,\n gatewayUrl: string,\n timeout: number,\n duration: number\n ): never {\n if (error instanceof GatewayError) {\n throw error;\n }\n\n if (error instanceof Error) {\n if (error.name === 'AbortError') {\n throw new GatewayError(`Request timed out after ${timeout}ms`, GatewayErrorType.TIMEOUT_ERROR, gatewayUrl, {\n cause: error,\n });\n }\n\n if (this.config.enableLogging) {\n logger.error('[GatewayClient] Request failed', {\n requestId: context.requestId,\n error: error.message,\n duration,\n });\n }\n\n throw new GatewayError(error.message, GatewayErrorType.NETWORK_ERROR, gatewayUrl, {\n cause: error,\n });\n }\n\n throw new GatewayError(String(error), GatewayErrorType.UNKNOWN_ERROR, gatewayUrl);\n }\n\n private async executeRequest<T>(\n gatewayUrl: string,\n options: GraphQLRequestOptions,\n context: RequestContext,\n bypassPermission: boolean\n ): Promise<GraphQLResponse<T>> {\n const timeout = options.timeout || this.config.timeout || 30000;\n const headers = this.buildRequestHeaders(context, options, bypassPermission);\n\n // Cross-layer calls transit the peer layer's PUBLIC gateway, which\n // requires JWT auth to propagate actor context. Mint a short-lived\n // service-actor JWT so the gateway admits the call and preserves\n // `x-actor-type: service` downstream. Skipped when the caller has\n // already supplied an Authorization header (e.g., user-originated\n // cross-layer flows) or when SERVICE_JWT_SECRET is unset.\n if (context.callType === 'cross-layer' && !hasAuthorizationHeader(headers)) {\n const serviceActorId = this.layerManager.getServiceIdentity();\n const serviceJwt = await signServiceJwt(serviceActorId);\n if (serviceJwt) {\n headers['Authorization'] = `Bearer ${serviceJwt}`;\n } else if (this.config.enableLogging) {\n // Subtle failure mode: without the JWT the public gateway strips\n // actor headers and the subgraph rejects with `authenticationRequired`.\n // Surface the root cause so operators rolling out a new caller don't\n // spend time debugging the downstream error.\n logger.debug(\n '[GatewayClient] SERVICE_JWT_SECRET not configured — cross-layer call will proceed without service JWT',\n { requestId: context.requestId, gatewayUrl }\n );\n }\n }\n\n const body = JSON.stringify({\n query: options.query,\n variables: options.variables || {},\n operationName: options.operationName,\n });\n\n if (this.config.enableLogging) {\n logger.debug('[GatewayClient] Executing request', {\n requestId: context.requestId,\n gatewayUrl,\n operationName: options.operationName,\n callType: context.callType,\n bypassPermission,\n });\n }\n\n try {\n const controller = new AbortController();\n const timeoutId = setTimeout(() => controller.abort(), timeout);\n\n const response = await fetch(gatewayUrl, {\n method: 'POST',\n headers,\n body,\n signal: controller.signal,\n });\n\n clearTimeout(timeoutId);\n const duration = Date.now() - context.startTime;\n\n if (!response.ok) {\n throw new GatewayError(\n `HTTP ${response.status}: ${response.statusText}`,\n GatewayErrorType.NETWORK_ERROR,\n gatewayUrl,\n { statusCode: response.status }\n );\n }\n\n const result = (await response.json()) as GraphQLResponse<T>;\n this.handleGraphQLErrors(result, context, gatewayUrl, duration);\n\n if (this.config.enableLogging) {\n logger.debug('[GatewayClient] Request completed', {\n requestId: context.requestId,\n duration,\n hasData: !!result.data,\n });\n }\n\n return result;\n } catch (error) {\n const duration = Date.now() - context.startTime;\n this.handleFetchError(error, context, gatewayUrl, timeout, duration);\n }\n }\n\n private sleep(ms: number): Promise<void> {\n return new Promise((resolve) => setTimeout(resolve, ms));\n }\n}\n\n/**\n * Create a gateway client for a specific layer\n */\nexport function createGatewayClient(config: GatewayClientConfig): GatewayClient {\n return new GatewayClient(config);\n}\n\n/**\n * Create a gateway client from environment variables\n *\n * Required environment variables:\n * - SERVICE_LAYER: 'wspace' | 'global'\n * - SERVICE_NAME: Service name\n *\n * Optional:\n * - SERVICE_IDENTITY: Service identity (defaults to SERVICE_NAME)\n * - {LAYER}_INT_GATEWAY_URL: Internal gateway URL\n * - {OPPOSITE_LAYER}_PUBLIC_GATEWAY_URL: Cross-layer gateway URL\n */\nexport function createGatewayClientFromEnv(): GatewayClient {\n const layer = process.env['SERVICE_LAYER'] as ServiceLayer;\n\n if (!layer || (layer !== 'wspace' && layer !== 'global')) {\n throw new Error(`[GatewayClient] Invalid or missing SERVICE_LAYER. Expected 'wspace' or 'global', got '${layer}'`);\n }\n\n const serviceName = process.env['SERVICE_NAME'];\n if (!serviceName) {\n throw new Error('[GatewayClient] SERVICE_NAME environment variable is required');\n }\n\n const serviceIdentity = process.env['SERVICE_IDENTITY'] || serviceName;\n\n return new GatewayClient({\n layer,\n serviceName,\n serviceIdentity,\n });\n}\n"]}
@@ -1,6 +1,6 @@
1
- import { resetGraphEventEmitter, getGraphEventEmitter, createMemoryPublisher, createGraphEventEmitter, createMemoryConsumer, createGraphEventEmitter2, MemoryEventQueue, MemoryEventPublisher, MemoryEventConsumer, MemoryEventBus, GraphEventEmitterImpl } from './chunk-HDB3UKUN.js';
2
- import { RedisStreamsEventPublisher, RedisStreamsEventConsumer, QueueType, EventQueueFactory } from './chunk-NKLJMTAT.js';
3
- import { streamKey, dlqKey, RedisStreamsConnection } from './chunk-MHNA7IS7.js';
1
+ import { resetGraphEventEmitter, getGraphEventEmitter, createMemoryPublisher, createGraphEventEmitter, createMemoryConsumer, createGraphEventEmitter2, MemoryEventQueue, MemoryEventPublisher, MemoryEventConsumer, MemoryEventBus, GraphEventEmitterImpl } from './chunk-OQ62HA7Z.js';
2
+ import { RedisStreamsEventPublisher, RedisStreamsEventConsumer, QueueType, EventQueueFactory } from './chunk-5ORHPLOA.js';
3
+ import { streamKey, dlqKey, RedisStreamsConnection } from './chunk-S7LWYERE.js';
4
4
  import { logger } from './chunk-CBZNP6RF.js';
5
5
  import { __export, __name } from './chunk-XE4OXN2W.js';
6
6
 
@@ -460,5 +460,5 @@ function createConsumer(stream, consumer) {
460
460
  __name(createConsumer, "createConsumer");
461
461
 
462
462
  export { EventPriority, EventsModule, ModuleEventsService, createConsumer, createModuleEventsService, createPublisher, event_queue_exports };
463
- //# sourceMappingURL=chunk-OIBCAEQJ.js.map
464
- //# sourceMappingURL=chunk-OIBCAEQJ.js.map
463
+ //# sourceMappingURL=chunk-A6WNRJZF.js.map
464
+ //# sourceMappingURL=chunk-A6WNRJZF.js.map
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/event-queue/index.ts","../src/event-queue/module-events.ts","../src/event-queue/events.ts"],"names":["createGraphEventEmitter","ModuleEventsService","productSource","subjectPrefix","loggerLabel","publisher","connected","connecting","config","moduleName","charAt","toUpperCase","slice","process","env","EventQueueFactory","createPublisherFromEnv","logger","info","MemoryEventPublisher","ensureConnected","connect","then","publish","subject","payload","data","buildPayload","type","action","id","userId","tenantId","workspaceId","correlationId","metadata","timestamp","Date","toISOString","buildSubject","entityType","normalizedType","replace","_match","p1","offset","toLowerCase","publishCreated","publishUpdated","publishDeleted","publishCustom","publishBulkCreated","_entityType","items","close","disconnect","healthCheck","result","isHealthy","status","healthy","message","error","createModuleEventsService","EventPriority","EventsModule","client","context","createStream","name","subjects","options","debug","mutation","variables","input","maxMessages","maxBytes","maxAge","storageType","replicas","response","query","getStreamInfo","deleteStream","purgeStream","sequence","purgedCount","createConsumer","streamName","consumerName","queueGroup","durableName","startPosition","ackMode","maxDeliver","ackWait","deleteConsumer","ackMessage","nakMessage","getConsumerInfo","createPublisher","stream","consumer","createConsumerFromEnv","MemoryEventConsumer"],"mappings":"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","file":"chunk-OIBCAEQJ.js","sourcesContent":["/**\n * Event Queue - Public API\n *\n * This module provides a complete abstraction over event queue systems (NATS, RabbitMQ, Kafka, SQS, etc.)\n * allowing the application to publish and consume events without direct dependency on any specific queue implementation.\n *\n * Usage:\n *\n * // Publishing events (workspaces-backend)\n * import { createPublisher } from './utils/event-queue';\n *\n * const publisher = createPublisher();\n * await publisher.connect();\n *\n * await publisher.publish({\n * subject: 'workspace.created',\n * data: { workspaceId: '123', name: 'My Workspace' },\n * metadata: { userId: 'user-123', source: 'api' }\n * });\n *\n * // Consuming events (workspaces-workers)\n * import { createConsumer } from './core/event-queue';\n *\n * const consumer = createConsumer('WORKSPACE_EVENTS', 'workspace-consumer');\n * await consumer.connect();\n *\n * await consumer.subscribe({\n * subject: 'workspace.*',\n * handler: async (event) => {\n * logger.log('Received event:', event.data);\n * await event.ack();\n * }\n * });\n */\n// Import factory for use in convenience functions\nimport { EventQueueFactory } from './factory/EventQueueFactory.js';\n// Import implementations for use in convenience functions\nimport { MemoryEventPublisher, MemoryEventConsumer } from './implementations/memory/MemoryEventQueue.js';\n// Import interfaces for type annotations\nimport type { IEventConsumer } from './interfaces/IEventConsumer.js';\nimport type { IEventPublisher } from './interfaces/IEventPublisher.js';\n\n// Export interfaces\nexport type { IEventQueue } from './interfaces/IEventQueue.js';\nexport type { IEventPublisher, PublishOptions } from './interfaces/IEventPublisher.js';\nexport type { IEventConsumer, ISubscription } from './interfaces/IEventConsumer.js';\n\n// Export types\nexport type {\n EventMessage,\n EventMetadata,\n AcknowledgeableEvent,\n EventHandler,\n StreamConfig,\n SubscriptionOptions,\n ConsumerOptions,\n} from './types/events.js';\n\nexport { QueueType } from './types/config.js';\n\nexport type {\n BaseQueueConfig,\n PublisherConfig,\n ConsumerConfig,\n EventQueueHealthCheckResult,\n QueueStatistics,\n} from './types/config.js';\n\n// Backwards compatibility alias\nexport type { EventQueueHealthCheckResult as HealthCheckResult } from './types/config.js';\n\n// Export factory\nexport { EventQueueFactory } from './factory/EventQueueFactory.js';\n\n// Export Redis Streams implementations\nexport {\n RedisStreamsEventPublisher,\n RedisStreamsEventConsumer,\n RedisStreamsConnection,\n streamKey as redisStreamKey,\n dlqKey as redisDlqKey,\n} from './implementations/redis-streams/index.js';\n\n// Export Memory implementations (for development/testing or fallback)\nexport {\n MemoryEventBus,\n MemoryEventQueue,\n MemoryEventPublisher,\n MemoryEventConsumer,\n createMemoryPublisher,\n createMemoryConsumer,\n createGraphEventEmitter as createMemoryGraphEventEmitter,\n} from './implementations/memory/MemoryEventQueue.js';\n\n// Export Graph Event Emitter (Redis Streams-backed).\nexport {\n GraphEventEmitterImpl,\n getGraphEventEmitter,\n createGraphEventEmitter,\n resetGraphEventEmitter,\n} from './graph-emitter.js';\nexport type { GraphEventEmitter, EntityEventType, EntityEventRbacMetadata } from './graph-emitter.js';\n\n// Export Module Events Service\nexport { ModuleEventsService, createModuleEventsService } from './module-events.js';\nexport type { ModuleEventPayload, BulkEventPayload, ModuleEventsConfig } from './module-events.js';\n\n// Export high-level Events Module (GraphQL-based event publishing)\nexport { EventsModule } from './events.js';\nexport {\n EventPriority,\n type PublishEventOptions,\n type SubscribeOptions,\n type EventMessage as GraphQLEventMessage,\n type PublishResult,\n type StreamInfo,\n} from './events.js';\n\n/**\n * Create an event publisher from environment configuration.\n *\n * Backend resolution:\n * - `REDIS_URL` set → Redis Streams (the only supported backend since\n * the NATS retirement on 2026-05-16).\n * - `REDIS_URL` unset → in-memory (dev/test fallback).\n */\nexport function createPublisher(): IEventPublisher {\n if (process.env['REDIS_URL']) {\n return EventQueueFactory.createPublisherFromEnv();\n }\n return new MemoryEventPublisher();\n}\n\n/**\n * Create an event consumer from environment configuration.\n */\nexport function createConsumer(stream: string, consumer: string): IEventConsumer {\n if (process.env['REDIS_URL']) {\n return EventQueueFactory.createConsumerFromEnv(stream, consumer);\n }\n return new MemoryEventConsumer(stream, consumer);\n}\n","/**\n * Module Events Service\n *\n * Generic event publishing service that modules can configure to publish\n * domain-specific events to NATS JetStream.\n *\n * @module event-queue/module-events\n * @category Events\n *\n * @example\n * ```typescript\n * import { createModuleEventsService } from '@burdenoff/be-sdk/event-queue';\n *\n * // Create a configured event service for the tags module\n * const tagsEventsService = createModuleEventsService({\n * moduleName: 'tags',\n * entityTypes: ['Tag', 'Vocabulary', 'Assignment'],\n * });\n *\n * // Publish events\n * await tagsEventsService.publishCreated('Tag', tagId, tagData, userId);\n * await tagsEventsService.publishUpdated('Vocabulary', vocabId, vocabData, userId);\n * ```\n */\nimport { logger } from '../logger/index.js';\nimport type { IEventPublisher } from './interfaces/IEventPublisher.js';\nimport { MemoryEventPublisher } from './implementations/memory/MemoryEventQueue.js';\nimport { EventQueueFactory } from './factory/EventQueueFactory.js';\n\n/**\n * Event payload structure for module events\n */\nexport interface ModuleEventPayload {\n /** Entity ID */\n id: string;\n /** Entity type (e.g., 'UniversalTag', 'UniversalTagVocabulary') */\n type: string;\n /** Action performed */\n action: 'created' | 'updated' | 'deleted' | 'assigned' | 'removed' | string;\n /** Entity data */\n data: Record<string, unknown>;\n /** Event metadata */\n metadata: {\n tenantId?: string;\n workspaceId?: string;\n userId: string;\n timestamp: string;\n productSource: string;\n correlationId?: string;\n };\n}\n\n/**\n * Bulk event payload structure\n */\nexport interface BulkEventPayload {\n /** Items in the bulk operation */\n items: Array<{ id: string; data: Record<string, unknown> }>;\n /** Event metadata */\n metadata: {\n tenantId?: string;\n workspaceId?: string;\n userId: string;\n timestamp: string;\n productSource: string;\n };\n}\n\n/**\n * Configuration for module events service\n */\nexport interface ModuleEventsConfig {\n /** Module name (used as productSource and in subject prefixes) */\n moduleName: string;\n /** Subject prefix override (defaults to moduleName) */\n subjectPrefix?: string;\n /** Custom logger label */\n loggerLabel?: string;\n}\n\n/**\n * Generic Module Events Service\n *\n * Provides a consistent interface for publishing domain events across all modules.\n * Automatically falls back to in-memory publisher when NATS is not configured.\n */\nexport class ModuleEventsService {\n private readonly productSource: string;\n private readonly subjectPrefix: string;\n private readonly loggerLabel: string;\n private publisher: IEventPublisher;\n private connected = false;\n private connecting: Promise<void> | null = null;\n\n constructor(config: ModuleEventsConfig) {\n this.productSource = config.moduleName;\n this.subjectPrefix = config.subjectPrefix || config.moduleName;\n this.loggerLabel =\n config.loggerLabel || `${config.moduleName.charAt(0).toUpperCase()}${config.moduleName.slice(1)}EventsService`;\n\n // Initialize publisher based on environment\n if (process.env['REDIS_URL']) {\n this.publisher = EventQueueFactory.createPublisherFromEnv();\n logger.info(`[${this.loggerLabel}] Using Redis Streams publisher`);\n } else {\n this.publisher = new MemoryEventPublisher();\n logger.info(`[${this.loggerLabel}] Using in-memory publisher (REDIS_URL not configured)`);\n }\n }\n\n /**\n * Ensure publisher is connected before publishing\n */\n private async ensureConnected(): Promise<void> {\n if (this.connected) {\n return;\n }\n\n if (this.connecting) {\n await this.connecting;\n return;\n }\n\n this.connecting = this.publisher.connect().then(() => {\n this.connected = true;\n this.connecting = null;\n logger.info(`[${this.loggerLabel}] Publisher connected`);\n });\n\n await this.connecting;\n }\n\n /**\n * Publish an event to the queue\n */\n private async publish(subject: string, payload: unknown): Promise<void> {\n await this.ensureConnected();\n await this.publisher.publish({\n subject,\n data: payload as Record<string, unknown>,\n });\n }\n\n /**\n * Build event payload\n */\n private buildPayload(\n type: string,\n action: string,\n id: string,\n data: Record<string, unknown>,\n userId: string,\n tenantId?: string,\n workspaceId?: string,\n correlationId?: string\n ): ModuleEventPayload {\n return {\n id,\n type,\n action,\n data,\n metadata: {\n tenantId,\n workspaceId,\n userId,\n timestamp: new Date().toISOString(),\n productSource: this.productSource,\n ...(correlationId && { correlationId }),\n },\n };\n }\n\n /**\n * Build subject string\n */\n private buildSubject(entityType: string, action: string): string {\n // Convert entityType from PascalCase to lowercase (e.g., UniversalTag -> tag)\n const normalizedType = entityType\n .replace(/^Universal/, '')\n .replace(/([A-Z])/g, (_match, p1, offset) => (offset > 0 ? '_' : '') + (p1 as string).toLowerCase())\n .replace(/^_/, '');\n return `${this.subjectPrefix}.${normalizedType}.${action}`;\n }\n\n /**\n * Publish entity created event\n */\n async publishCreated(\n entityType: string,\n id: string,\n data: Record<string, unknown>,\n userId: string,\n tenantId?: string,\n workspaceId?: string\n ): Promise<void> {\n const payload = this.buildPayload(entityType, 'created', id, data, userId, tenantId, workspaceId);\n await this.publish(this.buildSubject(entityType, 'created'), payload);\n }\n\n /**\n * Publish entity updated event\n */\n async publishUpdated(\n entityType: string,\n id: string,\n data: Record<string, unknown>,\n userId: string,\n tenantId?: string,\n workspaceId?: string\n ): Promise<void> {\n const payload = this.buildPayload(entityType, 'updated', id, data, userId, tenantId, workspaceId);\n await this.publish(this.buildSubject(entityType, 'updated'), payload);\n }\n\n /**\n * Publish entity deleted event\n */\n async publishDeleted(\n entityType: string,\n id: string,\n userId: string,\n tenantId?: string,\n workspaceId?: string\n ): Promise<void> {\n const payload = this.buildPayload(entityType, 'deleted', id, {}, userId, tenantId, workspaceId);\n await this.publish(this.buildSubject(entityType, 'deleted'), payload);\n }\n\n /**\n * Publish custom action event\n */\n async publishCustom(\n entityType: string,\n action: string,\n id: string,\n data: Record<string, unknown>,\n userId: string,\n tenantId?: string,\n workspaceId?: string\n ): Promise<void> {\n const payload = this.buildPayload(entityType, action, id, data, userId, tenantId, workspaceId);\n await this.publish(this.buildSubject(entityType, action), payload);\n }\n\n /**\n * Publish bulk created event\n */\n async publishBulkCreated(\n _entityType: string,\n items: Array<{ id: string; data: Record<string, unknown> }>,\n userId: string,\n tenantId?: string,\n workspaceId?: string\n ): Promise<void> {\n const payload: BulkEventPayload = {\n items,\n metadata: {\n tenantId,\n workspaceId,\n userId,\n timestamp: new Date().toISOString(),\n productSource: this.productSource,\n },\n };\n await this.publish(`${this.subjectPrefix}.bulk.created`, payload);\n }\n\n /**\n * Close event queue connection\n */\n async close(): Promise<void> {\n if (this.connected) {\n await this.publisher.disconnect();\n this.connected = false;\n logger.info(`[${this.loggerLabel}] Publisher disconnected`);\n }\n }\n\n /**\n * Get health check status\n */\n async healthCheck(): Promise<{ healthy: boolean; message: string }> {\n const result = await this.publisher.healthCheck();\n const isHealthy = result.status === 'healthy';\n return {\n healthy: isHealthy,\n message: result.error || (isHealthy ? 'Healthy' : 'Unhealthy'),\n };\n }\n}\n\n/**\n * Create a module events service instance\n */\nexport function createModuleEventsService(config: ModuleEventsConfig): ModuleEventsService {\n return new ModuleEventsService(config);\n}\n","/**\n * Events Module\n * Helpers for sending events to the Redis Streams event queue\n */\n\nimport type { BurdenoffGraphQLClient } from '../client/graphql.js';\nimport type { SDKContext } from '../types/index.js';\nimport { logger } from '../logger/index.js';\n\nexport enum EventPriority {\n LOW = 'low',\n NORMAL = 'normal',\n HIGH = 'high',\n CRITICAL = 'critical',\n}\n\nexport interface PublishEventOptions {\n /** Event subject/topic */\n subject: string;\n /** Event payload */\n data: Record<string, unknown>;\n /** Event priority */\n priority?: EventPriority;\n /** Event metadata */\n metadata?: Record<string, unknown>;\n /** Delay delivery by milliseconds */\n delay?: number;\n /** Message ID (for deduplication) */\n messageId?: string;\n /** Workspace context */\n workspaceId?: string;\n /** Organization context */\n organizationId?: string;\n}\n\nexport interface SubscribeOptions {\n /** Subject pattern to subscribe to */\n subject: string;\n /** Queue group name */\n queueGroup?: string;\n /** Durable consumer name */\n durableName?: string;\n /** Start from specific position */\n startPosition?: 'first' | 'last' | 'new';\n /** Acknowledge mode */\n ackMode?: 'explicit' | 'auto';\n /** Max messages to deliver */\n maxDeliver?: number;\n /** Acknowledgment timeout in milliseconds */\n ackWait?: number;\n}\n\nexport interface EventMessage {\n id: string;\n subject: string;\n data: Record<string, unknown>;\n priority: EventPriority;\n metadata?: Record<string, unknown>;\n workspaceId?: string;\n organizationId?: string;\n publishedAt: string;\n publishedBy?: string;\n}\n\nexport interface PublishResult {\n messageId: string;\n subject: string;\n sequence: number;\n timestamp: string;\n}\n\nexport interface StreamInfo {\n name: string;\n subjects: string[];\n messageCount: number;\n byteCount: number;\n firstSequence: number;\n lastSequence: number;\n consumerCount: number;\n}\n\n/**\n * Events Module\n */\nexport class EventsModule {\n constructor(\n private client: BurdenoffGraphQLClient,\n private context: SDKContext\n ) {}\n\n /**\n * Create stream\n */\n public async createStream(\n name: string,\n subjects: string[],\n options?: {\n maxMessages?: number;\n maxBytes?: number;\n maxAge?: number;\n storageType?: 'file' | 'memory';\n replicas?: number;\n }\n ): Promise<StreamInfo> {\n logger.debug('[Events] Creating stream', { name, subjects });\n\n const mutation = `\n mutation CreateStream($input: CreateStreamInput!) {\n createStream(input: $input) {\n name\n subjects\n messageCount\n byteCount\n firstSequence\n lastSequence\n consumerCount\n }\n }\n `;\n\n const variables = {\n input: {\n name,\n subjects,\n maxMessages: options?.maxMessages,\n maxBytes: options?.maxBytes,\n maxAge: options?.maxAge,\n storageType: options?.storageType || 'file',\n replicas: options?.replicas || 1,\n },\n };\n\n const response = await this.client.query<{ createStream: StreamInfo }>(mutation, variables, this.context);\n\n logger.info('[Events] Stream created', { name });\n\n return response.createStream;\n }\n\n /**\n * Get stream info\n */\n public async getStreamInfo(name: string): Promise<StreamInfo> {\n logger.debug('[Events] Getting stream info', { name });\n\n const query = `\n query GetStreamInfo($name: String!) {\n getStreamInfo(name: $name) {\n name\n subjects\n messageCount\n byteCount\n firstSequence\n lastSequence\n consumerCount\n }\n }\n `;\n\n const response = await this.client.query<{ getStreamInfo: StreamInfo }>(query, { name }, this.context);\n\n return response.getStreamInfo;\n }\n\n /**\n * Delete stream\n */\n public async deleteStream(name: string): Promise<boolean> {\n logger.debug('[Events] Deleting stream', { name });\n\n const mutation = `\n mutation DeleteStream($name: String!) {\n deleteStream(name: $name) {\n success\n }\n }\n `;\n\n await this.client.query(mutation, { name }, this.context);\n\n logger.info('[Events] Stream deleted', { name });\n\n return true;\n }\n\n /**\n * Purge stream messages\n */\n public async purgeStream(name: string, options?: { subject?: string; sequence?: number }): Promise<number> {\n logger.debug('[Events] Purging stream', { name, options });\n\n const mutation = `\n mutation PurgeStream($name: String!, $subject: String, $sequence: Int) {\n purgeStream(name: $name, subject: $subject, sequence: $sequence) {\n purgedCount\n }\n }\n `;\n\n const response = await this.client.query<{ purgeStream: { purgedCount: number } }>(\n mutation,\n { name, subject: options?.subject, sequence: options?.sequence },\n this.context\n );\n\n logger.info('[Events] Stream purged', { name, purgedCount: response.purgeStream.purgedCount });\n\n return response.purgeStream.purgedCount;\n }\n\n /**\n * Create consumer\n */\n public async createConsumer(\n streamName: string,\n consumerName: string,\n options: SubscribeOptions\n ): Promise<{ name: string; pending: number }> {\n logger.debug('[Events] Creating consumer', { streamName, consumerName });\n\n const mutation = `\n mutation CreateConsumer($input: CreateConsumerInput!) {\n createConsumer(input: $input) {\n name\n pending\n }\n }\n `;\n\n const variables = {\n input: {\n streamName,\n consumerName,\n subject: options.subject,\n queueGroup: options.queueGroup,\n durableName: options.durableName,\n startPosition: options.startPosition || 'last',\n ackMode: options.ackMode || 'explicit',\n maxDeliver: options.maxDeliver || 5,\n ackWait: options.ackWait || 30000,\n },\n };\n\n const response = await this.client.query<{ createConsumer: { name: string; pending: number } }>(\n mutation,\n variables,\n this.context\n );\n\n logger.info('[Events] Consumer created', { consumerName });\n\n return response.createConsumer;\n }\n\n /**\n * Delete consumer\n */\n public async deleteConsumer(streamName: string, consumerName: string): Promise<boolean> {\n logger.debug('[Events] Deleting consumer', { streamName, consumerName });\n\n const mutation = `\n mutation DeleteConsumer($streamName: String!, $consumerName: String!) {\n deleteConsumer(streamName: $streamName, consumerName: $consumerName) {\n success\n }\n }\n `;\n\n await this.client.query(mutation, { streamName, consumerName }, this.context);\n\n logger.info('[Events] Consumer deleted', { consumerName });\n\n return true;\n }\n\n /**\n * Acknowledge message\n */\n public async ackMessage(streamName: string, consumerName: string, sequence: number): Promise<boolean> {\n logger.debug('[Events] Acknowledging message', { streamName, consumerName, sequence });\n\n const mutation = `\n mutation AckMessage($streamName: String!, $consumerName: String!, $sequence: Int!) {\n ackMessage(streamName: $streamName, consumerName: $consumerName, sequence: $sequence) {\n success\n }\n }\n `;\n\n await this.client.query(mutation, { streamName, consumerName, sequence }, this.context);\n\n return true;\n }\n\n /**\n * Negative acknowledge message (requeue)\n */\n public async nakMessage(streamName: string, consumerName: string, sequence: number): Promise<boolean> {\n logger.debug('[Events] Negative acknowledging message', { streamName, consumerName, sequence });\n\n const mutation = `\n mutation NakMessage($streamName: String!, $consumerName: String!, $sequence: Int!) {\n nakMessage(streamName: $streamName, consumerName: $consumerName, sequence: $sequence) {\n success\n }\n }\n `;\n\n await this.client.query(mutation, { streamName, consumerName, sequence }, this.context);\n\n return true;\n }\n\n /**\n * Get consumer info\n */\n public async getConsumerInfo(\n streamName: string,\n consumerName: string\n ): Promise<{\n name: string;\n pending: number;\n redelivered: number;\n numAckPending: number;\n }> {\n logger.debug('[Events] Getting consumer info', { streamName, consumerName });\n\n const query = `\n query GetConsumerInfo($streamName: String!, $consumerName: String!) {\n getConsumerInfo(streamName: $streamName, consumerName: $consumerName) {\n name\n pending\n redelivered\n numAckPending\n }\n }\n `;\n\n const response = await this.client.query<{\n getConsumerInfo: {\n name: string;\n pending: number;\n redelivered: number;\n numAckPending: number;\n };\n }>(query, { streamName, consumerName }, this.context);\n\n return response.getConsumerInfo;\n }\n}\n"]}
1
+ {"version":3,"sources":["../src/event-queue/index.ts","../src/event-queue/module-events.ts","../src/event-queue/events.ts"],"names":["createGraphEventEmitter","ModuleEventsService","productSource","subjectPrefix","loggerLabel","publisher","connected","connecting","config","moduleName","charAt","toUpperCase","slice","process","env","EventQueueFactory","createPublisherFromEnv","logger","info","MemoryEventPublisher","ensureConnected","connect","then","publish","subject","payload","data","buildPayload","type","action","id","userId","tenantId","workspaceId","correlationId","metadata","timestamp","Date","toISOString","buildSubject","entityType","normalizedType","replace","_match","p1","offset","toLowerCase","publishCreated","publishUpdated","publishDeleted","publishCustom","publishBulkCreated","_entityType","items","close","disconnect","healthCheck","result","isHealthy","status","healthy","message","error","createModuleEventsService","EventPriority","EventsModule","client","context","createStream","name","subjects","options","debug","mutation","variables","input","maxMessages","maxBytes","maxAge","storageType","replicas","response","query","getStreamInfo","deleteStream","purgeStream","sequence","purgedCount","createConsumer","streamName","consumerName","queueGroup","durableName","startPosition","ackMode","maxDeliver","ackWait","deleteConsumer","ackMessage","nakMessage","getConsumerInfo","createPublisher","stream","consumer","createConsumerFromEnv","MemoryEventConsumer"],"mappings":"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","file":"chunk-A6WNRJZF.js","sourcesContent":["/**\n * Event Queue - Public API\n *\n * This module provides a complete abstraction over event queue systems (NATS, RabbitMQ, Kafka, SQS, etc.)\n * allowing the application to publish and consume events without direct dependency on any specific queue implementation.\n *\n * Usage:\n *\n * // Publishing events (workspaces-backend)\n * import { createPublisher } from './utils/event-queue';\n *\n * const publisher = createPublisher();\n * await publisher.connect();\n *\n * await publisher.publish({\n * subject: 'workspace.created',\n * data: { workspaceId: '123', name: 'My Workspace' },\n * metadata: { userId: 'user-123', source: 'api' }\n * });\n *\n * // Consuming events (workspaces-workers)\n * import { createConsumer } from './core/event-queue';\n *\n * const consumer = createConsumer('WORKSPACE_EVENTS', 'workspace-consumer');\n * await consumer.connect();\n *\n * await consumer.subscribe({\n * subject: 'workspace.*',\n * handler: async (event) => {\n * logger.log('Received event:', event.data);\n * await event.ack();\n * }\n * });\n */\n// Import factory for use in convenience functions\nimport { EventQueueFactory } from './factory/EventQueueFactory.js';\n// Import implementations for use in convenience functions\nimport { MemoryEventPublisher, MemoryEventConsumer } from './implementations/memory/MemoryEventQueue.js';\n// Import interfaces for type annotations\nimport type { IEventConsumer } from './interfaces/IEventConsumer.js';\nimport type { IEventPublisher } from './interfaces/IEventPublisher.js';\n\n// Export interfaces\nexport type { IEventQueue } from './interfaces/IEventQueue.js';\nexport type { IEventPublisher, PublishOptions } from './interfaces/IEventPublisher.js';\nexport type { IEventConsumer, ISubscription } from './interfaces/IEventConsumer.js';\n\n// Export types\nexport type {\n EventMessage,\n EventMetadata,\n AcknowledgeableEvent,\n EventHandler,\n StreamConfig,\n SubscriptionOptions,\n ConsumerOptions,\n} from './types/events.js';\n\nexport { QueueType } from './types/config.js';\n\nexport type {\n BaseQueueConfig,\n PublisherConfig,\n ConsumerConfig,\n EventQueueHealthCheckResult,\n QueueStatistics,\n} from './types/config.js';\n\n// Backwards compatibility alias\nexport type { EventQueueHealthCheckResult as HealthCheckResult } from './types/config.js';\n\n// Export factory\nexport { EventQueueFactory } from './factory/EventQueueFactory.js';\n\n// Export Redis Streams implementations\nexport {\n RedisStreamsEventPublisher,\n RedisStreamsEventConsumer,\n RedisStreamsConnection,\n streamKey as redisStreamKey,\n dlqKey as redisDlqKey,\n} from './implementations/redis-streams/index.js';\n\n// Export Memory implementations (for development/testing or fallback)\nexport {\n MemoryEventBus,\n MemoryEventQueue,\n MemoryEventPublisher,\n MemoryEventConsumer,\n createMemoryPublisher,\n createMemoryConsumer,\n createGraphEventEmitter as createMemoryGraphEventEmitter,\n} from './implementations/memory/MemoryEventQueue.js';\n\n// Export Graph Event Emitter (Redis Streams-backed).\nexport {\n GraphEventEmitterImpl,\n getGraphEventEmitter,\n createGraphEventEmitter,\n resetGraphEventEmitter,\n} from './graph-emitter.js';\nexport type { GraphEventEmitter, EntityEventType, EntityEventRbacMetadata } from './graph-emitter.js';\n\n// Export Module Events Service\nexport { ModuleEventsService, createModuleEventsService } from './module-events.js';\nexport type { ModuleEventPayload, BulkEventPayload, ModuleEventsConfig } from './module-events.js';\n\n// Export high-level Events Module (GraphQL-based event publishing)\nexport { EventsModule } from './events.js';\nexport {\n EventPriority,\n type PublishEventOptions,\n type SubscribeOptions,\n type EventMessage as GraphQLEventMessage,\n type PublishResult,\n type StreamInfo,\n} from './events.js';\n\n/**\n * Create an event publisher from environment configuration.\n *\n * Backend resolution:\n * - `REDIS_URL` set → Redis Streams (the only supported backend since\n * the NATS retirement on 2026-05-16).\n * - `REDIS_URL` unset → in-memory (dev/test fallback).\n */\nexport function createPublisher(): IEventPublisher {\n if (process.env['REDIS_URL']) {\n return EventQueueFactory.createPublisherFromEnv();\n }\n return new MemoryEventPublisher();\n}\n\n/**\n * Create an event consumer from environment configuration.\n */\nexport function createConsumer(stream: string, consumer: string): IEventConsumer {\n if (process.env['REDIS_URL']) {\n return EventQueueFactory.createConsumerFromEnv(stream, consumer);\n }\n return new MemoryEventConsumer(stream, consumer);\n}\n","/**\n * Module Events Service\n *\n * Generic event publishing service that modules can configure to publish\n * domain-specific events to NATS JetStream.\n *\n * @module event-queue/module-events\n * @category Events\n *\n * @example\n * ```typescript\n * import { createModuleEventsService } from '@burdenoff/be-sdk/event-queue';\n *\n * // Create a configured event service for the tags module\n * const tagsEventsService = createModuleEventsService({\n * moduleName: 'tags',\n * entityTypes: ['Tag', 'Vocabulary', 'Assignment'],\n * });\n *\n * // Publish events\n * await tagsEventsService.publishCreated('Tag', tagId, tagData, userId);\n * await tagsEventsService.publishUpdated('Vocabulary', vocabId, vocabData, userId);\n * ```\n */\nimport { logger } from '../logger/index.js';\nimport type { IEventPublisher } from './interfaces/IEventPublisher.js';\nimport { MemoryEventPublisher } from './implementations/memory/MemoryEventQueue.js';\nimport { EventQueueFactory } from './factory/EventQueueFactory.js';\n\n/**\n * Event payload structure for module events\n */\nexport interface ModuleEventPayload {\n /** Entity ID */\n id: string;\n /** Entity type (e.g., 'UniversalTag', 'UniversalTagVocabulary') */\n type: string;\n /** Action performed */\n action: 'created' | 'updated' | 'deleted' | 'assigned' | 'removed' | string;\n /** Entity data */\n data: Record<string, unknown>;\n /** Event metadata */\n metadata: {\n tenantId?: string;\n workspaceId?: string;\n userId: string;\n timestamp: string;\n productSource: string;\n correlationId?: string;\n };\n}\n\n/**\n * Bulk event payload structure\n */\nexport interface BulkEventPayload {\n /** Items in the bulk operation */\n items: Array<{ id: string; data: Record<string, unknown> }>;\n /** Event metadata */\n metadata: {\n tenantId?: string;\n workspaceId?: string;\n userId: string;\n timestamp: string;\n productSource: string;\n };\n}\n\n/**\n * Configuration for module events service\n */\nexport interface ModuleEventsConfig {\n /** Module name (used as productSource and in subject prefixes) */\n moduleName: string;\n /** Subject prefix override (defaults to moduleName) */\n subjectPrefix?: string;\n /** Custom logger label */\n loggerLabel?: string;\n}\n\n/**\n * Generic Module Events Service\n *\n * Provides a consistent interface for publishing domain events across all modules.\n * Automatically falls back to in-memory publisher when NATS is not configured.\n */\nexport class ModuleEventsService {\n private readonly productSource: string;\n private readonly subjectPrefix: string;\n private readonly loggerLabel: string;\n private publisher: IEventPublisher;\n private connected = false;\n private connecting: Promise<void> | null = null;\n\n constructor(config: ModuleEventsConfig) {\n this.productSource = config.moduleName;\n this.subjectPrefix = config.subjectPrefix || config.moduleName;\n this.loggerLabel =\n config.loggerLabel || `${config.moduleName.charAt(0).toUpperCase()}${config.moduleName.slice(1)}EventsService`;\n\n // Initialize publisher based on environment\n if (process.env['REDIS_URL']) {\n this.publisher = EventQueueFactory.createPublisherFromEnv();\n logger.info(`[${this.loggerLabel}] Using Redis Streams publisher`);\n } else {\n this.publisher = new MemoryEventPublisher();\n logger.info(`[${this.loggerLabel}] Using in-memory publisher (REDIS_URL not configured)`);\n }\n }\n\n /**\n * Ensure publisher is connected before publishing\n */\n private async ensureConnected(): Promise<void> {\n if (this.connected) {\n return;\n }\n\n if (this.connecting) {\n await this.connecting;\n return;\n }\n\n this.connecting = this.publisher.connect().then(() => {\n this.connected = true;\n this.connecting = null;\n logger.info(`[${this.loggerLabel}] Publisher connected`);\n });\n\n await this.connecting;\n }\n\n /**\n * Publish an event to the queue\n */\n private async publish(subject: string, payload: unknown): Promise<void> {\n await this.ensureConnected();\n await this.publisher.publish({\n subject,\n data: payload as Record<string, unknown>,\n });\n }\n\n /**\n * Build event payload\n */\n private buildPayload(\n type: string,\n action: string,\n id: string,\n data: Record<string, unknown>,\n userId: string,\n tenantId?: string,\n workspaceId?: string,\n correlationId?: string\n ): ModuleEventPayload {\n return {\n id,\n type,\n action,\n data,\n metadata: {\n tenantId,\n workspaceId,\n userId,\n timestamp: new Date().toISOString(),\n productSource: this.productSource,\n ...(correlationId && { correlationId }),\n },\n };\n }\n\n /**\n * Build subject string\n */\n private buildSubject(entityType: string, action: string): string {\n // Convert entityType from PascalCase to lowercase (e.g., UniversalTag -> tag)\n const normalizedType = entityType\n .replace(/^Universal/, '')\n .replace(/([A-Z])/g, (_match, p1, offset) => (offset > 0 ? '_' : '') + (p1 as string).toLowerCase())\n .replace(/^_/, '');\n return `${this.subjectPrefix}.${normalizedType}.${action}`;\n }\n\n /**\n * Publish entity created event\n */\n async publishCreated(\n entityType: string,\n id: string,\n data: Record<string, unknown>,\n userId: string,\n tenantId?: string,\n workspaceId?: string\n ): Promise<void> {\n const payload = this.buildPayload(entityType, 'created', id, data, userId, tenantId, workspaceId);\n await this.publish(this.buildSubject(entityType, 'created'), payload);\n }\n\n /**\n * Publish entity updated event\n */\n async publishUpdated(\n entityType: string,\n id: string,\n data: Record<string, unknown>,\n userId: string,\n tenantId?: string,\n workspaceId?: string\n ): Promise<void> {\n const payload = this.buildPayload(entityType, 'updated', id, data, userId, tenantId, workspaceId);\n await this.publish(this.buildSubject(entityType, 'updated'), payload);\n }\n\n /**\n * Publish entity deleted event\n */\n async publishDeleted(\n entityType: string,\n id: string,\n userId: string,\n tenantId?: string,\n workspaceId?: string\n ): Promise<void> {\n const payload = this.buildPayload(entityType, 'deleted', id, {}, userId, tenantId, workspaceId);\n await this.publish(this.buildSubject(entityType, 'deleted'), payload);\n }\n\n /**\n * Publish custom action event\n */\n async publishCustom(\n entityType: string,\n action: string,\n id: string,\n data: Record<string, unknown>,\n userId: string,\n tenantId?: string,\n workspaceId?: string\n ): Promise<void> {\n const payload = this.buildPayload(entityType, action, id, data, userId, tenantId, workspaceId);\n await this.publish(this.buildSubject(entityType, action), payload);\n }\n\n /**\n * Publish bulk created event\n */\n async publishBulkCreated(\n _entityType: string,\n items: Array<{ id: string; data: Record<string, unknown> }>,\n userId: string,\n tenantId?: string,\n workspaceId?: string\n ): Promise<void> {\n const payload: BulkEventPayload = {\n items,\n metadata: {\n tenantId,\n workspaceId,\n userId,\n timestamp: new Date().toISOString(),\n productSource: this.productSource,\n },\n };\n await this.publish(`${this.subjectPrefix}.bulk.created`, payload);\n }\n\n /**\n * Close event queue connection\n */\n async close(): Promise<void> {\n if (this.connected) {\n await this.publisher.disconnect();\n this.connected = false;\n logger.info(`[${this.loggerLabel}] Publisher disconnected`);\n }\n }\n\n /**\n * Get health check status\n */\n async healthCheck(): Promise<{ healthy: boolean; message: string }> {\n const result = await this.publisher.healthCheck();\n const isHealthy = result.status === 'healthy';\n return {\n healthy: isHealthy,\n message: result.error || (isHealthy ? 'Healthy' : 'Unhealthy'),\n };\n }\n}\n\n/**\n * Create a module events service instance\n */\nexport function createModuleEventsService(config: ModuleEventsConfig): ModuleEventsService {\n return new ModuleEventsService(config);\n}\n","/**\n * Events Module\n * Helpers for sending events to the Redis Streams event queue\n */\n\nimport type { BurdenoffGraphQLClient } from '../client/graphql.js';\nimport type { SDKContext } from '../types/index.js';\nimport { logger } from '../logger/index.js';\n\nexport enum EventPriority {\n LOW = 'low',\n NORMAL = 'normal',\n HIGH = 'high',\n CRITICAL = 'critical',\n}\n\nexport interface PublishEventOptions {\n /** Event subject/topic */\n subject: string;\n /** Event payload */\n data: Record<string, unknown>;\n /** Event priority */\n priority?: EventPriority;\n /** Event metadata */\n metadata?: Record<string, unknown>;\n /** Delay delivery by milliseconds */\n delay?: number;\n /** Message ID (for deduplication) */\n messageId?: string;\n /** Workspace context */\n workspaceId?: string;\n /** Organization context */\n organizationId?: string;\n}\n\nexport interface SubscribeOptions {\n /** Subject pattern to subscribe to */\n subject: string;\n /** Queue group name */\n queueGroup?: string;\n /** Durable consumer name */\n durableName?: string;\n /** Start from specific position */\n startPosition?: 'first' | 'last' | 'new';\n /** Acknowledge mode */\n ackMode?: 'explicit' | 'auto';\n /** Max messages to deliver */\n maxDeliver?: number;\n /** Acknowledgment timeout in milliseconds */\n ackWait?: number;\n}\n\nexport interface EventMessage {\n id: string;\n subject: string;\n data: Record<string, unknown>;\n priority: EventPriority;\n metadata?: Record<string, unknown>;\n workspaceId?: string;\n organizationId?: string;\n publishedAt: string;\n publishedBy?: string;\n}\n\nexport interface PublishResult {\n messageId: string;\n subject: string;\n sequence: number;\n timestamp: string;\n}\n\nexport interface StreamInfo {\n name: string;\n subjects: string[];\n messageCount: number;\n byteCount: number;\n firstSequence: number;\n lastSequence: number;\n consumerCount: number;\n}\n\n/**\n * Events Module\n */\nexport class EventsModule {\n constructor(\n private client: BurdenoffGraphQLClient,\n private context: SDKContext\n ) {}\n\n /**\n * Create stream\n */\n public async createStream(\n name: string,\n subjects: string[],\n options?: {\n maxMessages?: number;\n maxBytes?: number;\n maxAge?: number;\n storageType?: 'file' | 'memory';\n replicas?: number;\n }\n ): Promise<StreamInfo> {\n logger.debug('[Events] Creating stream', { name, subjects });\n\n const mutation = `\n mutation CreateStream($input: CreateStreamInput!) {\n createStream(input: $input) {\n name\n subjects\n messageCount\n byteCount\n firstSequence\n lastSequence\n consumerCount\n }\n }\n `;\n\n const variables = {\n input: {\n name,\n subjects,\n maxMessages: options?.maxMessages,\n maxBytes: options?.maxBytes,\n maxAge: options?.maxAge,\n storageType: options?.storageType || 'file',\n replicas: options?.replicas || 1,\n },\n };\n\n const response = await this.client.query<{ createStream: StreamInfo }>(mutation, variables, this.context);\n\n logger.info('[Events] Stream created', { name });\n\n return response.createStream;\n }\n\n /**\n * Get stream info\n */\n public async getStreamInfo(name: string): Promise<StreamInfo> {\n logger.debug('[Events] Getting stream info', { name });\n\n const query = `\n query GetStreamInfo($name: String!) {\n getStreamInfo(name: $name) {\n name\n subjects\n messageCount\n byteCount\n firstSequence\n lastSequence\n consumerCount\n }\n }\n `;\n\n const response = await this.client.query<{ getStreamInfo: StreamInfo }>(query, { name }, this.context);\n\n return response.getStreamInfo;\n }\n\n /**\n * Delete stream\n */\n public async deleteStream(name: string): Promise<boolean> {\n logger.debug('[Events] Deleting stream', { name });\n\n const mutation = `\n mutation DeleteStream($name: String!) {\n deleteStream(name: $name) {\n success\n }\n }\n `;\n\n await this.client.query(mutation, { name }, this.context);\n\n logger.info('[Events] Stream deleted', { name });\n\n return true;\n }\n\n /**\n * Purge stream messages\n */\n public async purgeStream(name: string, options?: { subject?: string; sequence?: number }): Promise<number> {\n logger.debug('[Events] Purging stream', { name, options });\n\n const mutation = `\n mutation PurgeStream($name: String!, $subject: String, $sequence: Int) {\n purgeStream(name: $name, subject: $subject, sequence: $sequence) {\n purgedCount\n }\n }\n `;\n\n const response = await this.client.query<{ purgeStream: { purgedCount: number } }>(\n mutation,\n { name, subject: options?.subject, sequence: options?.sequence },\n this.context\n );\n\n logger.info('[Events] Stream purged', { name, purgedCount: response.purgeStream.purgedCount });\n\n return response.purgeStream.purgedCount;\n }\n\n /**\n * Create consumer\n */\n public async createConsumer(\n streamName: string,\n consumerName: string,\n options: SubscribeOptions\n ): Promise<{ name: string; pending: number }> {\n logger.debug('[Events] Creating consumer', { streamName, consumerName });\n\n const mutation = `\n mutation CreateConsumer($input: CreateConsumerInput!) {\n createConsumer(input: $input) {\n name\n pending\n }\n }\n `;\n\n const variables = {\n input: {\n streamName,\n consumerName,\n subject: options.subject,\n queueGroup: options.queueGroup,\n durableName: options.durableName,\n startPosition: options.startPosition || 'last',\n ackMode: options.ackMode || 'explicit',\n maxDeliver: options.maxDeliver || 5,\n ackWait: options.ackWait || 30000,\n },\n };\n\n const response = await this.client.query<{ createConsumer: { name: string; pending: number } }>(\n mutation,\n variables,\n this.context\n );\n\n logger.info('[Events] Consumer created', { consumerName });\n\n return response.createConsumer;\n }\n\n /**\n * Delete consumer\n */\n public async deleteConsumer(streamName: string, consumerName: string): Promise<boolean> {\n logger.debug('[Events] Deleting consumer', { streamName, consumerName });\n\n const mutation = `\n mutation DeleteConsumer($streamName: String!, $consumerName: String!) {\n deleteConsumer(streamName: $streamName, consumerName: $consumerName) {\n success\n }\n }\n `;\n\n await this.client.query(mutation, { streamName, consumerName }, this.context);\n\n logger.info('[Events] Consumer deleted', { consumerName });\n\n return true;\n }\n\n /**\n * Acknowledge message\n */\n public async ackMessage(streamName: string, consumerName: string, sequence: number): Promise<boolean> {\n logger.debug('[Events] Acknowledging message', { streamName, consumerName, sequence });\n\n const mutation = `\n mutation AckMessage($streamName: String!, $consumerName: String!, $sequence: Int!) {\n ackMessage(streamName: $streamName, consumerName: $consumerName, sequence: $sequence) {\n success\n }\n }\n `;\n\n await this.client.query(mutation, { streamName, consumerName, sequence }, this.context);\n\n return true;\n }\n\n /**\n * Negative acknowledge message (requeue)\n */\n public async nakMessage(streamName: string, consumerName: string, sequence: number): Promise<boolean> {\n logger.debug('[Events] Negative acknowledging message', { streamName, consumerName, sequence });\n\n const mutation = `\n mutation NakMessage($streamName: String!, $consumerName: String!, $sequence: Int!) {\n nakMessage(streamName: $streamName, consumerName: $consumerName, sequence: $sequence) {\n success\n }\n }\n `;\n\n await this.client.query(mutation, { streamName, consumerName, sequence }, this.context);\n\n return true;\n }\n\n /**\n * Get consumer info\n */\n public async getConsumerInfo(\n streamName: string,\n consumerName: string\n ): Promise<{\n name: string;\n pending: number;\n redelivered: number;\n numAckPending: number;\n }> {\n logger.debug('[Events] Getting consumer info', { streamName, consumerName });\n\n const query = `\n query GetConsumerInfo($streamName: String!, $consumerName: String!) {\n getConsumerInfo(streamName: $streamName, consumerName: $consumerName) {\n name\n pending\n redelivered\n numAckPending\n }\n }\n `;\n\n const response = await this.client.query<{\n getConsumerInfo: {\n name: string;\n pending: number;\n redelivered: number;\n numAckPending: number;\n };\n }>(query, { streamName, consumerName }, this.context);\n\n return response.getConsumerInfo;\n }\n}\n"]}