dsh-hooks 0.13.0 → 0.13.1

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/events.js +32 -2
  2. package/package.json +1 -1
package/lib/events.js CHANGED
@@ -16,9 +16,39 @@ function callKey(session, callId) {
16
16
  function approvalKey(session, id) {
17
17
  return `${sessionKey(session)}\u0000${String(id)}`;
18
18
  }
19
- /** Best-effort access to a session's event log (test fakes may omit it). */
19
+ /**
20
+ * Best-effort access to a session's event log across harness versions.
21
+ *
22
+ * dsh ≤ 0.1.4 exposed the append-only log as a plain `session.events` array.
23
+ * 0.1.5-rc.1 made that array private (`eventsSnapshot`) and published methods
24
+ * instead: `snapshotEvents(from?, to?)` (whole log, frozen), `ownEvents()`
25
+ * (events after a fork-inherited prefix) and `eventAt(seq)`. Reading only the
26
+ * legacy array silently yielded `[]` there, which blanked the session title,
27
+ * the turn content and the turn usage at once.
28
+ *
29
+ * Preference order: the full snapshot, except for a forked (seeded) session
30
+ * where the fork-inherited prefix belongs to the parent — then its own events
31
+ * are the right scope. Legacy arrays still work, and any accessor that throws
32
+ * degrades to "no log" instead of breaking hook dispatch.
33
+ */
20
34
  function sessionEvents(session) {
21
- return Array.isArray(session.events) ? session.events : [];
35
+ const candidate = session;
36
+ try {
37
+ if (typeof candidate.snapshotEvents === 'function') {
38
+ const inherited = typeof candidate.inheritedEventCount === 'number' ? candidate.inheritedEventCount : 0;
39
+ if (inherited > 0 && typeof candidate.ownEvents === 'function')
40
+ return candidate.ownEvents();
41
+ return candidate.snapshotEvents();
42
+ }
43
+ if (typeof candidate.ownEvents === 'function')
44
+ return candidate.ownEvents();
45
+ if (Array.isArray(candidate.events))
46
+ return candidate.events;
47
+ }
48
+ catch {
49
+ // A hostile/broken accessor must never break hook dispatch.
50
+ }
51
+ return [];
22
52
  }
23
53
  /** Concatenate the text blocks of a message's content, or undefined. */
24
54
  function textOfBlocks(content) {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "dsh-hooks",
3
- "version": "0.13.0",
3
+ "version": "0.13.1",
4
4
  "packageManager": "pnpm@11.21.0",
5
5
  "description": "Config-driven lifecycle hooks plugin for DeepSeek Harness: declare event -> command hooks in cordis.patch.yml, no plugin code required. Includes a Hooks section in the Web GUI settings (history timeline + manual tester + notify tests + hook editor + Feishu connect).",
6
6
  "author": "PeterBon",