@cadenza.io/service 2.17.5 → 2.17.7

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.d.mts CHANGED
@@ -320,6 +320,8 @@ declare class ServiceRegistry {
320
320
  private markTransportClientCreated;
321
321
  private registerDependee;
322
322
  private unregisterDependee;
323
+ private reconcileBootstrapPlaceholderInstance;
324
+ private adoptBootstrapPlaceholderInstanceId;
323
325
  private getHeartbeatMisses;
324
326
  private shouldRequireReadinessFromCommunicationTypes;
325
327
  private resolveRuntimeStatusSnapshot;
@@ -23166,6 +23168,7 @@ interface ServiceInstanceDescriptor {
23166
23168
  health: AnyObject;
23167
23169
  isFrontend: boolean;
23168
23170
  isDatabase?: boolean;
23171
+ isBootstrapPlaceholder?: boolean;
23169
23172
  transports: ServiceTransportDescriptor[];
23170
23173
  clientCreatedTransportIds?: string[];
23171
23174
  }
package/dist/index.d.ts CHANGED
@@ -320,6 +320,8 @@ declare class ServiceRegistry {
320
320
  private markTransportClientCreated;
321
321
  private registerDependee;
322
322
  private unregisterDependee;
323
+ private reconcileBootstrapPlaceholderInstance;
324
+ private adoptBootstrapPlaceholderInstanceId;
323
325
  private getHeartbeatMisses;
324
326
  private shouldRequireReadinessFromCommunicationTypes;
325
327
  private resolveRuntimeStatusSnapshot;
@@ -23166,6 +23168,7 @@ interface ServiceInstanceDescriptor {
23166
23168
  health: AnyObject;
23167
23169
  isFrontend: boolean;
23168
23170
  isDatabase?: boolean;
23171
+ isBootstrapPlaceholder?: boolean;
23169
23172
  transports: ServiceTransportDescriptor[];
23170
23173
  clientCreatedTransportIds?: string[];
23171
23174
  }
package/dist/index.js CHANGED
@@ -531,6 +531,9 @@ function normalizeServiceInstanceDescriptor(value) {
531
531
  health: raw.health ?? {},
532
532
  isFrontend: Boolean(raw.isFrontend ?? raw.is_frontend ?? false),
533
533
  isDatabase: Boolean(raw.isDatabase ?? raw.is_database ?? false),
534
+ isBootstrapPlaceholder: Boolean(
535
+ raw.isBootstrapPlaceholder ?? raw.is_bootstrap_placeholder ?? false
536
+ ),
534
537
  transports,
535
538
  clientCreatedTransportIds: Array.isArray(raw.clientCreatedTransportIds) ? raw.clientCreatedTransportIds.map((entry) => normalizeString2(entry)).filter((entry) => entry.length > 0) : void 0
536
539
  };
@@ -944,6 +947,7 @@ var ServiceRegistry = class _ServiceRegistry {
944
947
  health: ctx.health ?? ctx.__health ?? {},
945
948
  numberOfRunningGraphs: ctx.numberOfRunningGraphs ?? ctx.__numberOfRunningGraphs ?? 0,
946
949
  isPrimary: false,
950
+ isBootstrapPlaceholder: !!ctx.isBootstrapPlaceholder,
947
951
  transports: ctx.transports ?? []
948
952
  } : void 0)
949
953
  );
@@ -998,6 +1002,9 @@ var ServiceRegistry = class _ServiceRegistry {
998
1002
  trackedInstance.acceptingWork = snapshot.acceptingWork;
999
1003
  trackedInstance.reportedAt = trackedInstance.reportedAt ?? (/* @__PURE__ */ new Date()).toISOString();
1000
1004
  }
1005
+ if (!serviceInstance.isBootstrapPlaceholder) {
1006
+ this.reconcileBootstrapPlaceholderInstance(serviceName, uuid5, emit);
1007
+ }
1001
1008
  if (this.serviceName === serviceName) {
1002
1009
  return false;
1003
1010
  }
