@senguoyun/dsh-arkme 0.1.57 → 0.1.59

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 (61) hide show
  1. package/docs/harness-activity.md +18 -0
  2. package/docs/harness-quick-create.md +13 -0
  3. package/docs/harness-session-dropdown.md +65 -0
  4. package/docs/harness-sidebar-settings.md +9 -0
  5. package/docs/harness-trajectory-navigation.md +28 -0
  6. package/docs/plugin-release.md +1 -1
  7. package/lib/client.js +643 -31
  8. package/lib/client.js.map +1 -1
  9. package/lib/harness-sidebar-client.js +840 -0
  10. package/lib/harness-trajectory-client.js +254 -0
  11. package/lib/index.js +117 -8
  12. package/lib/persistent-extension.js +1 -1
  13. package/lib/{persistent-runtime-BnDj8qcY.js → persistent-runtime-ByM3JB3z.js} +15 -7
  14. package/lib/types/arkme-service.d.ts.map +1 -1
  15. package/lib/types/client/ArkmeCallSurface.d.ts.map +1 -1
  16. package/lib/types/client/ArkmePersistentShell.d.ts.map +1 -1
  17. package/lib/types/client/ArkmeQuickAdd.d.ts +5 -2
  18. package/lib/types/client/ArkmeQuickAdd.d.ts.map +1 -1
  19. package/lib/types/client/ArkmeVirtualWorkspace.d.ts +3 -1
  20. package/lib/types/client/ArkmeVirtualWorkspace.d.ts.map +1 -1
  21. package/lib/types/client/DeepSeekHarnessSurface.d.ts +2 -1
  22. package/lib/types/client/DeepSeekHarnessSurface.d.ts.map +1 -1
  23. package/lib/types/client/frame-menu-dismissal.d.ts +3 -0
  24. package/lib/types/client/frame-menu-dismissal.d.ts.map +1 -0
  25. package/lib/types/client/harness-activity-reporter.d.ts +4 -0
  26. package/lib/types/client/harness-activity-reporter.d.ts.map +1 -0
  27. package/lib/types/client/harness-activity.d.ts +49 -0
  28. package/lib/types/client/harness-activity.d.ts.map +1 -0
  29. package/lib/types/client/harness-new-session.d.ts +3 -0
  30. package/lib/types/client/harness-new-session.d.ts.map +1 -0
  31. package/lib/types/client/harness-session-dropdown.d.ts +9 -0
  32. package/lib/types/client/harness-session-dropdown.d.ts.map +1 -0
  33. package/lib/types/client/harness-session-hover.d.ts +3 -0
  34. package/lib/types/client/harness-session-hover.d.ts.map +1 -0
  35. package/lib/types/client/harness-session-list-default.d.ts +12 -0
  36. package/lib/types/client/harness-session-list-default.d.ts.map +1 -0
  37. package/lib/types/client/harness-session-menu-bridge.d.ts +16 -0
  38. package/lib/types/client/harness-session-menu-bridge.d.ts.map +1 -0
  39. package/lib/types/client/harness-session-summary.d.ts +28 -0
  40. package/lib/types/client/harness-session-summary.d.ts.map +1 -0
  41. package/lib/types/client/harness-sidebar-client.d.ts +5 -0
  42. package/lib/types/client/harness-sidebar-client.d.ts.map +1 -0
  43. package/lib/types/client/harness-trajectory-client.d.ts +5 -0
  44. package/lib/types/client/harness-trajectory-client.d.ts.map +1 -0
  45. package/lib/types/client/harness-trajectory-menu.d.ts +7 -0
  46. package/lib/types/client/harness-trajectory-menu.d.ts.map +1 -0
  47. package/lib/types/client/live-photo-playback.d.ts.map +1 -1
  48. package/lib/types/client/use-harness-activity.d.ts +3 -0
  49. package/lib/types/client/use-harness-activity.d.ts.map +1 -0
  50. package/lib/types/dsh-remote/session-persistence.d.ts +4 -0
  51. package/lib/types/dsh-remote/session-persistence.d.ts.map +1 -0
  52. package/lib/types/dsh-remote/transport-fragment.d.ts.map +1 -1
  53. package/lib/types/harness-embed-contract.d.ts +2 -0
  54. package/lib/types/harness-embed-contract.d.ts.map +1 -1
  55. package/lib/types/harness-embed-route.d.ts +3 -1
  56. package/lib/types/harness-embed-route.d.ts.map +1 -1
  57. package/lib/types/index.d.ts.map +1 -1
  58. package/lib/types/services/call-history-service.d.ts +4 -2
  59. package/lib/types/services/call-history-service.d.ts.map +1 -1
  60. package/lib/types/services/chat-service.d.ts.map +1 -1
  61. package/package.json +5 -5
