@lmzhen/dsh-evolution-state-json 0.3.28 → 0.3.29

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 (2) hide show
  1. package/lib/index.js +44 -12
  2. package/package.json +6 -6
package/lib/index.js CHANGED
@@ -94,12 +94,41 @@ function apply(ctx, rawConfig) {
94
94
  return parsed;
95
95
  }
96
96
  const mutate = makeSerialQueue();
97
+ let legacyMigrated = false;
98
+ async function retireLegacyOnce(legacy, current) {
99
+ if (legacyMigrated) return {};
100
+ try {
101
+ const archivedIds = /* @__PURE__ */ new Set();
102
+ try {
103
+ const rawArchive = await readJson("pending-state-archive.json");
104
+ if (Array.isArray(rawArchive)) {
105
+ for (const entry of rawArchive) if (entry && typeof entry.id === "string") archivedIds.add(entry.id);
106
+ }
107
+ } catch {}
108
+ const retired = {};
109
+ for (const [id, record] of Object.entries(legacy)) {
110
+ if (id in (current ?? {})) continue;
111
+ if (archivedIds.has(id)) continue;
112
+ retired[id] = record;
113
+ }
114
+ await jsonTransact(io, root, "pending-state.json", () => ({
115
+ ...retired,
116
+ ...current ?? {}
117
+ }));
118
+ await io().rename(pathOf("pending.json"), pathOf("pending.json.migrated"));
119
+ legacyMigrated = true;
120
+ return retired;
121
+ } catch {
122
+ return legacy;
123
+ }
124
+ }
97
125
  async function loadPendingMap() {
98
126
  const [current, legacy] = await Promise.all([readJson("pending-state.json"), readJson("pending.json")]);
99
- return {
100
- ...legacy ?? {},
127
+ if (legacy !== null) return {
128
+ ...await retireLegacyOnce(legacy, current),
101
129
  ...current ?? {}
102
130
  };
131
+ return { ...current ?? {} };
103
132
  }
104
133
  /** 0.3.22 (F-336): when the live pending map holds more than
105
134
  * `PENDING_RESOLVED_CAP` resolved records, drop the oldest (by resolvedAt,
@@ -114,12 +143,15 @@ function apply(ctx, rawConfig) {
114
143
  evicted: []
115
144
  };
116
145
  const overflow = resolved.length - PENDING_RESOLVED_CAP;
117
- const oldest = resolved.sort((a, b) => {
118
- return (a.resolvedAt ? Date.parse(a.resolvedAt) : Number.MAX_SAFE_INTEGER) - (b.resolvedAt ? Date.parse(b.resolvedAt) : Number.MAX_SAFE_INTEGER);
119
- }).slice(0, overflow);
146
+ const entryTime = (record) => {
147
+ if (!record.resolvedAt) return Number.MAX_SAFE_INTEGER;
148
+ const parsed = Date.parse(record.resolvedAt);
149
+ return Number.isNaN(parsed) ? Number.MAX_SAFE_INTEGER : parsed;
150
+ };
151
+ const oldest = resolved.sort((a, b) => entryTime(a) - entryTime(b)).slice(0, overflow);
120
152
  const evictIds = new Set(oldest.map((record) => record.id));
121
153
  const kept = {};
122
- for (const [key, value] of Object.entries(map)) if (!evictIds.has(key)) kept[key] = value;
154
+ for (const [key, value] of Object.entries(map)) if (!evictIds.has(value.id)) kept[key] = value;
123
155
  return {
124
156
  map: kept,
125
157
  evicted: oldest
@@ -148,8 +180,8 @@ function apply(ctx, rawConfig) {
148
180
  if (fresh.length === 0) return current;
149
181
  const next = [...archive, ...fresh];
150
182
  if (next.length > ARCHIVE_RESOLVED_CAP) {
151
- await io().writeText(pathOf("pending-state-archive.json.bak"), JSON.stringify(archive, null, 2)).catch(() => {});
152
- return JSON.stringify(fresh, null, 2);
183
+ if (archive.length > 0) await io().writeText(pathOf("pending-state-archive.json.bak"), JSON.stringify(archive, null, 2)).catch(() => {});
184
+ return JSON.stringify(fresh.slice(-5e3), null, 2);
153
185
  }
154
186
  return JSON.stringify(next, null, 2);
155
187
  });
@@ -205,7 +237,7 @@ function apply(ctx, rawConfig) {
205
237
  await mutate(async () => {
206
238
  await jsonTransact(io, root, "pending-state.json", async (current) => {
207
239
  return {
208
- ...await readJson("pending.json") ?? {},
240
+ ...(legacyMigrated ? null : await readJson("pending.json")) ?? {},
209
241
  ...current ?? {},
210
242
  [record.id]: record
211
243
  };
@@ -217,7 +249,7 @@ function apply(ctx, rawConfig) {
217
249
  const slot = { claimed: null };
218
250
  await jsonTransact(io, root, "pending-state.json", async (current) => {
219
251
  const map = {
220
- ...await readJson("pending.json") ?? {},
252
+ ...(legacyMigrated ? null : await readJson("pending.json")) ?? {},
221
253
  ...current ?? {}
222
254
  };
223
255
  const record = map[id] ?? null;
@@ -239,7 +271,7 @@ function apply(ctx, rawConfig) {
239
271
  await mutate(async () => {
240
272
  await jsonTransact(io, root, "pending-state.json", async (current) => {
241
273
  const map = {
242
- ...await readJson("pending.json") ?? {},
274
+ ...(legacyMigrated ? null : await readJson("pending.json")) ?? {},
243
275
  ...current ?? {}
244
276
  };
245
277
  const record = map[id];
@@ -260,7 +292,7 @@ function apply(ctx, rawConfig) {
260
292
  let evicted = [];
261
293
  await jsonTransact(io, root, "pending-state.json", async (current) => {
262
294
  const map = {
263
- ...await readJson("pending.json") ?? {},
295
+ ...(legacyMigrated ? null : await readJson("pending.json")) ?? {},
264
296
  ...current ?? {}
265
297
  };
266
298
  const record = map[id] ?? null;
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@lmzhen/dsh-evolution-state-json",
3
3
  "description": "JSON-file evolution state provider over the IO seam (community build)",
4
- "version": "0.3.28",
4
+ "version": "0.3.29",
5
5
  "publishConfig": {
6
6
  "access": "public"
7
7
  },
@@ -31,17 +31,17 @@
31
31
  "license": "MIT",
32
32
  "dependencies": {
33
33
  "@deepseek-ai/schemastery": "^3.18.1",
34
- "@lmzhen/dsh-evolution-core": "^0.3.28"
34
+ "@lmzhen/dsh-evolution-core": "^0.3.29"
35
35
  },
36
36
  "peerDependencies": {
37
37
  "@deepseek-ai/dsh-invariants": "^0.1.1-rc.2",
38
38
  "@deepseek-ai/cordis": "^4.0.1",
39
- "@lmzhen/dsh-evolution-io": "^0.3.28",
40
- "@lmzhen/dsh-evolution-state-storage": "^0.3.28"
39
+ "@lmzhen/dsh-evolution-io": "^0.3.29",
40
+ "@lmzhen/dsh-evolution-state-storage": "^0.3.29"
41
41
  },
42
42
  "devDependencies": {
43
43
  "@deepseek-ai/dsh-invariants": "^0.1.1-rc.2",
44
- "@lmzhen/dsh-evolution-io": "^0.3.28",
45
- "@lmzhen/dsh-evolution-state-storage": "^0.3.28"
44
+ "@lmzhen/dsh-evolution-io": "^0.3.29",
45
+ "@lmzhen/dsh-evolution-state-storage": "^0.3.29"
46
46
  }
47
47
  }