dsh-rewind-plugin 0.7.4 → 0.7.5

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.
@@ -7,30 +7,29 @@
7
7
  > compatibility invariants. A probe failure is a finding; it enters the
8
8
  > fix/pin/record loop.
9
9
  >
10
- > Targeted version: npm `@deepseek-ai/*@0.1.1-rc.2` (matches `package-lock.json`);
11
- > source reference: the `oss/deepseek-harness` local fork.
10
+ > Targeted version: npm `@deepseek-ai/*@0.1.1-rc.2` (matches `package-lock.json`).
11
+ > Source reference: the upstream [github.com/deepseek-ai/deepseek-harness](https://github.com/deepseek-ai/deepseek-harness).
12
12
  >
13
13
  > Version alignment: `peerDependencies` use an OR-union (e.g.
14
14
  > `^0.1.0-rc.6 || ^0.1.1-rc.2 || ^0.1.2-alpha.2`) covering each published tuple series. npm's
15
15
  > prerelease matching rules require a candidate to share the range comparator's
16
- > `[major, minor, patch]` tuple, so each new tuple series (e.g. a future
17
- > `0.1.2-rc.x`, `0.2.x`) requires appending a union member; rc rolling within a
18
- > tuple (`0.1.1-rc.2 → rc.3`) is a no-op. Signal: `npm view @deepseek-ai/dsh version`;
16
+ > `[major, minor, patch]` tuple, so appending is needed only for a genuinely new
17
+ > tuple (e.g. a future `0.2.x`); any prerelease within the SAME tuple (alpha rc)
18
+ > is a no-op. Signal: `npm view @deepseek-ai/dsh version`;
19
19
  > flow: `scripts/check-dsh-version.mjs` (it reads the `latest` dist-tag only; a
20
20
  > `-alpha` prerelease published under another tag, e.g. `0.1.2-alpha.2` under
21
21
  > `alpha`, is a manual pre-release check).
22
22
  >
23
23
  > `0.1.2-alpha.1` was never published to npm, so the peer OR-union is declared only from `0.1.2-alpha.2`; the plugin code still supports the `alpha.1`+ client.
24
24
  >
25
- > `0.1.2-alpha.2` … `0.1.2-alpha.5` verified-compatible. Built/tested on the rc.2
26
- > baseline (the `latest` dist-tag); the same published build also drives the alpha
27
- > line, and `alpha.2`/`alpha.3`/`alpha.4`/`alpha.5` share the `0.1.2` tuple, so the
28
- > single `^0.1.2-alpha.2` peer member covers all four. `rc.2` (`latest`) remains the
29
- > primary baseline; five versions verified: rc.2, alpha.2, alpha.3, alpha.4, alpha.5.
25
+ > `0.1.2-alpha.2` … `0.1.2-alpha.5` and `0.1.2-rc.1` verified-compatible; `rc.1` is
26
+ > source-identical to `alpha.5`. They share the `0.1.2` tuple, so the single
27
+ > `^0.1.2-alpha.2` peer member covers all six. `rc.2` (`latest`) stays the primary
28
+ > baseline; verified: rc.2, alpha.2, alpha.3, alpha.4, alpha.5, rc.1.
30
29
 
31
30
  ### Channeled seams (version × channel)
32
31
 
33
- | Seam | rc.2 (`0.1.1-rc.2`) | alpha.2 / alpha.3 | alpha.4 / alpha.5 |
32
+ | Seam | rc.2 (`0.1.1-rc.2`) | alpha.2 / alpha.3 | alpha.4 / alpha.5 / rc.1 |
34
33
  | --- | --- | --- | --- |
35
34
  | Host session log (`eventsOf`) | `Session.events` | `Session.events` | `session.snapshotEvents()` |
36
35
  | Client chat snapshot (`chatSnapshotOf`) | session-face `chat` field | `uiConversation` `chat` view | `uiConversation` `chat` view |
@@ -21,7 +21,7 @@ the plugin itself uses (it never reads the DOM or host copy):
21
21
  ```ts
22
22
  import { hiddenSeqsOf, type HiddenChat } from 'dsh-rewind-plugin/client'
23
23
 
24
- const chat = session.getSnapshot().chat // rc.2 source; 0.1.2-alpha.1+ uses the uiConversation "chat" view
24
+ const chat = session.getSnapshot().chat // rc.2 source; 0.1.2-rc.1 uses the uiConversation "chat" view
25
25
  const hidden = hiddenSeqsOf(chat as HiddenChat) // Set<number> of anchor seqs
26
26
  ```
27
27
 
@@ -20,7 +20,7 @@
20
20
  ```ts
21
21
  import { hiddenSeqsOf, type HiddenChat } from 'dsh-rewind-plugin/client'
22
22
 
23
- const chat = session.getSnapshot().chat // rc.2 来源;0.1.2-alpha.1+ 用 uiConversation "chat" 视图
23
+ const chat = session.getSnapshot().chat // rc.2 来源;0.1.2-rc.1 用 uiConversation "chat" 视图
24
24
  const hidden = hiddenSeqsOf(chat as HiddenChat) // 被隐藏的 anchor seq 集合
25
25
  ```
26
26
 
@@ -1,8 +1,7 @@
1
1
  # DeepSeek Harness interface reference
2
2
 
3
3
  > Maintainer doc: the harness subsystems this plugin depends on, and the key
4
- > source files behind each interface. Local fork (if present):
5
- > `<workspace>/oss/deepseek-harness/` — official repo:
4
+ > source files behind each interface. Official repo:
6
5
  > [github.com/deepseek-ai/deepseek-harness](https://github.com/deepseek-ai/deepseek-harness)
7
6
 
8
7
  ## Subsystem docs (`docs/subsystems/`)
package/lib/client.js CHANGED
@@ -329,11 +329,11 @@ var STYLE = `
329
329
 
330
330
  /* ---- Snapshot-cleanup settings card (mirrors the harness PluginCard look) ---- */
331
331
  /* Dual-channel note: the harness card corner/border drifted across versions \u2014
332
- rc.2 uses border-radius 12px + 1px solid border-l2, while alpha uses 16px +
333
- 0.5px border-l4 (and adds corner-shape: round). We intentionally keep the
334
- rc.2 values here for now; if the alpha look is wanted, switch these on the
335
- host version like the other dual-channel surfaces (see the host-version probe
336
- in src/client/index.ts). */
332
+ 0.1.1-rc.2 uses border-radius 12px + 1px solid border-l2, while 0.1.2-rc.1
333
+ uses 16px + 0.5px border-l4 (and adds corner-shape: round). We intentionally
334
+ keep the 0.1.1-rc.2 values here for now; if the 0.1.2-rc.1 look is wanted,
335
+ switch these on the host version like the other dual-channel surfaces (see the
336
+ host-version probe in src/client/index.ts). */
337
337
  .dsh-rewind-cleanup-card {
338
338
  list-style: none;
339
339
  border: 1px solid var(--dsw-alias-border-l2);
@@ -1116,8 +1116,9 @@ function actionsContainerOf(row) {
1116
1116
  const root = row?.matches(ACTIONS_ROOT_SELECTOR) ? row : row?.querySelector(ACTIONS_ROOT_SELECTOR);
1117
1117
  const actions = root?.lastElementChild;
1118
1118
  if (actions instanceof HTMLElement && actions.querySelector("button") !== null) return actions;
1119
- const copy = row?.querySelector("button");
1120
- const structural = copy?.parentElement;
1119
+ const buttons = Array.from(row?.querySelectorAll("button") ?? []);
1120
+ const lastButton = buttons.filter((button) => !button.classList.contains(CLASS.button)).at(-1);
1121
+ const structural = lastButton?.parentElement;
1121
1122
  if (structural instanceof HTMLElement && structural.querySelector("button") !== null) return structural;
1122
1123
  return void 0;
1123
1124
  }
@@ -1356,8 +1357,8 @@ function createRewindBridge(deps) {
1356
1357
  }
1357
1358
 
1358
1359
  // src/client/build-info.ts
1359
- var PLUGIN_VERSION = true ? "0.7.4" : "dev";
1360
- var BUILD_HASH = true ? "73e01232" : "dev";
1360
+ var PLUGIN_VERSION = true ? "0.7.5" : "dev";
1361
+ var BUILD_HASH = true ? "25e8b3ca" : "dev";
1361
1362
 
1362
1363
  // src/client/locales.ts
1363
1364
  var zh = {
@@ -14,11 +14,12 @@ export interface HiddenChat {
14
14
  };
15
15
  }
16
16
  /**
17
- * Reader for one session's live chat snapshot. The dual channel hides the
18
- * harness split behind SiriLee/dsh-rewind#7: rc.2 serves the chat from the
19
- * session face snapshot, while 0.1.2-alpha.1+ serves it from the
20
- * `uiConversation` service's named "chat" view (contributed by
21
- * dsh-client-ui-chat through the uiSession slot hook).
17
+ * Reader for one session's live chat snapshot. This is one of the plugin's
18
+ * "0.1.1-rc.2 0.1.2-rc.1" dual channels: 0.1.1-rc.2 serves the chat from the
19
+ * session face snapshot, while 0.1.2-rc.1 (and the whole 0.1.2 line) serves it
20
+ * from the `uiConversation` service's named "chat" view (contributed by
21
+ * dsh-client-ui-chat through the uiSession slot hook). See
22
+ * SiriLee/dsh-rewind#7.
22
23
  */
23
24
  export type ChatOf = (session: {
24
25
  readonly sessionId: string;
@@ -29,17 +30,18 @@ export type ChatOf = (session: {
29
30
  /**
30
31
  * Subscribe to one session's live chat-update signal, for waiting on a chat
31
32
  * snapshot change without polling. Dual-channel, mirroring `chatOf`: the
32
- * alpha.1+ `uiConversation` "chat" view when registered, else the session face
33
- * (rc.2, whose snapshot still carries `chat`, so its own `subscribe` is the
34
- * chat-update signal). `cb` fires whenever the chat snapshot invalidates.
33
+ * 0.1.2-rc.1 `uiConversation` "chat" view when registered, else the session
34
+ * face (0.1.1-rc.2, whose snapshot still carries `chat`, so its own
35
+ * `subscribe` is the chat-update signal). `cb` fires whenever the chat
36
+ * snapshot invalidates.
35
37
  */
36
38
  export type ChatWatch = (sessionId: string, cb: () => void) => () => void;
37
39
  /**
38
40
  * Choose the chat-update subscription for `waitForCommand`: prefer the
39
- * `uiConversation` "chat" view's own `subscribe` when available (alpha.1+,
41
+ * `uiConversation` "chat" view's own `subscribe` when available (0.1.2-rc.1,
40
42
  * where the chat-update signal lives), else the session face's `subscribe`
41
- * (rc.2, whose snapshot still carries the chat, so its own subscribe is the
42
- * chat-update signal). Extracted as a pure channel-selection step so the
43
+ * (0.1.1-rc.2, whose snapshot still carries the chat, so its own subscribe is
44
+ * the chat-update signal). Extracted as a pure channel-selection step so the
43
45
  * "view vs face" branch is unit-testable; the resolvers are injected by the
44
46
  * caller (see `watchChat` in index.ts). Never throws.
45
47
  */
@@ -50,11 +52,11 @@ export declare function resolveChatWatch(resolveView: (sessionId: string) => {
50
52
  } | undefined, sessionId: string, cb: () => void): () => void;
51
53
  /**
52
54
  * Resolve the chat snapshot across the two harness channels: the session-face
53
- * snapshot first (rc.2 — on alpha.1+ the face no longer carries `chat`, so the
54
- * field reads `undefined`), then the `uiConversation` "chat" view. The view's
55
- * `getSnapshot()` returns undefined until the named view is registered, so
56
- * both channels missing degrades to `undefined` (no targets, no hiding —
57
- * never a crash).
55
+ * snapshot first (0.1.1-rc.2 — on 0.1.2-rc.1 the face no longer carries
56
+ * `chat`, so the field reads `undefined`), then the `uiConversation` "chat"
57
+ * view. The view's `getSnapshot()` returns undefined until the named view is
58
+ * registered, so both channels missing degrades to `undefined` (no targets, no
59
+ * hiding — never a crash).
58
60
  */
59
61
  export declare function chatSnapshotOf(face: {
60
62
  getSnapshot(): {
@@ -33,14 +33,14 @@ export interface PopoverOptions {
33
33
  readonly onRetract?: () => void;
34
34
  readonly preview: string;
35
35
  /**
36
- * Dual-channel chat reader (rc.2 session face / alpha.1+ uiConversation
37
- * view): the durable variant's command probes scan the chat through it.
38
- * Unused by the pending-retract variant.
36
+ * Dual-channel chat reader (0.1.1-rc.2 session face / 0.1.2-rc.1
37
+ * uiConversation view): the durable variant's command probes scan the chat
38
+ * through it. Unused by the pending-retract variant.
39
39
  */
40
40
  readonly chatOf: ChatOf;
41
41
  /**
42
42
  * Subscribe to one session's live chat-update signal, so a probe waiting on
43
- * a command's chat node can be woken when the chat snapshot changes (alpha.1+
43
+ * a command's chat node can be woken when the chat snapshot changes (0.1.2-rc.1
44
44
  * the session face no longer fires on a chat update). Passed straight through
45
45
  * to `waitForCommand`.
46
46
  */
@@ -53,15 +53,15 @@ export type PortalTarget = {
53
53
  export interface RewindBridgeDeps {
54
54
  readonly sessionOf: (sessionId: string) => SessionFace | undefined;
55
55
  /**
56
- * Dual-channel chat reader (rc.2 session face / alpha.1+ uiConversation
57
- * "chat" view): every chat snapshot read goes through it. See
56
+ * Dual-channel chat reader (0.1.1-rc.2 session face / 0.1.2-rc.1
57
+ * uiConversation "chat" view): every chat snapshot read goes through it. See
58
58
  * `chatSnapshotOf` in hidden.ts for the channel precedence.
59
59
  */
60
60
  readonly chatOf: ChatOf;
61
61
  /**
62
62
  * Subscribe to one session's live chat-update signal, so the composer refill
63
63
  * waiting on an executed rewind's chat node can be woken when the chat
64
- * snapshot changes (alpha.1+ the session face no longer fires on a chat
64
+ * snapshot changes (0.1.2-rc.1 the session face no longer fires on a chat
65
65
  * update). Passed through to `waitForCommand`.
66
66
  */
67
67
  readonly watchChat: ChatWatch;
@@ -70,9 +70,9 @@ export interface RewindBridgeDeps {
70
70
  readonly subscribeLocale: (cb: () => void) => () => void;
71
71
  /**
72
72
  * Session-aware dual-channel composer writer (see `writeComposer`): the
73
- * alpha.1+ `conversation.input` facade `setDraft` when reachable, else the
74
- * rc.2/alpha.1 DOM fill. Session-scoped so the refill only lands in the
75
- * session that just rewound.
73
+ * 0.1.2-rc.1 `conversation.input` facade `setDraft` when reachable, else the
74
+ * 0.1.1-rc.2/0.1.2-rc.1 DOM fill. Session-scoped so the refill only lands in
75
+ * the session that just rewound.
76
76
  */
77
77
  readonly setComposerText: (sessionId: string, text: string) => boolean;
78
78
  }
@@ -90,7 +90,7 @@ export interface SlotsLike {
90
90
  }
91
91
  /** Join the text blocks of a user message into one plain preview. */
92
92
  /**
93
- * The alpha.1+ session input facade's write face (structural, so the plugin
93
+ * The 0.1.2-rc.1 session input facade's write face (structural, so the plugin
94
94
  * never imports the conversation UI package). `setDraft` replaces the whole
95
95
  * composer draft through the harness's own Lexical editor — the correct way
96
96
  * to restore the withdrawn text.
@@ -99,8 +99,8 @@ interface ComposerDraftWriter {
99
99
  setDraft(text: string): void;
100
100
  }
101
101
  /**
102
- * Fill the dsh composer with `text`. DOM dual-channel fallback: the rc.2
103
- * `<textarea>` path, then the alpha.1+ `contenteditable` path. Used by
102
+ * Fill the dsh composer with `text`. DOM dual-channel fallback: the 0.1.1-rc.2
103
+ * `<textarea>` path, then the 0.1.2-rc.1 `contenteditable` path. Used by
104
104
  * `setComposerText` (the harness-facade-aware writer) as the last-resort and
105
105
  * by `runRewindAndFill` to put the withdrawn target message back into the
106
106
  * composer after a rewind. Best-effort — no composer match means false,
@@ -109,12 +109,12 @@ interface ComposerDraftWriter {
109
109
  export declare function fillComposer(text: string): boolean;
110
110
  /**
111
111
  * Dual-channel composer write, mirroring `chatSnapshotOf`: prefer the harness
112
- * facade's `setDraft` (alpha.1+, correct whole-draft replace), then degrade
113
- * to the DOM `fillComposer` (rc.2 textarea / alpha.1 contenteditable). A
114
- * facade that throws (session teardown) is treated as absent so the DOM path
112
+ * facade's `setDraft` (0.1.2-rc.1, correct whole-draft replace), then degrade
113
+ * to the DOM `fillComposer` (0.1.1-rc.2 textarea / 0.1.2-rc.1 contenteditable).
114
+ * A facade that throws (session teardown) is treated as absent so the DOM path
115
115
  * still restores the text. Never throws.
116
116
  * @param text - the withdrawn target message text.
117
- * @param facade - the alpha.1+ session input draft writer, when reachable.
117
+ * @param facade - the 0.1.2-rc.1 session input draft writer, when reachable.
118
118
  * @returns whether a channel applied the text.
119
119
  */
120
120
  export declare function writeComposer(text: string, facade: ComposerDraftWriter | undefined): boolean;
@@ -136,17 +136,20 @@ export declare function runRewindAndFill(session: SessionFace, seq: number, mode
136
136
  * Locate the actions container of a user/steering seat row — the element the
137
137
  * ↶ button portals into (the copy/branch IconActions row).
138
138
  *
139
- * Dual channel:
140
- * - rc.2 (0.1.1-rc.2) / alpha.2+ (0.1.2-alpha.2): the hover-reveal root is
141
- * attribute-marked (`[data-time-hover-root]` rc.x, `[data-actions-reveal]`
142
- * alpha.2+) and mounts the actions row as its LAST child. A pending row IS
143
- * that root; a durable row CONTAINS it as a descendant.
144
- * - alpha.4 (0.1.2-alpha.4): the marker was removed from user rows (it now
145
- * lives only on the per-turn tail footer, `TurnTailNodeView`), and the user
146
- * action row is revealed via CSS `:has()`. The container is instead located
147
- * structurally: the direct holder of the copy `<button>` (the
148
- * `MessageIconActions` container, which mounts that button as a direct
149
- * child — `MessageIconActions.tsx:83,86`).
139
+ * @dualmode 0.1.1-rc.2 ↔ 0.1.2-rc.1
140
+ * - 0.1.1-rc.2: the hover-reveal root is attribute-marked
141
+ * `[data-time-hover-root]` and mounts the actions row as its LAST child. A
142
+ * pending row IS that root; a durable row CONTAINS it as a descendant.
143
+ * - 0.1.2-rc.1: the marker was removed from user rows (it now lives only on the
144
+ * per-turn tail footer, `TurnTailNodeView`), and the user action row is
145
+ * revealed via CSS `:has()`. The container is instead located structurally:
146
+ * the direct holder of the copy `<button>` (the `MessageIconActions`
147
+ * container, which mounts that button as a direct child —
148
+ * `MessageIconActions.tsx:83,86`).
149
+ *
150
+ * The 0.1.2-alpha.2/3 `[data-actions-reveal]` attribute-marked rows (see
151
+ * `ACTIONS_ROOT_SELECTOR`) are an intermediate state absorbed by the
152
+ * attribute branch below; they are not needed by either endpoint.
150
153
  *
151
154
  * Returns undefined when no qualifying container is found; the caller refuses
152
155
  * to portal (never a crash, never a wrong attachment). Exported as a test seam
@@ -171,9 +174,10 @@ interface RewindPortalsProps extends RewindBridgeDeps {
171
174
  * synchronous full-transcript scan inside a commit microtask.
172
175
  */
173
176
  export declare function RewindPortals({ sessionId, sessionOf, chatOf, currentSessionId, watchChat, t, subscribeLocale, setComposerText }: RewindPortalsProps): ReactNode;
174
- /** The current composer draft, on whichever channel: rc.2 textarea `.value`,
175
- * alpha.1+ contenteditable `textContent`. Empty when the composer is absent.
176
- * Exported as a test seam (the empty-composer guard in `retractPending`). */
177
+ /** The current composer draft, on whichever channel: 0.1.1-rc.2 textarea
178
+ * `.value`, 0.1.2-rc.1 contenteditable `textContent`. Empty when the composer
179
+ * is absent. Exported as a test seam (the empty-composer guard in
180
+ * `retractPending`). */
177
181
  export declare function composerText(): string;
178
182
  /**
179
183
  * Build the slot-entry component for the plugin apply(): a tiny bridge that
@@ -11,10 +11,11 @@
11
11
  * host schema enforces). "Discard changes" restores the last-read baseline.
12
12
  *
13
13
  * It neither imports the client settings typed contract nor depends on the
14
- * alpha-only `mutate` write API: it reads `getSnapshot().value` and writes via
15
- * the `set(field, value)` method present on both rc.2 and alpha, and the card
16
- * receives a tiny structural `CleanupCardApi` supplied by `src/client/index.ts`
17
- * so the component stays harness-agnostic and unit-testable in isolation.
14
+ * 0.1.2-rc.1-only `mutate` write API: it reads `getSnapshot().value` and writes
15
+ * via the `set(field, value)` method present on both 0.1.1-rc.2 and 0.1.2-rc.1,
16
+ * and the card receives a tiny structural `CleanupCardApi` supplied by
17
+ * `src/client/index.ts` so the component stays harness-agnostic and
18
+ * unit-testable in isolation.
18
19
  *
19
20
  * @module dsh-rewind/client/settings-card
20
21
  */
@@ -23,4 +23,4 @@ export declare const CLASS: {
23
23
  /** The ↶ glyph, drawn inline so the bundle stays dependency-free. */
24
24
  export declare const REWIND_ICON_SVG: string;
25
25
  /** One injected stylesheet (scoped under `.dsh-rewind-*`). */
26
- export declare const STYLE = "\n.dsh-rewind-btn {\n display: inline-flex;\n align-items: center;\n justify-content: center;\n width: 28px;\n height: 28px;\n padding: 6px;\n border: none;\n border-radius: 28px;\n background: transparent;\n color: var(--dsw-alias-label-tertiary);\n cursor: pointer;\n}\n.dsh-rewind-btn:hover {\n background: var(--dsw-alias-interactive-bg-hover);\n color: var(--dsw-alias-label-secondary);\n}\n\n.dsh-rewind-popover {\n position: fixed;\n z-index: 1000;\n width: 288px;\n padding: 12px;\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 12px;\n background: var(--dsw-specific-menu, var(--dsw-alias-bg-layer-3));\n box-shadow: var(--dsw-shadow-lv3);\n font-size: 14px;\n line-height: 20px;\n color: var(--dsw-alias-label-primary);\n}\n.dsh-rewind-popover-title {\n font-size: 14px;\n font-weight: 600;\n line-height: 20px;\n}\n.dsh-rewind-popover-target {\n margin: 4px 0 10px;\n font-size: 12px;\n line-height: 16px;\n color: var(--dsw-alias-label-tertiary);\n word-break: break-all;\n}\n.dsh-rewind-popover-option {\n display: flex;\n flex-direction: column;\n gap: 2px;\n width: 100%;\n margin: 0 0 6px;\n padding: 8px 10px;\n border: 1px solid transparent;\n border-radius: 8px;\n background: transparent;\n color: inherit;\n font: inherit;\n text-align: left;\n cursor: pointer;\n}\n.dsh-rewind-popover-option:hover {\n background: var(--dsw-alias-interactive-bg-hover);\n}\n.dsh-rewind-popover-option:disabled {\n opacity: 0.5;\n cursor: default;\n}\n.dsh-rewind-popover-option-label {\n font-weight: 500;\n}\n.dsh-rewind-popover-option-hint {\n font-size: 12px;\n line-height: 16px;\n color: var(--dsw-alias-label-tertiary);\n}\n.dsh-rewind-popover-impact {\n margin: 4px 0 10px;\n padding: 8px 10px;\n border-radius: 8px;\n background: var(--dsw-alias-interactive-bg-hover);\n font-size: 12px;\n line-height: 16px;\n color: var(--dsw-alias-label-secondary);\n white-space: pre-wrap;\n max-height: 160px;\n overflow: auto;\n}\n.dsh-rewind-popover-actions {\n display: flex;\n justify-content: flex-end;\n gap: 8px;\n}\n.dsh-rewind-popover-primary,\n.dsh-rewind-popover-ghost {\n padding: 5px 12px;\n border: none;\n border-radius: 8px;\n font: inherit;\n font-size: 13px;\n line-height: 18px;\n cursor: pointer;\n}\n.dsh-rewind-popover-primary {\n background: var(--dsw-alias-button-primary-fill);\n color: var(--dsw-alias-label-primary-foreground);\n}\n.dsh-rewind-popover-primary:hover:not(:disabled) {\n background: var(--dsw-alias-button-primary-hover);\n}\n.dsh-rewind-popover-primary:disabled {\n opacity: 0.5;\n cursor: default;\n}\n.dsh-rewind-popover-ghost {\n background: transparent;\n color: var(--dsw-alias-label-secondary);\n}\n.dsh-rewind-popover-ghost:hover {\n background: var(--dsw-alias-interactive-bg-hover);\n}\n\n.dsh-rewind-guard-hint {\n position: fixed;\n z-index: 1000;\n max-width: min(440px, calc(100vw - 24px));\n padding: 8px 12px;\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 10px;\n background: var(--dsw-specific-menu, var(--dsw-alias-bg-layer-3));\n box-shadow: var(--dsw-shadow-lv3);\n font-size: 13px;\n line-height: 18px;\n color: var(--dsw-alias-label-primary);\n pointer-events: none;\n}\n\n/* ---- Snapshot-cleanup settings card (mirrors the harness PluginCard look) ---- */\n/* Dual-channel note: the harness card corner/border drifted across versions \u2014\n rc.2 uses border-radius 12px + 1px solid border-l2, while alpha uses 16px +\n 0.5px border-l4 (and adds corner-shape: round). We intentionally keep the\n rc.2 values here for now; if the alpha look is wanted, switch these on the\n host version like the other dual-channel surfaces (see the host-version probe\n in src/client/index.ts). */\n.dsh-rewind-cleanup-card {\n list-style: none;\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 12px;\n background: var(--dsw-alias-bg-layer-3);\n transition: border-color .16s, background .16s;\n}\n.dsh-rewind-cleanup-card:hover {\n border-color: var(--dsw-alias-label-dimmed);\n}\n.dsh-rewind-cleanup-card-open {\n background: var(--dsw-alias-bg-layer-2);\n border-color: var(--dsw-alias-label-dimmed);\n}\n.dsh-rewind-cleanup-header {\n width: 100%;\n appearance: none;\n border: 0;\n background: none;\n font: inherit;\n color: inherit;\n text-align: left;\n cursor: pointer;\n display: flex;\n align-items: center;\n gap: 12px;\n padding: 14px 16px;\n border-radius: 12px;\n}\n.dsh-rewind-cleanup-header:focus-visible {\n outline: 2px solid var(--dsw-alias-brand-primary);\n outline-offset: -2px;\n}\n.dsh-rewind-cleanup-head-text {\n flex: 1;\n min-width: 0;\n display: flex;\n flex-direction: column;\n gap: 4px;\n}\n.dsh-rewind-cleanup-name {\n font-size: 15px;\n font-weight: 600;\n line-height: 1.4;\n color: var(--dsw-alias-label-primary);\n}\n.dsh-rewind-cleanup-desc {\n font-size: 13px;\n line-height: 1.5;\n color: var(--dsw-alias-label-tertiary);\n}\n.dsh-rewind-cleanup-chevron {\n flex: none;\n color: var(--dsw-alias-label-tertiary);\n transition: transform .16s;\n}\n.dsh-rewind-cleanup-chevron-open {\n transform: rotate(180deg);\n}\n.dsh-rewind-cleanup-pending {\n flex: none;\n border-radius: 999px;\n padding: 1px 8px;\n font-size: 11px;\n line-height: 17px;\n font-weight: 500;\n white-space: nowrap;\n background: var(--dsw-alias-bg-module-platform);\n color: var(--dsw-alias-label-secondary);\n}\n.dsh-rewind-cleanup-body {\n border-top: 1px solid var(--dsw-alias-border-l2);\n margin: 0 16px;\n padding: 4px 0 8px;\n}\n.dsh-rewind-cleanup-readonly {\n margin: 12px 0 0;\n font-size: 12px;\n line-height: 1.5;\n color: var(--dsw-alias-label-tertiary);\n}\n.dsh-rewind-cleanup-permission {\n display: grid;\n gap: 6px;\n padding: 12px 0;\n}\n.dsh-rewind-cleanup-field {\n display: flex;\n flex-direction: column;\n gap: 6px;\n padding: 12px 0;\n}\n.dsh-rewind-cleanup-field + .dsh-rewind-cleanup-field {\n border-top: 1px solid var(--dsw-alias-border-l2);\n}\n.dsh-rewind-cleanup-head {\n display: flex;\n align-items: center;\n gap: 8px;\n}\n.dsh-rewind-cleanup-label {\n flex: 1;\n min-width: 0;\n font-size: 13px;\n font-weight: 500;\n line-height: 1.5;\n color: var(--dsw-alias-label-primary);\n}\n.dsh-rewind-cleanup-hint {\n margin: 0;\n font-size: 12px;\n line-height: 1.5;\n color: var(--dsw-alias-label-tertiary);\n}\n.dsh-rewind-cleanup-error {\n margin: 0;\n font-size: 12px;\n line-height: 1.5;\n color: var(--dsw-alias-label-error);\n}\n/* Switch row: label left, role=switch button right, hint below (Subagent module). */\n.dsh-rewind-cleanup-toggle-row {\n display: flex;\n align-items: flex-start;\n justify-content: space-between;\n gap: 16px;\n font-size: 13px;\n line-height: 1.5;\n color: var(--dsw-alias-label-primary);\n}\n.dsh-rewind-cleanup-toggle-label {\n flex: 1;\n min-width: 0;\n}\n.dsh-rewind-cleanup-switch {\n box-sizing: border-box;\n position: relative;\n flex: 0 0 auto;\n width: 36px;\n height: 20px;\n padding: 2px;\n border: 0;\n border-radius: 10px;\n background: var(--dsw-alias-border-l3);\n cursor: pointer;\n}\n.dsh-rewind-cleanup-switch-on {\n background: var(--dsw-alias-brand-primary);\n}\n.dsh-rewind-cleanup-switch:disabled {\n cursor: default;\n opacity: 0.5;\n}\n.dsh-rewind-cleanup-switch:focus-visible {\n outline: 2px solid var(--dsw-alias-brand-primary);\n outline-offset: 2px;\n}\n.dsh-rewind-cleanup-thumb {\n display: block;\n width: 16px;\n height: 16px;\n border-radius: 50%;\n corner-shape: round;\n background: var(--dsw-alias-label-primary-foreground);\n transition: transform 120ms ease;\n}\n.dsh-rewind-cleanup-switch-on .dsh-rewind-cleanup-thumb {\n transform: translateX(16px);\n}\n.dsh-rewind-cleanup-input {\n box-sizing: border-box;\n height: 34px;\n padding: 0 12px;\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 8px;\n background: var(--dsw-alias-bg-layer-3);\n font: inherit;\n font-size: 13px;\n line-height: 1.5;\n color: var(--dsw-alias-label-primary);\n}\n.dsh-rewind-cleanup-input:focus-visible {\n outline: none;\n border-color: var(--dsw-alias-brand-primary);\n}\n.dsh-rewind-cleanup-input:disabled {\n color: var(--dsw-alias-label-tertiary);\n cursor: default;\n}\n.dsh-rewind-cleanup-input-invalid {\n border-color: var(--dsw-alias-label-error);\n}\n.dsh-rewind-cleanup-footer {\n display: flex;\n align-items: center;\n justify-content: flex-end;\n gap: 8px;\n padding: 12px 0 4px;\n border-top: 1px solid var(--dsw-alias-border-l2);\n}\n.dsh-rewind-cleanup-failed {\n flex: 1;\n min-width: 0;\n margin: 0;\n font-size: 12px;\n line-height: 1.5;\n color: var(--dsw-alias-label-error);\n}\n.dsh-rewind-cleanup-discard,\n.dsh-rewind-cleanup-save {\n appearance: none;\n border: 1px solid transparent;\n border-radius: 8px;\n padding: 5px 14px;\n font: inherit;\n font-size: 13px;\n line-height: 1.5;\n cursor: pointer;\n}\n.dsh-rewind-cleanup-discard {\n border-color: var(--dsw-alias-border-l2);\n background: none;\n color: var(--dsw-alias-label-secondary);\n}\n.dsh-rewind-cleanup-discard:hover:not(:disabled) {\n color: var(--dsw-alias-label-primary);\n border-color: var(--dsw-alias-label-dimmed);\n}\n.dsh-rewind-cleanup-save {\n background: var(--dsw-alias-label-primary);\n color: var(--dsw-alias-bg-layer-3);\n}\n.dsh-rewind-cleanup-discard:disabled,\n.dsh-rewind-cleanup-save:disabled {\n opacity: 0.4;\n cursor: default;\n}\n.dsh-rewind-cleanup-discard:focus-visible,\n.dsh-rewind-cleanup-save:focus-visible {\n outline: 2px solid var(--dsw-alias-brand-primary);\n outline-offset: 1px;\n}\n";
26
+ export declare const STYLE = "\n.dsh-rewind-btn {\n display: inline-flex;\n align-items: center;\n justify-content: center;\n width: 28px;\n height: 28px;\n padding: 6px;\n border: none;\n border-radius: 28px;\n background: transparent;\n color: var(--dsw-alias-label-tertiary);\n cursor: pointer;\n}\n.dsh-rewind-btn:hover {\n background: var(--dsw-alias-interactive-bg-hover);\n color: var(--dsw-alias-label-secondary);\n}\n\n.dsh-rewind-popover {\n position: fixed;\n z-index: 1000;\n width: 288px;\n padding: 12px;\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 12px;\n background: var(--dsw-specific-menu, var(--dsw-alias-bg-layer-3));\n box-shadow: var(--dsw-shadow-lv3);\n font-size: 14px;\n line-height: 20px;\n color: var(--dsw-alias-label-primary);\n}\n.dsh-rewind-popover-title {\n font-size: 14px;\n font-weight: 600;\n line-height: 20px;\n}\n.dsh-rewind-popover-target {\n margin: 4px 0 10px;\n font-size: 12px;\n line-height: 16px;\n color: var(--dsw-alias-label-tertiary);\n word-break: break-all;\n}\n.dsh-rewind-popover-option {\n display: flex;\n flex-direction: column;\n gap: 2px;\n width: 100%;\n margin: 0 0 6px;\n padding: 8px 10px;\n border: 1px solid transparent;\n border-radius: 8px;\n background: transparent;\n color: inherit;\n font: inherit;\n text-align: left;\n cursor: pointer;\n}\n.dsh-rewind-popover-option:hover {\n background: var(--dsw-alias-interactive-bg-hover);\n}\n.dsh-rewind-popover-option:disabled {\n opacity: 0.5;\n cursor: default;\n}\n.dsh-rewind-popover-option-label {\n font-weight: 500;\n}\n.dsh-rewind-popover-option-hint {\n font-size: 12px;\n line-height: 16px;\n color: var(--dsw-alias-label-tertiary);\n}\n.dsh-rewind-popover-impact {\n margin: 4px 0 10px;\n padding: 8px 10px;\n border-radius: 8px;\n background: var(--dsw-alias-interactive-bg-hover);\n font-size: 12px;\n line-height: 16px;\n color: var(--dsw-alias-label-secondary);\n white-space: pre-wrap;\n max-height: 160px;\n overflow: auto;\n}\n.dsh-rewind-popover-actions {\n display: flex;\n justify-content: flex-end;\n gap: 8px;\n}\n.dsh-rewind-popover-primary,\n.dsh-rewind-popover-ghost {\n padding: 5px 12px;\n border: none;\n border-radius: 8px;\n font: inherit;\n font-size: 13px;\n line-height: 18px;\n cursor: pointer;\n}\n.dsh-rewind-popover-primary {\n background: var(--dsw-alias-button-primary-fill);\n color: var(--dsw-alias-label-primary-foreground);\n}\n.dsh-rewind-popover-primary:hover:not(:disabled) {\n background: var(--dsw-alias-button-primary-hover);\n}\n.dsh-rewind-popover-primary:disabled {\n opacity: 0.5;\n cursor: default;\n}\n.dsh-rewind-popover-ghost {\n background: transparent;\n color: var(--dsw-alias-label-secondary);\n}\n.dsh-rewind-popover-ghost:hover {\n background: var(--dsw-alias-interactive-bg-hover);\n}\n\n.dsh-rewind-guard-hint {\n position: fixed;\n z-index: 1000;\n max-width: min(440px, calc(100vw - 24px));\n padding: 8px 12px;\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 10px;\n background: var(--dsw-specific-menu, var(--dsw-alias-bg-layer-3));\n box-shadow: var(--dsw-shadow-lv3);\n font-size: 13px;\n line-height: 18px;\n color: var(--dsw-alias-label-primary);\n pointer-events: none;\n}\n\n/* ---- Snapshot-cleanup settings card (mirrors the harness PluginCard look) ---- */\n/* Dual-channel note: the harness card corner/border drifted across versions \u2014\n 0.1.1-rc.2 uses border-radius 12px + 1px solid border-l2, while 0.1.2-rc.1\n uses 16px + 0.5px border-l4 (and adds corner-shape: round). We intentionally\n keep the 0.1.1-rc.2 values here for now; if the 0.1.2-rc.1 look is wanted,\n switch these on the host version like the other dual-channel surfaces (see the\n host-version probe in src/client/index.ts). */\n.dsh-rewind-cleanup-card {\n list-style: none;\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 12px;\n background: var(--dsw-alias-bg-layer-3);\n transition: border-color .16s, background .16s;\n}\n.dsh-rewind-cleanup-card:hover {\n border-color: var(--dsw-alias-label-dimmed);\n}\n.dsh-rewind-cleanup-card-open {\n background: var(--dsw-alias-bg-layer-2);\n border-color: var(--dsw-alias-label-dimmed);\n}\n.dsh-rewind-cleanup-header {\n width: 100%;\n appearance: none;\n border: 0;\n background: none;\n font: inherit;\n color: inherit;\n text-align: left;\n cursor: pointer;\n display: flex;\n align-items: center;\n gap: 12px;\n padding: 14px 16px;\n border-radius: 12px;\n}\n.dsh-rewind-cleanup-header:focus-visible {\n outline: 2px solid var(--dsw-alias-brand-primary);\n outline-offset: -2px;\n}\n.dsh-rewind-cleanup-head-text {\n flex: 1;\n min-width: 0;\n display: flex;\n flex-direction: column;\n gap: 4px;\n}\n.dsh-rewind-cleanup-name {\n font-size: 15px;\n font-weight: 600;\n line-height: 1.4;\n color: var(--dsw-alias-label-primary);\n}\n.dsh-rewind-cleanup-desc {\n font-size: 13px;\n line-height: 1.5;\n color: var(--dsw-alias-label-tertiary);\n}\n.dsh-rewind-cleanup-chevron {\n flex: none;\n color: var(--dsw-alias-label-tertiary);\n transition: transform .16s;\n}\n.dsh-rewind-cleanup-chevron-open {\n transform: rotate(180deg);\n}\n.dsh-rewind-cleanup-pending {\n flex: none;\n border-radius: 999px;\n padding: 1px 8px;\n font-size: 11px;\n line-height: 17px;\n font-weight: 500;\n white-space: nowrap;\n background: var(--dsw-alias-bg-module-platform);\n color: var(--dsw-alias-label-secondary);\n}\n.dsh-rewind-cleanup-body {\n border-top: 1px solid var(--dsw-alias-border-l2);\n margin: 0 16px;\n padding: 4px 0 8px;\n}\n.dsh-rewind-cleanup-readonly {\n margin: 12px 0 0;\n font-size: 12px;\n line-height: 1.5;\n color: var(--dsw-alias-label-tertiary);\n}\n.dsh-rewind-cleanup-permission {\n display: grid;\n gap: 6px;\n padding: 12px 0;\n}\n.dsh-rewind-cleanup-field {\n display: flex;\n flex-direction: column;\n gap: 6px;\n padding: 12px 0;\n}\n.dsh-rewind-cleanup-field + .dsh-rewind-cleanup-field {\n border-top: 1px solid var(--dsw-alias-border-l2);\n}\n.dsh-rewind-cleanup-head {\n display: flex;\n align-items: center;\n gap: 8px;\n}\n.dsh-rewind-cleanup-label {\n flex: 1;\n min-width: 0;\n font-size: 13px;\n font-weight: 500;\n line-height: 1.5;\n color: var(--dsw-alias-label-primary);\n}\n.dsh-rewind-cleanup-hint {\n margin: 0;\n font-size: 12px;\n line-height: 1.5;\n color: var(--dsw-alias-label-tertiary);\n}\n.dsh-rewind-cleanup-error {\n margin: 0;\n font-size: 12px;\n line-height: 1.5;\n color: var(--dsw-alias-label-error);\n}\n/* Switch row: label left, role=switch button right, hint below (Subagent module). */\n.dsh-rewind-cleanup-toggle-row {\n display: flex;\n align-items: flex-start;\n justify-content: space-between;\n gap: 16px;\n font-size: 13px;\n line-height: 1.5;\n color: var(--dsw-alias-label-primary);\n}\n.dsh-rewind-cleanup-toggle-label {\n flex: 1;\n min-width: 0;\n}\n.dsh-rewind-cleanup-switch {\n box-sizing: border-box;\n position: relative;\n flex: 0 0 auto;\n width: 36px;\n height: 20px;\n padding: 2px;\n border: 0;\n border-radius: 10px;\n background: var(--dsw-alias-border-l3);\n cursor: pointer;\n}\n.dsh-rewind-cleanup-switch-on {\n background: var(--dsw-alias-brand-primary);\n}\n.dsh-rewind-cleanup-switch:disabled {\n cursor: default;\n opacity: 0.5;\n}\n.dsh-rewind-cleanup-switch:focus-visible {\n outline: 2px solid var(--dsw-alias-brand-primary);\n outline-offset: 2px;\n}\n.dsh-rewind-cleanup-thumb {\n display: block;\n width: 16px;\n height: 16px;\n border-radius: 50%;\n corner-shape: round;\n background: var(--dsw-alias-label-primary-foreground);\n transition: transform 120ms ease;\n}\n.dsh-rewind-cleanup-switch-on .dsh-rewind-cleanup-thumb {\n transform: translateX(16px);\n}\n.dsh-rewind-cleanup-input {\n box-sizing: border-box;\n height: 34px;\n padding: 0 12px;\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 8px;\n background: var(--dsw-alias-bg-layer-3);\n font: inherit;\n font-size: 13px;\n line-height: 1.5;\n color: var(--dsw-alias-label-primary);\n}\n.dsh-rewind-cleanup-input:focus-visible {\n outline: none;\n border-color: var(--dsw-alias-brand-primary);\n}\n.dsh-rewind-cleanup-input:disabled {\n color: var(--dsw-alias-label-tertiary);\n cursor: default;\n}\n.dsh-rewind-cleanup-input-invalid {\n border-color: var(--dsw-alias-label-error);\n}\n.dsh-rewind-cleanup-footer {\n display: flex;\n align-items: center;\n justify-content: flex-end;\n gap: 8px;\n padding: 12px 0 4px;\n border-top: 1px solid var(--dsw-alias-border-l2);\n}\n.dsh-rewind-cleanup-failed {\n flex: 1;\n min-width: 0;\n margin: 0;\n font-size: 12px;\n line-height: 1.5;\n color: var(--dsw-alias-label-error);\n}\n.dsh-rewind-cleanup-discard,\n.dsh-rewind-cleanup-save {\n appearance: none;\n border: 1px solid transparent;\n border-radius: 8px;\n padding: 5px 14px;\n font: inherit;\n font-size: 13px;\n line-height: 1.5;\n cursor: pointer;\n}\n.dsh-rewind-cleanup-discard {\n border-color: var(--dsw-alias-border-l2);\n background: none;\n color: var(--dsw-alias-label-secondary);\n}\n.dsh-rewind-cleanup-discard:hover:not(:disabled) {\n color: var(--dsw-alias-label-primary);\n border-color: var(--dsw-alias-label-dimmed);\n}\n.dsh-rewind-cleanup-save {\n background: var(--dsw-alias-label-primary);\n color: var(--dsw-alias-bg-layer-3);\n}\n.dsh-rewind-cleanup-discard:disabled,\n.dsh-rewind-cleanup-save:disabled {\n opacity: 0.4;\n cursor: default;\n}\n.dsh-rewind-cleanup-discard:focus-visible,\n.dsh-rewind-cleanup-save:focus-visible {\n outline: 2px solid var(--dsw-alias-brand-primary);\n outline-offset: 1px;\n}\n";
@@ -1,16 +1,17 @@
1
1
  /**
2
2
  * Cross-channel session event-log reader.
3
3
  *
4
- * Harness 0.1.1-rc.2 exposes the full log as `Session.events`
5
- * (`get events(): readonly SessionEvent[]`), while 0.1.2-alpha.4 removed that
4
+ * This is a "0.1.1-rc.2 0.1.2-rc.1" dual-channel reader. Harness 0.1.1-rc.2
5
+ * exposes the full log as `Session.events` (`get events(): readonly
6
+ * SessionEvent[]`); the 0.1.2 line (alpha.4+, now 0.1.2-rc.1) removed that
6
7
  * member and replaced it with the on-demand APIs `snapshotEvents(from?, to?)`
7
8
  * (half-open range, internally cached), `eventAt(seq)`, `ownEvents()` and
8
9
  * `seq`. This module reads the full log through whichever channel the host
9
- * exposes, so the plugin keeps one code path across both.
10
+ * exposes, so the plugin keeps one code path across both endpoints.
10
11
  *
11
12
  * `snapshotEvents()` is deliberately preferred over `ownEvents()`:
12
13
  * `snapshotEvents()` defaults to the whole log (including any fork-inherited
13
- * prefix), which is exactly what `Session.events` returned on rc.2 — the
14
+ * prefix), which is exactly what `Session.events` returned on 0.1.1-rc.2 — the
14
15
  * rewind semantics are preserved for fork-seeded sessions. `ownEvents()`
15
16
  * would drop the inherited prefix and change behaviour.
16
17
  *
@@ -20,15 +21,17 @@ import type { Session, SessionEvent } from '@deepseek-ai/dsh-session';
20
21
  /**
21
22
  * Read the full event log of a session, transparently across harness channels:
22
23
  * - 0.1.1-rc.2 (`Session.events`): the live immutable log array.
23
- * - 0.1.2-alpha.4 (`Session.snapshotEvents()`): a deep-frozen snapshot, cached
24
- * by the session until the next append.
24
+ * - 0.1.2-rc.1 (`Session.snapshotEvents()`): a deep-frozen snapshot, cached
25
+ * by the session until the next append. This is the single 0.1.2-line
26
+ * channel (alpha.2/3 still exposed `events` and thus fall into the
27
+ * 0.1.1-rc.2 branch below).
25
28
  *
26
29
  * Falls back to an empty log when the session exposes neither member (a future
27
30
  * harness shape) rather than throwing — callers already treat the empty log as
28
31
  * "no candidates".
29
32
  *
30
33
  * @param session - the session to read.
31
- * @returns the full event log in log order (the same shape rc.2's `events`
34
+ * @returns the full event log in log order (the same shape 0.1.1-rc.2's `events`
32
35
  * returned, so existing consumers are unchanged).
33
36
  */
34
37
  export declare function eventsOf(session: Session): readonly SessionEvent[];
@@ -1,12 +1,13 @@
1
1
  /**
2
2
  * Version-neutral settings-namespace reading for the host half.
3
3
  *
4
- * DSH rc.2 exposes a `settingsNamespace(value)` brand helper, and `settings.get`
5
- * is typed to require a branded `SettingsNamespace`. DSH 0.1.2-alpha.2 removed
4
+ * This is a "0.1.1-rc.2 0.1.2-rc.1" dual channel. DSH 0.1.1-rc.2 exposes a
5
+ * `settingsNamespace(value)` brand helper, and `settings.get` is typed to
6
+ * require a branded `SettingsNamespace`. The 0.1.2 line (0.1.2-rc.1) removed
6
7
  * that helper (the `SettingsNamespace` *type* remains) and `settings.get`
7
8
  * accepts the raw namespace string. This module collapses both into one runtime
8
- * call: on rc.2 the brand is a compile-time marker erased at runtime (so
9
- * `settingsNamespace(ns)` returns `ns`), on 0.1.2-alpha.2 the brand helper is
9
+ * call: on 0.1.1-rc.2 the brand is a compile-time marker erased at runtime (so
10
+ * `settingsNamespace(ns)` returns `ns`), on 0.1.2-rc.1 the brand helper is
10
11
  * absent and the raw `ns` string is used directly. That is what lets a single
11
12
  * compiled host bundle link and run on both harness generations.
12
13
  *
@@ -16,17 +17,17 @@
16
17
  export interface SettingsProviderLike {
17
18
  /**
18
19
  * Read one registered settings section by namespace. Accepts whatever the
19
- * running DSH generation passes: a branded `SettingsNamespace` (rc.2, brand
20
- * erased) or the raw namespace string (0.1.2-alpha.2).
20
+ * running DSH generation passes: a branded `SettingsNamespace` (0.1.1-rc.2,
21
+ * brand erased) or the raw namespace string (0.1.2-rc.1).
21
22
  */
22
23
  get(ns: string): unknown;
23
24
  }
24
- /** The `settingsNamespace(ns)` brand helper, or `undefined` when removed (0.1.2-alpha.2). */
25
+ /** The `settingsNamespace(ns)` brand helper, or `undefined` when removed (0.1.2-rc.1). */
25
26
  export type SettingsNamespaceBrand = ((value: string) => string) | undefined;
26
27
  /**
27
28
  * Read one settings section keyed by `ns`, tolerant of the settings-namespace
28
- * brand across DSH generations. Pass the brand helper when available (the rc.2
29
- * path); it is `undefined` on 0.1.2-alpha.2, where the raw `ns` string is used
30
- * directly. Never throws: an absent section simply returns `undefined`.
29
+ * brand across DSH generations. Pass the brand helper when available (the
30
+ * 0.1.1-rc.2 path); it is `undefined` on 0.1.2-rc.1, where the raw `ns` string
31
+ * is used directly. Never throws: an absent section simply returns `undefined`.
31
32
  */
32
33
  export declare function readSettingsSection(provider: SettingsProviderLike, ns: string, brand: SettingsNamespaceBrand): unknown;
@@ -46,9 +46,9 @@ export declare const CleanupConfigSchema: z<CleanupConfig>;
46
46
  /**
47
47
  * Structural face of the settings scope the host needs for the policy: a
48
48
  * resolved read and a validated write. Kept local (never imports the settings
49
- * contract) so the host bundle links on both rc.2 and alpha — the settings
50
- * API drift (alpha adds `mutate`, rd2 does not) is confined to the seam the
51
- * host passes in, never to this module.
49
+ * contract) so the host bundle links on both 0.1.1-rc.2 and 0.1.2-rc.1 — the
50
+ * settings API drift (0.1.2 adds `mutate`, 0.1.1 does not) is confined to the
51
+ * seam the host passes in, never to this module.
52
52
  */
53
53
  export interface CleanupSettingsScope {
54
54
  /** The resolved policy: schema defaults, then base, then the user layer. */
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "dsh-rewind-plugin",
3
- "version": "0.7.4",
3
+ "version": "0.7.5",
4
4
  "description": "DSH 插件:真正便捷无感的同窗口内对话回退,从不新建分支;自带轻量工作区备份,可一并还原文件(完整 Claude Code /rewind 语义)。 · DSH plugin: genuinely effortless in-window conversation rewind — never forking a new session; ships a lightweight workspace backup that restores files together with the rewind (full Claude Code /rewind semantics).",
5
5
  "keywords": [
6
6
  "deepseek-harness",