@@ -0,0 +1,254 @@
1
+ window.__ModuleLoader__.load({
2
+ id: "@senguoyun/dsh-arkme/harness-trajectory",
3
+ factory: (require) => {
4
+ var module = { exports: {} };
5
+ var exports = module.exports;
6
+ Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
7
+ //#region src/client/harness-trajectory-menu.ts
8
+ const HEADER_SLOT = "[data-slot=\"conversation.session.header\"]";
9
+ const UTILITIES_SLOT = "[data-slot=\"conversation.session.header.utilities\"]";
10
+ const OWNED = "[data-arkme-harness-return], [data-arkme-harness-trajectory-item]";
11
+ const TABS_MARKER = "data-arkme-harness-view-tabs";
12
+ const HEADER_MARKER = "data-arkme-harness-compact-header";
13
+ const COPY = [{
14
+ chat: "对话",
15
+ trajectory: "轨迹",
16
+ more: "更多操作",
17
+ view: "查看轨迹",
18
+ back: "← 返回对话"
19
+ }, {
20
+ chat: "Chat",
21
+ trajectory: "Trajectory",
22
+ more: "More actions",
23
+ view: "View trajectory",
24
+ back: "← Back to chat"
25
+ }];
26
+ /** Only recognize the native two-view header; new upstream views keep their own navigation. */
27
+ function navigation(header) {
28
+ const tablists = header.querySelectorAll(":scope > [role=\"tablist\"]");
29
+ if (tablists.length !== 1) return;
30
+ const tabs = tablists[0];
31
+ const buttons = [...tabs.querySelectorAll(":scope > button[role=\"tab\"]")];
32
+ if (buttons.length !== 2 || tabs.children.length !== 2) return;
33
+ const copy = COPY.find((value) => buttons.some((button) => button.textContent?.trim() === value.chat) && buttons.some((button) => button.textContent?.trim() === value.trajectory));
34
+ if (copy === void 0) return;
35
+ const chat = buttons.find((button) => button.textContent?.trim() === copy.chat);
36
+ const trajectory = buttons.find((button) => button.textContent?.trim() === copy.trajectory);
37
+ if (chat.disabled || trajectory.disabled) return;
38
+ if (buttons.filter((button) => button.getAttribute("aria-selected") === "true").length !== 1) return;
39
+ const triggers = [...header.querySelectorAll(`${UTILITIES_SLOT} button[aria-haspopup="menu"]`)].filter((button) => button.getAttribute("aria-label") === copy.more && !button.disabled);
40
+ if (triggers.length !== 1) return;
41
+ const more = triggers[0];
42
+ if (more.parentElement?.closest(UTILITIES_SLOT) === null) return;
43
+ return {
44
+ header,
45
+ tabs,
46
+ chat,
47
+ trajectory,
48
+ more,
49
+ copy
50
+ };
51
+ }
52
+ function removeMount(mount) {
53
+ mount.tabs.removeAttribute(TABS_MARKER);
54
+ mount.header.removeAttribute(HEADER_MARKER);
55
+ mount.back.remove();
56
+ mount.item?.remove();
57
+ }
58
+ /**
59
+ * A reversible presentation adapter for DSH's native header. DSH 0.1.5-rc.2
60
+ * has no tab-strip or export-menu-item slot. Keep its components, handlers,
61
+ * session state and other menu entries intact; never copy/replace the header.
62
+ */
63
+ function installHarnessTrajectoryMenu(doc) {
64
+ const Observer = doc.defaultView?.MutationObserver;
65
+ if (Observer === void 0 || doc.body === null) return () => {};
66
+ const mounts = /* @__PURE__ */ new Map();
67
+ const unsupported = /* @__PURE__ */ new WeakSet();
68
+ let disposed = false;
69
+ const style = doc.createElement("style");
70
+ style.dataset.arkmeHarnessTrajectory = "true";
71
+ style.textContent = `
72
+ [${TABS_MARKER}] { display: none !important; }
73
+ ${HEADER_SLOT} > header[${HEADER_MARKER}] {
74
+ min-height: 0; padding-bottom: 10px;
75
+ }
76
+ [data-arkme-harness-return] {
77
+ background: transparent; border: 0; padding: 4px 0; margin-top: 8px;
78
+ color: var(--dsw-alias-label-secondary, inherit); font: inherit;
79
+ font-size: 13px; cursor: pointer;
80
+ }
81
+ [data-arkme-harness-return]:hover { color: var(--dsw-alias-label-primary, inherit); }
82
+ [data-arkme-harness-return][hidden] { display: none; }
83
+ `;
84
+ doc.head.append(style);
85
+ function makeMount(value) {
86
+ const back = doc.createElement("button");
87
+ back.type = "button";
88
+ back.dataset.arkmeHarnessReturn = "true";
89
+ back.textContent = value.copy.back;
90
+ back.hidden = true;
91
+ const mount = {
92
+ ...value,
93
+ back,
94
+ focusBack: false
95
+ };
96
+ back.addEventListener("click", () => {
97
+ if (!mount.chat.isConnected || mount.chat.disabled) return;
98
+ mount.chat.click();
99
+ mount.more.focus();
100
+ });
101
+ value.header.append(back);
102
+ return mount;
103
+ }
104
+ function syncMenu(mount) {
105
+ if (mount.more.getAttribute("aria-expanded") !== "true") {
106
+ mount.item?.remove();
107
+ delete mount.item;
108
+ return true;
109
+ }
110
+ const menus = mount.more.parentElement?.querySelectorAll(":scope > [role=\"menu\"]");
111
+ if (menus?.length !== 1) return false;
112
+ const menu = menus[0];
113
+ const template = [...menu.querySelectorAll("button[role=\"menuitem\"]")].find((button) => !button.closest(OWNED) && button.closest("[role=\"menu\"]") === menu);
114
+ const itemParent = template?.parentElement;
115
+ const viewport = itemParent?.parentElement;
116
+ const label = template === void 0 ? void 0 : [...template.children].find((child) => child.tagName === "SPAN" && child.textContent?.trim() === template.textContent?.trim());
117
+ if (template === void 0 || itemParent === null || itemParent === void 0 || viewport?.getAttribute("role") !== "presentation" || viewport.parentElement !== menu || label === void 0) return false;
118
+ if (mount.item?.parentElement === viewport) return true;
119
+ mount.item?.remove();
120
+ const item = doc.createElement("div");
121
+ item.dataset.arkmeHarnessTrajectoryItem = "true";
122
+ item.className = itemParent.className;
123
+ const button = doc.createElement("button");
124
+ button.type = "button";
125
+ button.setAttribute("role", "menuitem");
126
+ button.className = template.className;
127
+ const templateIcon = [...template.children].find((child) => child.tagName === "SPAN" && child.querySelector("svg"));
128
+ if (templateIcon !== void 0) {
129
+ const icon = doc.createElement("span");
130
+ icon.className = templateIcon.className;
131
+ const svg = doc.createElementNS("http://www.w3.org/2000/svg", "svg");
132
+ svg.setAttribute("width", "16");
133
+ svg.setAttribute("height", "16");
134
+ svg.setAttribute("viewBox", "0 0 16 16");
135
+ svg.setAttribute("fill", "none");
136
+ svg.setAttribute("aria-hidden", "true");
137
+ const path = doc.createElementNS(svg.namespaceURI, "path");
138
+ path.setAttribute("d", "M3.5 3h.01M3.5 8h.01M3.5 13h.01M3.5 4.5v2M3.5 9.5v2M7 3h6M7 8h6M7 13h6");
139
+ path.setAttribute("stroke", "currentColor");
140
+ path.setAttribute("stroke-width", "1.5");
141
+ path.setAttribute("stroke-linecap", "round");
142
+ svg.append(path);
143
+ icon.append(svg);
144
+ button.append(icon);
145
+ }
146
+ const text = doc.createElement("span");
147
+ text.className = label.className;
148
+ text.textContent = mount.copy.view;
149
+ button.append(text);
150
+ button.addEventListener("click", (event) => {
151
+ event.stopPropagation();
152
+ if (!mount.trajectory.isConnected || mount.trajectory.disabled) return;
153
+ mount.focusBack = true;
154
+ mount.more.click();
155
+ mount.trajectory.click();
156
+ });
157
+ button.addEventListener("keydown", (event) => {
158
+ if (event.key !== "Escape") return;
159
+ event.preventDefault();
160
+ event.stopPropagation();
161
+ mount.more.click();
162
+ mount.more.focus();
163
+ });
164
+ item.append(button);
165
+ viewport.append(item);
166
+ mount.item = item;
167
+ return true;
168
+ }
169
+ function sync() {
170
+ if (disposed) return;
171
+ for (const [header, mount] of mounts) if (!header.isConnected) {
172
+ removeMount(mount);
173
+ mounts.delete(header);
174
+ }
175
+ for (const header of doc.querySelectorAll(`${HEADER_SLOT} > header`)) {
176
+ const value = unsupported.has(header) ? void 0 : navigation(header);
177
+ let mount = mounts.get(header);
178
+ if (mount !== void 0 && (value === void 0 || mount.tabs !== value.tabs || mount.more !== value.more || mount.chat !== value.chat || mount.trajectory !== value.trajectory || mount.copy !== value.copy || mount.back.parentElement !== header)) {
179
+ removeMount(mount);
180
+ mounts.delete(header);
181
+ mount = void 0;
182
+ }
183
+ if (value === void 0) continue;
184
+ if (mount === void 0) {
185
+ mount = makeMount(value);
186
+ mounts.set(header, mount);
187
+ }
188
+ if (!syncMenu(mount)) {
189
+ unsupported.add(header);
190
+ removeMount(mount);
191
+ mounts.delete(header);
192
+ continue;
193
+ }
194
+ if (!mount.tabs.hasAttribute(TABS_MARKER)) mount.tabs.setAttribute(TABS_MARKER, "");
195
+ if (!mount.header.hasAttribute(HEADER_MARKER)) mount.header.setAttribute(HEADER_MARKER, "");
196
+ const inTrajectory = mount.trajectory.getAttribute("aria-selected") === "true";
197
+ if (mount.back.hidden === inTrajectory) mount.back.hidden = !inTrajectory;
198
+ if (mount.focusBack && inTrajectory) {
199
+ mount.focusBack = false;
200
+ mount.back.focus();
201
+ }
202
+ }
203
+ }
204
+ function touchesHeader(record) {
205
+ const target = record.target.nodeType === 1 ? record.target : record.target.parentElement;
206
+ if (target?.closest(OWNED)) return false;
207
+ if (target?.closest(HEADER_SLOT)) return true;
208
+ return [...record.addedNodes, ...record.removedNodes].some((node) => {
209
+ if (node.nodeType !== 1) return false;
210
+ const element = node;
211
+ return element.matches(HEADER_SLOT) || element.querySelector(HEADER_SLOT) !== null;
212
+ });
213
+ }
214
+ const observer = new Observer((records) => {
215
+ if (records.some(touchesHeader)) sync();
216
+ });
217
+ observer.observe(doc.body, {
218
+ childList: true,
219
+ subtree: true,
220
+ characterData: true,
221
+ attributes: true,
222
+ attributeFilter: [
223
+ "aria-selected",
224
+ "aria-expanded",
225
+ "aria-label",
226
+ "disabled",
227
+ "role",
228
+ "data-slot"
229
+ ]
230
+ });
231
+ sync();
232
+ return () => {
233
+ if (disposed) return;
234
+ disposed = true;
235
+ observer.disconnect();
236
+ for (const mount of mounts.values()) removeMount(mount);
237
+ mounts.clear();
238
+ style.remove();
239
+ };
240
+ }
241
+ //#endregion
242
+ //#region src/client/harness-trajectory-client.ts
243
+ const inject = [];
244
+ /** This client is added only to the Arkme-owned native Harness iframe. */
245
+ function apply(ctx) {
246
+ if (typeof document === "undefined" || typeof window === "undefined" || new URLSearchParams(window.location.search).get("arkme-harness-embed") !== "1") return;
247
+ ctx.effect(() => installHarnessTrajectoryMenu(document), "arkme: native Harness trajectory navigation");
248
+ }
249
+ //#endregion
250
+ exports.apply = apply;
251
+ exports.inject = inject;
252
+ return module.exports;
253
+ }
254
+ });
package/lib/index.js CHANGED
@@ -1,4 +1,4 @@
1
- import { $ as ARKME_DEFAULT_SHARE_WEBSITE, A as inspectNativeBundleArtifactV3, At as createDesktopLifecycleReader, D as bundleSha256, Dt as ArkmePluginError, E as arkmeSandboxEntryId, Et as normalizeRecentEmojiIds, F as assertExtensionArtifactSize, Ft as __toCommonJS, G as validateVoiceprintPcm16Wav, I as canonicalExtensionJson, J as arkmeRequiredLinkMetadataFallback, K as arkmeExtensionShareRefFromLink, L as sha256Hex, M as packLocalNativeBundleDirectoryV3, Mt as __esmMin, N as readNativeBundleTarballV3, Nt as __exportAll, O as canonicalBundleJson, Ot as retryAfterMillis, P as renderArkmeSandboxHostEntry, Pt as __require, Q as parseArkmeRecordReeditAttachments, R as unpackArkmeExtension, S as ARKME_BUNDLE_ARTIFACT_KIND, St as sameRecordingImportIdentity, T as ArkmeBundleArtifactError, Tt as isRecentEmojiId, U as ARKME_EXTENSION_RUNTIME_UNAVAILABLE_MESSAGE, W as ArkmeService, X as arkmeRichBackgroundSound, Y as arkmeFileBackgroundSound, Z as ArkmeRecordReeditDraftConflict, _ as arkmeClientContentDigest, _t as SecretValue, at as ARKME_WORLD_PUBLISH_MAX_IMAGE_BYTES, b as verifyExtensionResolutionSignature, bt as isUnresolvedRecordingImportJob, c as persistentExtensionBundleDirectory, ct as mergeMemberJoinEvents, d as readPersistentExtensionActivation, dt as ARKME_TOOL_FILE_MAX_BYTES, et as ARKME_PROVIDER_CONTRACT_VERSION, f as refreshPersistentClientWrapper, ft as arkmeCanInlineLocalFile, g as activeProfileExtensionOwnerConflicts, gt as ArkmeOutgoingCallError, h as renderArkmeBundleClientBundle, ht as isArkmeBotAvatarRef, i as invokePersistentArkmeExtension, it as ARKME_WORLD_PUBLISH_MAX_IMAGES, j as packBundleFiles, jt as __commonJSMin, k as inspectBundleArtifact, kt as recordOwnerId, l as persistentExtensionPackageIdentity, lt as validateMemberUpdate, m as writePersistentExtensionActivation, mt as arkmePickedFileKind, o as persistentArkmeExtensionRuntimeState, ot as applyMemberUpdate, p as repairPersistentExtensionInstallation, pt as arkmeNormalizedFileMimeType, q as arkmeIsGenericLinkMetadataTitle, r as deactivatePersistentArkmeExtension, s as materializePersistentExtensionBundle, st as cachedMemberItem, t as activatePersistentArkmeExtension, u as quarantinePersistentExtension, ut as ARKME_RUNTIME_INSTANCE_ID, v as arkmeClientContentDigestFromSource, vt as ArkmeDirectMessageAdmissionError, w as ARKME_NATIVE_BUNDLE_ARTIFACT_KIND, wt as recordingImportFileNameKey, x as verifyNativeBundleResolutionSignature, xt as recordingImportFileKind, y as verifyBundleResolutionSignature, yt as isRecordingInstantOnOrAfterUnixEpoch, z as ARKME_EXTENSION_FORMAT } from "./persistent-runtime-BnDj8qcY.js";
1
+ import { $ as ARKME_DEFAULT_SHARE_WEBSITE, A as inspectNativeBundleArtifactV3, At as createDesktopLifecycleReader, D as bundleSha256, Dt as ArkmePluginError, E as arkmeSandboxEntryId, Et as normalizeRecentEmojiIds, F as assertExtensionArtifactSize, Ft as __toCommonJS, G as validateVoiceprintPcm16Wav, I as canonicalExtensionJson, J as arkmeRequiredLinkMetadataFallback, K as arkmeExtensionShareRefFromLink, L as sha256Hex, M as packLocalNativeBundleDirectoryV3, Mt as __esmMin, N as readNativeBundleTarballV3, Nt as __exportAll, O as canonicalBundleJson, Ot as retryAfterMillis, P as renderArkmeSandboxHostEntry, Pt as __require, Q as parseArkmeRecordReeditAttachments, R as unpackArkmeExtension, S as ARKME_BUNDLE_ARTIFACT_KIND, St as sameRecordingImportIdentity, T as ArkmeBundleArtifactError, Tt as isRecentEmojiId, U as ARKME_EXTENSION_RUNTIME_UNAVAILABLE_MESSAGE, W as ArkmeService, X as arkmeRichBackgroundSound, Y as arkmeFileBackgroundSound, Z as ArkmeRecordReeditDraftConflict, _ as arkmeClientContentDigest, _t as SecretValue, at as ARKME_WORLD_PUBLISH_MAX_IMAGE_BYTES, b as verifyExtensionResolutionSignature, bt as isUnresolvedRecordingImportJob, c as persistentExtensionBundleDirectory, ct as mergeMemberJoinEvents, d as readPersistentExtensionActivation, dt as ARKME_TOOL_FILE_MAX_BYTES, et as ARKME_PROVIDER_CONTRACT_VERSION, f as refreshPersistentClientWrapper, ft as arkmeCanInlineLocalFile, g as activeProfileExtensionOwnerConflicts, gt as ArkmeOutgoingCallError, h as renderArkmeBundleClientBundle, ht as isArkmeBotAvatarRef, i as invokePersistentArkmeExtension, it as ARKME_WORLD_PUBLISH_MAX_IMAGES, j as packBundleFiles, jt as __commonJSMin, k as inspectBundleArtifact, kt as recordOwnerId, l as persistentExtensionPackageIdentity, lt as validateMemberUpdate, m as writePersistentExtensionActivation, mt as arkmePickedFileKind, o as persistentArkmeExtensionRuntimeState, ot as applyMemberUpdate, p as repairPersistentExtensionInstallation, pt as arkmeNormalizedFileMimeType, q as arkmeIsGenericLinkMetadataTitle, r as deactivatePersistentArkmeExtension, s as materializePersistentExtensionBundle, st as cachedMemberItem, t as activatePersistentArkmeExtension, u as quarantinePersistentExtension, ut as ARKME_RUNTIME_INSTANCE_ID, v as arkmeClientContentDigestFromSource, vt as ArkmeDirectMessageAdmissionError, w as ARKME_NATIVE_BUNDLE_ARTIFACT_KIND, wt as recordingImportFileNameKey, x as verifyNativeBundleResolutionSignature, xt as recordingImportFileKind, y as verifyBundleResolutionSignature, yt as isRecordingInstantOnOrAfterUnixEpoch, z as ARKME_EXTENSION_FORMAT } from "./persistent-runtime-ByM3JB3z.js";
2
2
  import { _ as parsePluginUpdateManifest, b as validatePluginUpdateServiceOrigin, d as writePluginUpdateLifecycleLog, f as PluginUpdateInstallStateStore, g as existingCachedPluginArtifactPath, h as downloadAndCachePluginArtifact, m as PluginUpdateArtifactError, n as buildTargetInstallArgs, o as reconcilePluginUpdaterProfilePolicy, p as ARKME_PLUGIN_PACKAGE_NAME$1, t as assertTargetArtifactIntegrity, u as detachManagedProfilePluginLink, v as pluginUpdateEndpointUrl, y as validatePluginUpdateArtifactOrigin } from "./plugin-updater-helper-y7wzJLOx.js";
