@cadenza.io/core 3.26.1 → 3.27.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.mjs CHANGED
@@ -3853,6 +3853,7 @@ var Actor = class {
3853
3853
  this.stateByKey = /* @__PURE__ */ new Map();
3854
3854
  this.sessionByKey = /* @__PURE__ */ new Map();
3855
3855
  this.idempotencyByKey = /* @__PURE__ */ new Map();
3856
+ this.pendingHydrationByKey = /* @__PURE__ */ new Map();
3856
3857
  this.writeQueueByKey = /* @__PURE__ */ new Map();
3857
3858
  this.nextTaskBindingIndex = 0;
3858
3859
  if (!spec.name || typeof spec.name !== "string") {
@@ -3864,6 +3865,7 @@ var Actor = class {
3864
3865
  }
3865
3866
  this.kind = options.isMeta || spec.kind === "meta" ? "meta" : "standard";
3866
3867
  this.sourceDefinition = options.definitionSource;
3868
+ this.hydrateDurableState = options.hydrateDurableState;
3867
3869
  this.spec = {
3868
3870
  ...spec,
3869
3871
  defaultKey: normalizedDefaultKey,
@@ -3891,7 +3893,7 @@ var Actor = class {
3891
3893
  this.pruneExpiredActorKeys(now2);
3892
3894
  this.touchSession(actorKey, invocationOptions.touchSession, now2);
3893
3895
  const runTask = async () => {
3894
- const stateRecord = this.ensureStateRecord(actorKey);
3896
+ const stateRecord = await this.maybeHydrateStateRecord(actorKey);
3895
3897
  stateRecord.lastReadAt = Date.now();
3896
3898
  let durableStateChanged = false;
3897
3899
  let runtimeStateChanged = false;
@@ -4133,6 +4135,7 @@ var Actor = class {
4133
4135
  this.stateByKey.clear();
4134
4136
  this.sessionByKey.clear();
4135
4137
  this.idempotencyByKey.clear();
4138
+ this.pendingHydrationByKey.clear();
4136
4139
  if ((this.spec.loadPolicy ?? "eager") === "eager") {
4137
4140
  this.ensureStateRecord(this.spec.defaultKey);
4138
4141
  }
@@ -4144,6 +4147,7 @@ var Actor = class {
4144
4147
  }
4145
4148
  this.stateByKey.delete(normalizedKey);
4146
4149
  this.sessionByKey.delete(normalizedKey);
4150
+ this.pendingHydrationByKey.delete(normalizedKey);
4147
4151
  for (const key of this.idempotencyByKey.keys()) {
4148
4152
  if (key.startsWith(`${normalizedKey}:`)) {
4149
4153
  this.idempotencyByKey.delete(key);
@@ -4229,6 +4233,7 @@ var Actor = class {
4229
4233
  runtimeState: this.resolveInitialRuntimeState(),
4230
4234
  version: 0,
4231
4235
  runtimeVersion: 0,
4236
+ hydrationResolved: this.hydrateDurableState === void 0,
4232
4237
  createdAt: now2,
4233
4238
  lastReadAt: now2,
4234
4239
  lastDurableWriteAt: now2,
@@ -4238,6 +4243,54 @@ var Actor = class {
4238
4243
  this.touchSession(actorKey, true, now2);
4239
4244
  return record;
4240
4245
  }
4246
+ async maybeHydrateStateRecord(actorKey) {
4247
+ const record = this.ensureStateRecord(actorKey);
4248
+ if (record.hydrationResolved || !this.hydrateDurableState) {
4249
+ return record;
4250
+ }
4251
+ const pending = this.pendingHydrationByKey.get(actorKey);
4252
+ if (pending) {
4253
+ return pending;
4254
+ }
4255
+ let hydrationPromise;
4256
+ hydrationPromise = (async () => {
4257
+ const current = this.ensureStateRecord(actorKey);
4258
+ if (current.hydrationResolved || !this.hydrateDurableState) {
4259
+ return current;
4260
+ }
4261
+ const snapshot = await this.hydrateDurableState(actorKey);
4262
+ const latest = this.ensureStateRecord(actorKey);
4263
+ if (latest.hydrationResolved) {
4264
+ return latest;
4265
+ }
4266
+ if (snapshot) {
4267
+ const durableVersion = Number(snapshot.durableVersion);
4268
+ if (!Number.isInteger(durableVersion) || durableVersion < 0) {
4269
+ throw new Error(
4270
+ `Actor "${this.spec.name}" received invalid hydrated durable version for key "${actorKey}"`
4271
+ );
4272
+ }
4273
+ if (!isObject2(snapshot.durableState) || Array.isArray(snapshot.durableState)) {
4274
+ throw new Error(
4275
+ `Actor "${this.spec.name}" received invalid hydrated durable state for key "${actorKey}"`
4276
+ );
4277
+ }
4278
+ const hydratedAt = Date.now();
4279
+ latest.durableState = cloneForDurableState(snapshot.durableState);
4280
+ latest.version = durableVersion;
4281
+ latest.lastReadAt = hydratedAt;
4282
+ latest.lastDurableWriteAt = hydratedAt;
4283
+ }
4284
+ latest.hydrationResolved = true;
4285
+ return latest;
4286
+ })().finally(() => {
4287
+ if (this.pendingHydrationByKey.get(actorKey) === hydrationPromise) {
4288
+ this.pendingHydrationByKey.delete(actorKey);
4289
+ }
4290
+ });
4291
+ this.pendingHydrationByKey.set(actorKey, hydrationPromise);
4292
+ return hydrationPromise;
4293
+ }
4241
4294
  touchSession(actorKey, shouldTouch, touchedAt) {
4242
4295
  if (!this.spec.session?.enabled || !shouldTouch) {
4243
4296
  return;
@@ -7335,7 +7388,8 @@ var Cadenza = class {
7335
7388
  };
7336
7389
  const actorOptions = {
7337
7390
  isMeta: options.isMeta,
7338
- definitionSource: definition
7391
+ definitionSource: definition,
7392
+ hydrateDurableState: options.hydrateDurableState
7339
7393
  };
7340
7394
  return this.createActor(spec, actorOptions);
7341
7395
  }