@lmzhen/dsh-evolution-feedback 0.3.65 → 0.3.67

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 +26 -5
  2. package/package.json +7 -7
package/lib/index.js CHANGED
@@ -86,7 +86,7 @@ var EvolutionFeedback = class EvolutionFeedback {
86
86
  const rawEvents = await io.readText(eventsPath);
87
87
  const archiveNames = await listEventArchives(io, eventsPath);
88
88
  if ((rawEvents === null || rawEvents.trim() === "") && archiveNames.length === 0) {
89
- const aggregate = parseAggregate(await io.readText(path));
89
+ const aggregate = parseAggregate(await io.readText(path), this.warn);
90
90
  if (aggregate) try {
91
91
  await migrateFeedbackEvents(io, eventsPath, aggregate);
92
92
  } catch {}
@@ -293,13 +293,34 @@ async function migrateFeedbackEvents(io, eventsPath, aggregate) {
293
293
  }, null, 2));
294
294
  });
295
295
  }
296
- /** Parse a legacy aggregate (v1) or a v2 cache into a plain aggregate state. */
297
- function parseAggregate(raw) {
296
+ /** Parse a legacy aggregate (v1) or a v2 cache into a plain aggregate state.
297
+ * V24-05 (v24): every record passes the shared per-record sanitizer (same
298
+ * validation as `parseCache` — S6.4), and migrated counts are clamped so one
299
+ * corrupted field cannot expand into an unbounded event array at boot. */
300
+ const MAX_MIGRATED_EVENTS_PER_RECORD = 1e4;
301
+ function parseAggregate(raw, warn = () => {}) {
298
302
  if (raw === null) return null;
299
303
  try {
300
304
  const parsed = JSON.parse(raw);
301
- const skills = isRecord(parsed.skills) ? parsed.skills : void 0;
302
- const sessions = isRecord(parsed.sessions) ? parsed.sessions : void 0;
305
+ const clamp = (count, target, field) => {
306
+ if (count > MAX_MIGRATED_EVENTS_PER_RECORD) {
307
+ warn(`evolution-feedback: migration clamps ${field}=${count} for "${target}" to ${MAX_MIGRATED_EVENTS_PER_RECORD} — the on-disk aggregate is not trustworthy at that scale`);
308
+ return MAX_MIGRATED_EVENTS_PER_RECORD;
309
+ }
310
+ return count;
311
+ };
312
+ const sanitizeSection = (section, kind) => {
313
+ if (!isRecord(section)) return void 0;
314
+ const cleaned = sanitizeCacheRecords(section, kind, warn);
315
+ for (const [target, record] of Object.entries(cleaned)) if (record.positive > MAX_MIGRATED_EVENTS_PER_RECORD || record.negative > MAX_MIGRATED_EVENTS_PER_RECORD) cleaned[target] = {
316
+ ...record,
317
+ positive: clamp(record.positive, target, "positive"),
318
+ negative: clamp(record.negative, target, "negative")
319
+ };
320
+ return cleaned;
321
+ };
322
+ const skills = sanitizeSection(parsed.skills, "skill");
323
+ const sessions = sanitizeSection(parsed.sessions, "session");
303
324
  if (!skills && !sessions) return null;
304
325
  return {
305
326
  skills: skills ?? {},
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@lmzhen/dsh-evolution-feedback",
3
3
  "description": "Feedback-to-quality scoring for self-evolution (community build)",
4
- "version": "0.3.65",
4
+ "version": "0.3.67",
5
5
  "publishConfig": {
6
6
  "access": "public"
7
7
  },
@@ -31,18 +31,18 @@
31
31
  "license": "MIT",
32
32
  "dependencies": {
33
33
  "@deepseek-ai/schemastery": "^3.18.1",
34
- "@lmzhen/dsh-evolution-core": "^0.3.65"
34
+ "@lmzhen/dsh-evolution-core": "^0.3.67"
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.65",
40
- "@lmzhen/dsh-skill-usage": "^0.3.65"
39
+ "@lmzhen/dsh-evolution-io": "^0.3.67",
40
+ "@lmzhen/dsh-skill-usage": "^0.3.67"
41
41
  },
42
42
  "devDependencies": {
43
43
  "@deepseek-ai/dsh-invariants": "^0.1.1-rc.2",
44
- "@lmzhen/dsh-evolution-io": "^0.3.65",
45
- "@lmzhen/dsh-evolution-io-node": "^0.3.65",
46
- "@lmzhen/dsh-skill-usage": "^0.3.65"
44
+ "@lmzhen/dsh-evolution-io": "^0.3.67",
45
+ "@lmzhen/dsh-evolution-io-node": "^0.3.67",
46
+ "@lmzhen/dsh-skill-usage": "^0.3.67"
47
47
  }
48
48
  }