3
3
  import { a as securePrivateDirectory, c as securePrivateFileSync, i as prepareProfilePackageManager, n as isArkmeProfilePackageName, o as securePrivateDirectorySync, r as localExtensionPnpmArgs, s as securePrivateFile, t as applyArkmeProfileBundlePolicy } from "./profile-bundle-policy-DLXDyohJ.js";
4
4
  import { i as invokeArkmeBundle, n as arkmeBundleActive, r as deactivateArkmeBundle } from "./bundle-runtime-CE73h3vS.js";
@@ -35,6 +35,43 @@ import WebSocket$1, { WebSocket, WebSocketServer } from "ws";
35
35
  import { Buffer as Buffer$1 } from "node:buffer";
36
36
  import { AttachmentError, AttachmentId } from "@deepseek-ai/dsh-attachment";
37
37
  import { scheduler, setTimeout as setTimeout$1 } from "node:timers/promises";
38
+ //#region src/dsh-remote/session-persistence.ts
39
+ /** Preserve legacy backends; adapt the public handle API introduced in DSH 0.1.5. */
40
+ function adaptSessionPersistence(value) {
41
+ if (value == null) return void 0;
42
+ const service = value;
43
+ if (typeof service.listSnapshots === "function" && typeof service.readFrom === "function") return service;
44
+ if (typeof service.list !== "function" || typeof service.open !== "function") {
45
+ const unsupported = async () => {
46
+ throw new Error("Unsupported DSH session persistence API: expected listSnapshots/readFrom or list/open");
47
+ };
48
+ return {
49
+ listSnapshots: unsupported,
50
+ readFrom: unsupported
51
+ };
52
+ }
53
+ const persistence = service;
54
+ return {
55
+ listSnapshots: async (signal) => [...await persistence.list(signal === void 0 ? void 0 : { signal })],
56
+ readFrom: async (id, offset, signal) => {
57
+ signal?.throwIfAborted();
58
+ const options = signal === void 0 ? void 0 : { signal };
59
+ const handle = await persistence.open(id, "read", options);
60
+ try {
61
+ signal?.throwIfAborted();
62
+ const { events } = await handle.read(offset, void 0, options);
63
+ signal?.throwIfAborted();
64
+ return {
65
+ meta: handle.header,
66
+ events: [...events]
67
+ };
68
+ } finally {
69
+ await handle.close();
70
+ }
71
+ }
72
+ };
73
+ }
74
+ //#endregion
38
75
  //#region src/tools/shared/output.ts