@@ -1287,9 +1294,23 @@ var ServiceRegistry = class _ServiceRegistry {
1287
1294
  (ctx, emit) => {
1288
1295
  const { serviceName, serviceInstanceId } = ctx;
1289
1296
  const serviceInstances = this.instances.get(serviceName);
1290
- const instance = serviceInstances?.find(
1297
+ let instance = serviceInstances?.find(
1291
1298
  (i) => i.uuid === serviceInstanceId
1292
1299
  );
1300
+ if (!instance && serviceName && serviceInstanceId) {
1301
+ const bootstrapPlaceholder = serviceInstances?.find(
1302
+ (candidate) => candidate.isBootstrapPlaceholder && (!ctx.serviceTransportId || candidate.transports.some(
1303
+ (transport) => transport.uuid === ctx.serviceTransportId
1304
+ ))
1305
+ );
1306
+ if (bootstrapPlaceholder) {
1307
+ instance = this.adoptBootstrapPlaceholderInstanceId(
1308
+ serviceName,
1309
+ bootstrapPlaceholder.uuid,
1310
+ serviceInstanceId
1311
+ );
1312
+ }
1313
+ }
1293
1314
  if (!instance) {
1294
1315
  return false;
1295
1316
  }
@@ -2361,6 +2382,7 @@ var ServiceRegistry = class _ServiceRegistry {
2361
2382
  reportedAt: instance?.reportedAt ?? null,
2362
2383
  isDatabase: instance?.isDatabase,
2363
2384
  isFrontend: instance?.isFrontend,
2385
+ isBootstrapPlaceholder: instance?.isBootstrapPlaceholder,
2364
2386
  transports: (instance?.transports ?? []).map((transport) => ({
2365
2387
  uuid: transport.uuid,
2366
2388
  role: transport.role,
@@ -2527,6 +2549,105 @@ var ServiceRegistry = class _ServiceRegistry {
2527
2549
  this.missedHeartbeatsByInstance.delete(serviceInstanceId);
2528
2550
  this.runtimeStatusFallbackInFlightByInstance.delete(serviceInstanceId);
2529
2551
  }
2552
+ reconcileBootstrapPlaceholderInstance(serviceName, resolvedInstanceId, emit) {
2553
+ const instances = this.instances.get(serviceName);
2554
+ if (!instances?.length) {
2555
+ return;
2556
+ }
2557
+ const placeholders = instances.filter(
2558
+ (instance) => instance.uuid !== resolvedInstanceId && instance.isBootstrapPlaceholder
2559
+ );
2560
+ if (!placeholders.length) {
2561
+ return;
2562
+ }
2563
+ for (const placeholder of placeholders) {
2564
+ const wasDependee = this.dependeeByInstance.has(placeholder.uuid);
2565
+ const requiredForReadiness = this.readinessDependeeByInstance.has(
2566
+ placeholder.uuid
2567
+ );
2568
+ for (const transport of placeholder.transports) {
2569
+ const transportKey = buildTransportClientKey(transport);
2570
+ emit(`meta.socket_shutdown_requested:${transportKey}`, {});
2571
+ emit(`meta.fetch.destroy_requested:${transportKey}`, {});
2572
+ }
2573
+ this.unregisterDependee(placeholder.uuid, serviceName);
2574
+ if (wasDependee) {
2575
+ this.registerDependee(serviceName, resolvedInstanceId, {
2576
+ requiredForReadiness
2577
+ });
2578
+ }
2579
+ }
2580
+ this.instances.set(
2581
+ serviceName,
2582
+ instances.filter((instance) => !instance.isBootstrapPlaceholder)
2583
+ );
2584
+ }
2585
+ adoptBootstrapPlaceholderInstanceId(serviceName, placeholderInstanceId, resolvedInstanceId) {
2586
+ if (!serviceName || !placeholderInstanceId || !resolvedInstanceId) {
2587
+ return void 0;
2588
+ }
2589
+ const instances = this.instances.get(serviceName);
2590
+ if (!instances?.length) {
2591
+ return void 0;
2592
+ }
2593
+ const resolvedInstance = instances.find(
2594
+ (instance) => instance.uuid === resolvedInstanceId
2595
+ );
2596
+ if (resolvedInstance) {
2597
+ return resolvedInstance;
2598
+ }
2599
+ const placeholder = instances.find(
2600
+ (instance) => instance.uuid === placeholderInstanceId && instance.isBootstrapPlaceholder
2601
+ );
2602
+ if (!placeholder) {
2603
+ return void 0;
2604
+ }
2605
+ const wasDependee = this.dependeeByInstance.has(placeholderInstanceId);
2606
+ const dependeeServiceName = this.dependeeByInstance.get(placeholderInstanceId) ?? serviceName;
2607
+ const requiredForReadiness = this.readinessDependeeByInstance.has(
2608
+ placeholderInstanceId
2609
+ );
2610
+ const lastHeartbeatAt = this.lastHeartbeatAtByInstance.get(placeholderInstanceId) ?? Date.now();
2611
+ const missedHeartbeats = this.missedHeartbeatsByInstance.get(placeholderInstanceId) ?? 0;
2612
+ const inFlight = this.runtimeStatusFallbackInFlightByInstance.has(
2613
+ placeholderInstanceId
2614
+ );
2615
+ this.dependeeByInstance.delete(placeholderInstanceId);
2616
+ this.readinessDependeeByInstance.delete(placeholderInstanceId);
2617
+ this.lastHeartbeatAtByInstance.delete(placeholderInstanceId);
2618
+ this.missedHeartbeatsByInstance.delete(placeholderInstanceId);
2619
+ this.runtimeStatusFallbackInFlightByInstance.delete(placeholderInstanceId);
2620
+ placeholder.uuid = resolvedInstanceId;
2621
+ placeholder.isBootstrapPlaceholder = false;
2622
+ placeholder.transports = placeholder.transports.map((transport) => ({
2623
+ ...transport,
2624
+ serviceInstanceId: resolvedInstanceId
2625
+ }));
2626
+ if (wasDependee) {
2627
+ this.dependeeByInstance.set(resolvedInstanceId, dependeeServiceName);
2628
+ if (this.dependeesByService.has(dependeeServiceName)) {
2629
+ this.dependeesByService.get(dependeeServiceName).delete(
2630
+ placeholderInstanceId
2631
+ );
2632
+ this.dependeesByService.get(dependeeServiceName).add(resolvedInstanceId);
2633
+ }
2634
+ this.lastHeartbeatAtByInstance.set(resolvedInstanceId, lastHeartbeatAt);
2635
+ this.missedHeartbeatsByInstance.set(resolvedInstanceId, missedHeartbeats);
2636
+ }
2637
+ if (requiredForReadiness) {
2638
+ this.readinessDependeeByInstance.set(resolvedInstanceId, serviceName);
2639
+ if (this.readinessDependeesByService.has(serviceName)) {
2640
+ this.readinessDependeesByService.get(serviceName).delete(
2641
+ placeholderInstanceId
2642
+ );
2643
+ this.readinessDependeesByService.get(serviceName).add(resolvedInstanceId);
2644
+ }
2645
+ }
2646
+ if (inFlight) {
2647
+ this.runtimeStatusFallbackInFlightByInstance.add(resolvedInstanceId);
2648
+ }
2649
+ return placeholder;
2650
+ }
2530
2651
  getHeartbeatMisses(serviceInstanceId, now = Date.now()) {
2531
2652
  const observedMisses = this.missedHeartbeatsByInstance.get(serviceInstanceId) ?? 0;
2532
2653
  const lastHeartbeatAt = this.lastHeartbeatAtByInstance.get(serviceInstanceId) ?? 0;
@@ -9615,6 +9736,7 @@ var CadenzaService = class {
9615
9736
  isBlocked: false,
9616
9737
  health: {},
9617
9738
  isFrontend: false,
9739
+ isBootstrapPlaceholder: true,
9618
9740
  transports: resolvedBootstrapEndpoint ? [
9619
9741
  this.createBootstrapTransport(
9620
9742
  "cadenza-db",
@@ -9642,6 +9764,7 @@ var CadenzaService = class {
9642
9764
  isBlocked: false,
9643
9765
  health: {},
9644
9766
  isFrontend: false,
9767
+ isBootstrapPlaceholder: true,
9645
9768
  transports: relatedTransport ? [
9646
9769
  {
9647
9770
  uuid: `${service[0]}-${relatedTransport.role}`,