@deepseek-ai/dsh-session 0.1.2-alpha.2 → 0.1.2-alpha.4

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.
@@ -1,4 +1,4 @@
1
- import { type Branded } from '@deepseek-ai/dsh-brand';
1
+ import { type Branded, type BrandedNumber } from '@deepseek-ai/dsh-brand';
2
2
  import type { AssistantMessage, ToolCallId, LlmCallConfig, LlmCallConfigAdapterDefaults, LlmFailure, StreamChunk, TokenUsage, ToolResultMessage, ToolSchema, UserMessage } from '@deepseek-ai/dsh-llm';
3
3
  import type { JsonValue } from '@deepseek-ai/dsh-util-values';
4
4
  /** Identifies one session in the store (and its persistence artifacts). */
@@ -9,6 +9,26 @@ export type SessionId = Branded<'SessionId'>;
9
9
  * @returns the same string with the session-id brand.
10
10
  */
11
11
  export declare function SessionId(id: string): SessionId;
12
+ /** Sequence number of one existing event in a Session log. */
13
+ export type SessionSeq = BrandedNumber<'SessionSeq'>;
14
+ /**
15
+ * Admit a numeric value as an existing Session event position.
16
+ * @param value - non-negative safe integer admitted by the owning log operation.
17
+ * @returns the same number with the Session-sequence brand.
18
+ */
19
+ export declare function SessionSeq(value: number): SessionSeq;
20
+ /** A Session log gap, prefix length, or read offset, which may equal the event count. */
21
+ export type SessionLogOffset = BrandedNumber<'SessionLogOffset'>;
22
+ /**
23
+ * Admit a numeric value as a Session log offset.
24
+ * @param value - non-negative safe integer used as a gap or prefix length.
25
+ * @returns the same number with the Session-log-offset brand.
26
+ */
27
+ export declare function SessionLogOffset(value: number): SessionLogOffset;
28
+ /** Inclusive Session event watermark, or `-1` before any event exists. */
29
+ export type SessionSeqCursor = SessionSeq | -1;
30
+ /** One existing Session event position, or explicit absence. */
31
+ export type OptionalSessionSeq = SessionSeq | null;
12
32
  /**
13
33
  * The on-disk session format version, stamped into every newly-written {@link SessionHeader}
14
34
  * and enforced by every persistence backend on load. The single source of truth for the
@@ -52,10 +72,10 @@ export interface SessionHeader {
52
72
  /** The session this one was forked from (seed lineage), if any. */
53
73
  readonly parentSession?: SessionId;
54
74
  /**
55
- * How many leading events were inherited through a seed. Persisting this
56
- * boundary lets resume and replay distinguish parent history from child work.
75
+ * Whether this Session contains a fork-inherited event prefix. The exact prefix
76
+ * length is Session state rather than ordinary header metadata.
57
77
  */
58
- readonly seedLength?: number;
78
+ readonly isSeeded: boolean;
59
79
  /**
60
80
  * Coarse product classification for a session created as a subagent child.
61
81
  * This is presentation metadata, not proof that the child is continuable.
@@ -84,14 +104,19 @@ export interface CreateSessionOptions {
84
104
  /** Initial replay or fork history supplied at construction. */
85
105
  readonly seed?: readonly SessionEvent[];
86
106
  /**
87
- * Storage metadata read once before publication. `seedLength` is explicit
88
- * because a resumed seed contains the full stored log, not only its inherited prefix.
107
+ * Exact fork-inherited prefix length when `meta.isSeeded` is true. A
108
+ * constructor seed may also contain child-owned setup events after this cut.
109
+ */
110
+ readonly inheritedEventCount?: SessionLogOffset;
111
+ /**
112
+ * Storage metadata read once before publication. `isSeeded` marks fork
113
+ * lineage; supplying replay history alone does not make it inherited.
89
114
  */
90
115
  readonly meta?: {
91
116
  readonly cwd?: string;
92
117
  readonly parentSession?: SessionId;
93
118
  readonly createdAt?: number;
94
- readonly seedLength?: number;
119
+ readonly isSeeded?: boolean;
95
120
  readonly origin?: 'subagent';
96
121
  readonly delegationDepth?: number;
97
122
  readonly agentPreset?: string;
@@ -106,6 +131,8 @@ export interface RestoredSessionOptions {
106
131
  readonly seed: SessionEvent[];
107
132
  /** Fresh detached storage metadata to validate and freeze in place. */
108
133
  readonly meta: SessionHeader;
134
+ /** Exact number of fork-inherited leading events decoded from storage. */
135
+ readonly inheritedEventCount: SessionLogOffset;
109
136
  /** Select the persistence ownership-transfer path. */
110
137
  readonly seedSource: 'persistence';
111
138
  }
@@ -375,8 +402,8 @@ export type SurfaceEvent = SessionEvent<SurfaceEventType> & {
375
402
  */
376
403
  export type SurfaceOp = 'append' | {
377
404
  op: 'replace';
378
- start: number;
379
- end: number;
405
+ start: SessionSeq;
406
+ end: SessionSeq;
380
407
  };
381
408
  /**
382
409
  * Surface placement and cited source-event seqs for {@link Session.append}. Required on
@@ -390,7 +417,7 @@ export interface SurfaceIntent {
390
417
  * absent, the event does not record which earlier events produced the message.
391
418
  * Other surface events require a non-empty set when this field is present.
392
419
  */
393
- sourceEventSeqs?: number[];
420
+ sourceEventSeqs?: SessionSeq[];
394
421
  }
395
422
  /**
396
423
  * One immutable entry in the session log.
@@ -409,7 +436,7 @@ export type SessionEvent<T extends SessionEventType = SessionEventType> = {
409
436
  [K in SessionEventType]: {
410
437
  type: K;
411
438
  /** Monotonic sequence number within the session. */
412
- seq: number;
439
+ seq: SessionSeq;
413
440
  /** Unix epoch milliseconds. */
414
441
  time: number;
415
442
  data: SessionEventMap[K];
@@ -433,7 +460,7 @@ export type SessionEvent<T extends SessionEventType = SessionEventType> = {
433
460
  * provider stream; when the field is absent, the event does not record which
434
461
  * earlier events produced the message.
435
462
  */
436
- sourceEventSeqs?: number[];
463
+ sourceEventSeqs?: SessionSeq[];
437
464
  /** How this event entered the surface; absent for non-surface events. */
438
465
  surfaceOp?: SurfaceOp;
439
466
  } : object);