39
76
  const TEXT_OUTPUT$3 = {
40
77
  schema: { type: "string" },
@@ -109,6 +146,8 @@ const HARNESS_SESSION_CLIENT_ID = "@senguoyun/dsh-arkme/harness-session";
109
146
  const HARNESS_SESSION_CLIENT_PATH = "/arkme-self/harness-session-client.js";
110
147
  const ARKME_HARNESS_MODEL_CLIENT_PATH = "/arkme-self/harness-model-client.js";
111
148
  const ARKME_HARNESS_ONBOARDING_CLIENT_PATH = "/arkme-self/harness-onboarding-client.js";
149
+ const ARKME_HARNESS_TRAJECTORY_CLIENT_PATH = "/arkme-self/harness-trajectory-client.js";
150
+ const ARKME_HARNESS_SIDEBAR_CLIENT_PATH = "/arkme-self/harness-sidebar-client.js";
112
151
  //#endregion
113
152
  //#region src/plugin-update-policy.ts
114
153
  const PLUGIN_UPDATE_TERMINAL_STATE_TTL_MS = 10 * 6e4;
@@ -12393,7 +12432,7 @@ function projectBootBatches(batches, keptPackageNames) {
12393
12432
  * Host halves stay process-owned and untouched; only this document's browser
12394
12433
  * boot graph is projected.
12395
12434
  */
12396
- function projectHarnessBootGraph(graph, installedPackageNames, modelClient) {
12435
+ function projectHarnessBootGraph(graph, installedPackageNames, modelClient, trajectoryClient, sidebarClient) {
12397
12436
  const requiredPackageNames = requiredBootPackages(graph.entries);
12398
12437
  const removedPackageNames = /* @__PURE__ */ new Set([
12399
12438
  ARKME_PLUGIN_PACKAGE_NAME,
@@ -12414,6 +12453,37 @@ function projectHarnessBootGraph(graph, installedPackageNames, modelClient) {
12414
12453
  entries: [modelClient.id]
12415
12454
  });
12416
12455
  }
12456
+ const trajectoryPackages = [
12457
+ "@deepseek-ai/dsh-client-ui-conversation",
12458
+ "@deepseek-ai/dsh-client-ui-trajectory",
12459
+ "@deepseek-ai/dsh-session-log-export"
12460
+ ];
12461
+ if (trajectoryClient && trajectoryPackages.every((id) => entries.some((entry) => entry.id === id))) {
12462
+ const entry = {
12463
+ ...trajectoryClient,
12464
+ inject: trajectoryPackages
12465
+ };
12466
+ entries.push(entry);
12467
+ batches?.push({
12468
+ phase: "application",
12469
+ url: entry.url,
12470
+ rev: entry.rev,
12471
+ entries: [entry.id]
12472
+ });
12473
+ }
12474
+ if (sidebarClient && entries.some((entry) => entry.id === "@deepseek-ai/dsh-client-ui-sidebar")) {
12475
+ const entry = {
12476
+ ...sidebarClient,
12477
+ inject: ["@deepseek-ai/dsh-client-ui-sidebar"]
12478
+ };
12479
+ entries.push(entry);
12480
+ batches?.push({
12481
+ phase: "application",
12482
+ url: entry.url,
12483
+ rev: entry.rev,
12484
+ entries: [entry.id]
12485
+ });
12486
+ }
12417
12487
  return {
12418
12488
  rev: shortHash(JSON.stringify(batches === void 0 ? entries : {
12419
12489
  entries,
@@ -12454,7 +12524,7 @@ function createHarnessEmbedRouteHandler(options) {
12454
12524
  }
12455
12525
  try {
12456
12526
  const fullGraph = options.getGraph();
12457
- const projectedGraph = projectHarnessBootGraph(fullGraph, options.installedPackageNames(), options.modelClient);
12527
+ const projectedGraph = projectHarnessBootGraph(fullGraph, options.installedPackageNames(), options.modelClient, options.trajectoryClient, options.sidebarClient);
12458
12528
  if (options.onboardingClient !== void 0) {
12459
12529
  const entry = {
12460
12530
  ...options.onboardingClient,
@@ -31988,13 +32058,18 @@ function sha256(value) {
31988
32058
  * Splits a large typed payload into independently bounded Realtime events.
31989
32059
  */
31990
32060
  function dshRemoteOutboundPayloads(envelope, transferSeed) {
31991
- const encoded = Buffer.from(JSON.stringify(envelope));
31992
- if (encoded.length <= DIRECT_PLAINTEXT_BYTES) return [{ value: envelope }];
32061
+ let hasEmptyArray = false;
32062
+ const encoded = Buffer.from(JSON.stringify(envelope, (_key, value) => {
32063
+ if (Array.isArray(value) && value.length === 0) hasEmptyArray = true;
32064
+ return value;
32065
+ }));
32066
+ if (encoded.length <= DIRECT_PLAINTEXT_BYTES && !hasEmptyArray) return [{ value: envelope }];
31993
32067
  if (encoded.length > 67108864) throw new DshRemoteError("CAPABILITY_UNSUPPORTED", "完整 DSH 事件超过 64MiB 安全上限", false, {
31994
32068
  logicalTooLarge: true,
31995
32069
  payloadBytes: encoded.length
31996
32070
  });
31997
- const fragmentCount = Math.ceil(encoded.length / FRAGMENT_CHUNK_BYTES);
32071
+ const chunkBytes = encoded.length <= DIRECT_PLAINTEXT_BYTES ? Math.ceil(encoded.length / 2) : FRAGMENT_CHUNK_BYTES;
32072
+ const fragmentCount = Math.ceil(encoded.length / chunkBytes);
31998
32073
  if (fragmentCount > MAX_FRAGMENT_COUNT) throw new DshRemoteError("CAPABILITY_UNSUPPORTED", "完整 DSH 事件需要过多远控分片", false, {
31999
32074
  logicalTooLarge: true,
32000
32075
  fragmentCount
@@ -32013,7 +32088,7 @@ function dshRemoteOutboundPayloads(envelope, transferSeed) {
32013
32088
  fragment_count: fragmentCount,
32014
32089
  payload_bytes: encoded.length,
32015
32090
  payload_sha256: digest,
32016
- chunk: encoded.subarray(fragmentIndex * FRAGMENT_CHUNK_BYTES, Math.min(encoded.length, (fragmentIndex + 1) * FRAGMENT_CHUNK_BYTES)).toString("base64url")
32091
+ chunk: encoded.subarray(fragmentIndex * chunkBytes, Math.min(encoded.length, (fragmentIndex + 1) * chunkBytes)).toString("base64url")
32017
32092
  }
32018
32093
  }));
32019
32094
  }
@@ -36624,7 +36699,7 @@ function apply(ctx, config) {
36624
36699
  const attachRemoteApi = (apiCtx, publicApi) => {
36625
36700
  if (remoteHost !== void 0) return;
36626
36701
  const agentDefaultModel = apiCtx.get("agentDefaultModel");
36627
- const sessionPersistence = apiCtx.get("sessionPersistence");
36702
+ const sessionPersistence = adaptSessionPersistence(apiCtx.get("sessionPersistence"));
36628
36703
  const apiProxy = new DshApiProxyAdapter(publicApi, { ...typeof agentDefaultModel?.currentSelection !== "function" ? {} : { defaultModelSelection: () => agentDefaultModel.currentSelection() } });
36629
36704
  service.accountScope.attachGuestConversationProbe(async () => {
36630
36705
  try {
@@ -36826,6 +36901,30 @@ function apply(ctx, config) {
36826
36901
  }), "arkme: Harness session observer asset");
36827
36902
  const harnessModelClient = readFileSync(new URL("../lib/harness-model-client.js", import.meta.url));
36828
36903
  const harnessOnboardingClient = readFileSync(new URL("../lib/harness-onboarding-client.js", import.meta.url));
36904
+ const harnessTrajectoryClient = readFileSync(new URL("../lib/harness-trajectory-client.js", import.meta.url));
36905
+ const harnessSidebarClient = readFileSync(new URL("../lib/harness-sidebar-client.js", import.meta.url));
36906
+ ctx.effect(() => ctx.webServer.register({
36907
+ kind: "exact",
36908
+ path: ARKME_HARNESS_SIDEBAR_CLIENT_PATH,
36909
+ handler: (_request, response) => {
36910
+ response.writeHead(200, {
36911
+ "Content-Type": "application/javascript",
36912
+ "Cache-Control": "no-cache"
36913
+ });
36914
+ response.end(harnessSidebarClient);
36915
+ }
36916
+ }), "arkme: Harness sidebar settings asset");
36917
+ ctx.effect(() => ctx.webServer.register({
36918
+ kind: "exact",
36919
+ path: ARKME_HARNESS_TRAJECTORY_CLIENT_PATH,
36920
+ handler: (_request, response) => {
36921
+ response.writeHead(200, {
36922
+ "Content-Type": "application/javascript",
36923
+ "Cache-Control": "no-cache"
36924
+ });
36925
+ response.end(harnessTrajectoryClient);
36926
+ }
36927
+ }), "arkme: Harness trajectory navigation asset");
36829
36928
  ctx.effect(() => ctx.webServer.register({
36830
36929
  kind: "exact",
36831
36930
  path: ARKME_HARNESS_ONBOARDING_CLIENT_PATH,
@@ -36838,6 +36937,16 @@ function apply(ctx, config) {
36838
36937
  }
36839
36938
  }), "arkme: Harness onboarding bridge asset");
36840
36939
  const harnessEmbedHandler = createHarnessEmbedRouteHandler({
36940
+ sidebarClient: {
36941
+ id: "@senguoyun/dsh-arkme/harness-sidebar",
36942
+ url: ARKME_HARNESS_SIDEBAR_CLIENT_PATH,
36943
+ rev: createHash("sha256").update(harnessSidebarClient).digest("hex")
36944
+ },
36945
+ trajectoryClient: {
36946
+ id: "@senguoyun/dsh-arkme/harness-trajectory",
36947
+ url: ARKME_HARNESS_TRAJECTORY_CLIENT_PATH,
36948
+ rev: createHash("sha256").update(harnessTrajectoryClient).digest("hex")
36949
+ },
36841
36950
  onboardingClient: {
36842
36951
  id: "@senguoyun/dsh-arkme/harness-onboarding",
36843
36952
  url: ARKME_HARNESS_ONBOARDING_CLIENT_PATH,
@@ -1,2 +1,2 @@
1
- import { a as persistentArkmeExtensionActive, i as invokePersistentArkmeExtension, n as applyPersistentArkmeHostExtension, o as persistentArkmeExtensionRuntimeState, r as deactivatePersistentArkmeExtension, t as activatePersistentArkmeExtension } from "./persistent-runtime-BnDj8qcY.js";
1
+ import { a as persistentArkmeExtensionActive, i as invokePersistentArkmeExtension, n as applyPersistentArkmeHostExtension, o as persistentArkmeExtensionRuntimeState, r as deactivatePersistentArkmeExtension, t as activatePersistentArkmeExtension } from "./persistent-runtime-ByM3JB3z.js";
2
2
  export { activatePersistentArkmeExtension, applyPersistentArkmeHostExtension, deactivatePersistentArkmeExtension, invokePersistentArkmeExtension, persistentArkmeExtensionActive, persistentArkmeExtensionRuntimeState };
@@ -38669,10 +38669,12 @@ var CallHistoryService = class {
38669
38669
  runtime;
38670
38670
  profile;
38671
38671
  media;
38672
- constructor(runtime, profile, media) {
38672
+ source;
38673
+ constructor(runtime, profile, media, source) {
38673
38674
  this.runtime = runtime;
38674
38675
  this.profile = profile;
38675
38676
  this.media = media;
38677
+ this.source = source;
38676
38678
  }
38677
38679
  async listCallHistory(options = {}, signal) {
38678
38680
  const session = await this.runtime.requireSession();
@@ -38688,7 +38690,7 @@ var CallHistoryService = class {
38688
38690
  failureCooldownMs: 2e3
38689
38691
  });
38690
38692
  const validItems = (await Promise.all(this.historyItems(raw).map(async (item) => await this.normalizeHistoryItem(item, session.userId)))).filter((item) => item !== void 0);
38691
- await this.attachPeerAvatars(validItems, session, signal);
38693
+ await this.attachPeerPresentation(validItems, session, signal);
38692
38694
  const hasMore = booleanValue$9(raw.has_more ?? raw.hasMore);
38693
38695
  const nextCursor = firstString$1(raw, [
38694
38696
  "next_cursor",
@@ -38931,16 +38933,18 @@ var CallHistoryService = class {
38931
38933
  return [];
38932
38934
  }
38933
38935
  }
38934
- async attachPeerAvatars(items, session, signal) {
38936
+ async attachPeerPresentation(items, session, signal) {
38935
38937
  const ids = [...new Set(items.flatMap((item) => item.peerUserId === void 0 ? [] : [item.peerUserId]))];
38936
38938
  if (ids.length === 0) return;
38937
- const profiles = await this.profile.publicProfilesByUserIds(ids, session, signal).catch(() => /* @__PURE__ */ new Map());
38939
+ const [profiles, remarks] = await Promise.all([this.profile.publicProfileSummariesByUserIds(ids, session, signal).catch(() => /* @__PURE__ */ new Map()), this.source?.privateRemarksByUserIds(ids, signal === void 0 ? {} : { signal }).catch(() => /* @__PURE__ */ new Map()) ?? Promise.resolve(/* @__PURE__ */ new Map())]);
38938
38940
  await Promise.all(items.map(async (item) => {
38939
38941
  const peerUserId = item.peerUserId;
38940
38942
  if (peerUserId === void 0) return;
38941
38943
  const profile = profiles.get(peerUserId);
38942
38944
  const displayName = profile?.displayName?.trim() ?? "";
38943
- if (displayName !== "" && /^Arkme 用户 \d+$/.test(item.peerDisplayName.trim())) item.peerDisplayName = displayName;
38945
+ const remark = remarks.get(peerUserId)?.trim() ?? "";
38946
+ if (remark !== "") item.peerDisplayName = remark;
38947
+ else if (displayName !== "" && /^Arkme 用户 \d+$/.test(item.peerDisplayName.trim())) item.peerDisplayName = displayName;
38944
38948
  if (profile?.avatarUrl === void 0) return;
38945
38949
  item.peerAvatarRef = await this.profile.sealProfileImageRef(session.userId, peerUserId);
38946
38950
  }));
@@ -43784,7 +43788,11 @@ function snapshotDetailFromChatRaw(raw, fallback) {
43784
43788
  ...position,
43785
43789
  ...objectValue$2(values.position)
43786
43790
  });
43787
- const locationLabel = firstSnapshotText(position.poi, position.poi_name, position.poiName, position.address, position.road, location.poi_name, location.poiName, location.address, location.name);
43791
+ const locationLabel = firstSnapshotText([
43792
+ [firstSnapshotText(position.city)?.replace(/市$/, ""), firstSnapshotText(position.county)?.replace(/(区|县|市)$/, "")].filter(Boolean).join("·"),
43793
+ firstSnapshotText(position.road),
43794
+ firstSnapshotText(position.poi, position.poi_name, position.poiName)
43795
+ ].join(""), position.address, location.poi_name, location.poiName, location.address, location.name);
43788
43796
  const weather = snapshotWeatherText(position.weather, position.weatherText, location.weather, values.weather);
43789
43797
  const altitudeMeters = nonNegativeNumberValue(location.altitude, location.alt, position.altitude, position.alt);
43790
43798
  const movement = snapshotMovement({
@@ -89513,7 +89521,7 @@ var ArkmeService = class {
89513
89521
  this.arrangement = new ArrangementService(this.runtime);
89514
89522
  this.wechat = new WechatService(this.runtime);
89515
89523
  this.profile = new ProfileService(this.runtime);
89516
- this.callHistory = new CallHistoryService(this.runtime, this.profile, { forwardContentBlocks: (files, viewerUserId) => this.media.forwardContentBlocks(files, viewerUserId) });
89524
+ this.callHistory = new CallHistoryService(this.runtime, this.profile, { forwardContentBlocks: (files, viewerUserId) => this.media.forwardContentBlocks(files, viewerUserId) }, { privateRemarksByUserIds: (userIds, options) => this.source.privateRemarksByUserIds(userIds, options) });
89517
89525
  this.extensionReview = new ExtensionReviewService(this.runtime, this.profile, { createTextForConversation: async (recordUid, textContent) => {
89518
89526
  return await this.createTextForConversation(recordUid, textContent);
89519
89527
  } });