@@ -1,4 +1,4 @@
1
- import { brandString } from '@deepseek-ai/dsh-brand';
1
+ import { brandNumber, brandString } from '@deepseek-ai/dsh-brand';
2
2
  /**
3
3
  * Brand a string as a {@link SessionId}.
4
4
  * @param id - the raw session id string.
@@ -7,6 +7,28 @@ import { brandString } from '@deepseek-ai/dsh-brand';
7
7
  export function SessionId(id) {
8
8
  return brandString(id);
9
9
  }
10
+ /**
11
+ * Admit a numeric value as an existing Session event position.
12
+ * @param value - non-negative safe integer admitted by the owning log operation.
13
+ * @returns the same number with the Session-sequence brand.
14
+ */
15
+ export function SessionSeq(value) {
16
+ if (!Number.isSafeInteger(value) || value < 0 || Object.is(value, -0)) {
17
+ throw new TypeError(`SessionSeq must be a non-negative safe integer, got ${String(value)}`);
18
+ }
19
+ return brandNumber(value);
20
+ }
21
+ /**
22
+ * Admit a numeric value as a Session log offset.
23
+ * @param value - non-negative safe integer used as a gap or prefix length.
24
+ * @returns the same number with the Session-log-offset brand.
25
+ */
26
+ export function SessionLogOffset(value) {
27
+ if (!Number.isSafeInteger(value) || value < 0 || Object.is(value, -0)) {
28
+ throw new TypeError(`SessionLogOffset must be a non-negative safe integer, got ${String(value)}`);
29
+ }
30
+ return brandNumber(value);
31
+ }
10
32
  /**
11
33
  * The on-disk session format version, stamped into every newly-written {@link SessionHeader}
12
34
  * and enforced by every persistence backend on load. The single source of truth for the
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@deepseek-ai/dsh-session",
3
3
  "description": "Event-sourced session store for the DeepSeek Harness",
4
- "version": "0.1.2-alpha.2",
4
+ "version": "0.1.2-alpha.4",
5
5
  "publishConfig": {
6
6
  "access": "public"
7
7
  },
@@ -45,19 +45,19 @@
45
45
  ],
46
46
  "license": "MIT",
47
47
  "peerDependencies": {
48
- "@deepseek-ai/dsh-scope": "^0.1.2-alpha.2",
49
- "@deepseek-ai/cordis": "^4.0.2"
48
+ "@deepseek-ai/cordis": "^4.0.2",
49
+ "@deepseek-ai/dsh-scope": "^0.1.2-alpha.4"
50
50
  },
51
51
  "devDependencies": {
52
- "@deepseek-ai/dsh-scope": "^0.1.2-alpha.2",
53
- "@deepseek-ai/dsh-typert-protocol": "^0.1.2-alpha.2",
54
- "@deepseek-ai/dsh-invariants": "^0.1.2-alpha.2",
55
- "@deepseek-ai/cordis": "^4.0.2",
56
- "@deepseek-ai/dsh-typert-registry": "^0.1.2-alpha.2"
52
+ "@deepseek-ai/dsh-invariants": "^0.1.2-alpha.4",
53
+ "@deepseek-ai/dsh-scope": "^0.1.2-alpha.4",
54
+ "@deepseek-ai/dsh-typert-protocol": "^0.1.2-alpha.4",
55
+ "@deepseek-ai/dsh-typert-registry": "^0.1.2-alpha.4",
56
+ "@deepseek-ai/cordis": "^4.0.2"
57
57
  },
58
58
  "dependencies": {
59
- "@deepseek-ai/dsh-llm": "^0.1.2-alpha.2",
60
- "@deepseek-ai/dsh-brand": "^0.1.2-alpha.2",
61
- "@deepseek-ai/dsh-util-values": "^0.1.2-alpha.2"
59
+ "@deepseek-ai/dsh-llm": "^0.1.2-alpha.4",
60
+ "@deepseek-ai/dsh-brand": "^0.1.2-alpha.4",
61
+ "@deepseek-ai/dsh-util-values": "^0.1.2-alpha.4"
62
62
  }
63
63
  }