dsh-edge 0.9.0 → 0.10.0
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.
- package/THIRD_PARTY_NOTICES.md +1318 -1075
- package/dist/assets/index-Df-65__b.js +110 -0
- package/dist/assets/index-b24khbeK.css +1 -0
- package/dist/assets/langs/{php-DDkx9sim.js → php-DJl5gRdb.js} +2 -2
- package/dist/assets/langs/{ruby-DCxyoPen.js → ruby-5eNB0pDK.js} +2 -2
- package/dist/assets/vendor-BNsW4eBh.css +1 -0
- package/dist/assets/vendor-CCJJTK99.js +411 -0
- package/dist/index.html +8 -8
- package/dist/plugins/@deepseek-ai/dsh-api-gateway/client.js +1513 -77
- package/dist/plugins/@deepseek-ai/dsh-api-remotes/client.js +3608 -757
- package/dist/plugins/@deepseek-ai/dsh-api-session-controller/client.js +2777 -0
- package/dist/plugins/@deepseek-ai/dsh-api-workspace-controller/client.js +415 -0
- package/dist/plugins/@deepseek-ai/dsh-client-connection/client.js +1975 -7466
- package/dist/plugins/@deepseek-ai/dsh-client-locale/client.js +225 -76
- package/dist/plugins/@deepseek-ai/dsh-client-modules/client.js +67 -15
- package/dist/plugins/@deepseek-ai/dsh-client-ui-agent-preset/client.js +270 -460
- package/dist/plugins/@deepseek-ai/dsh-client-ui-approval/client.js +292 -0
- package/dist/plugins/@deepseek-ai/dsh-client-ui-attachment/client.js +42 -17
- package/dist/plugins/@deepseek-ai/dsh-client-ui-brand-official/client.js +7 -9
- package/dist/plugins/@deepseek-ai/dsh-client-ui-chat/client.js +8177 -0
- package/dist/plugins/@deepseek-ai/dsh-client-ui-commands/client.js +22 -10
- package/dist/plugins/@deepseek-ai/dsh-client-ui-conversation/client.js +14950 -8910
- package/dist/plugins/@deepseek-ai/dsh-client-ui-deliverables/client.js +161 -137
- package/dist/plugins/@deepseek-ai/dsh-client-ui-goal/client.js +6 -7
- package/dist/plugins/@deepseek-ai/dsh-client-ui-input-trigger/client.js +268 -40
- package/dist/plugins/@deepseek-ai/dsh-client-ui-jobs/client.js +1 -1
- package/dist/plugins/@deepseek-ai/dsh-client-ui-layout/client.js +45 -11
- package/dist/plugins/@deepseek-ai/dsh-client-ui-message-feedback/client.js +30 -58
- package/dist/plugins/@deepseek-ai/dsh-client-ui-model-selection/client.js +188 -89
- package/dist/plugins/@deepseek-ai/dsh-client-ui-permission-presets/client.js +105 -75
- package/dist/plugins/@deepseek-ai/dsh-client-ui-renderer/client.js +650 -188
- package/dist/plugins/@deepseek-ai/dsh-client-ui-schedule/client.js +307 -0
- package/dist/plugins/@deepseek-ai/dsh-client-ui-session/client.js +340 -0
- package/dist/plugins/@deepseek-ai/dsh-client-ui-settings/client.js +57 -50
- package/dist/plugins/@deepseek-ai/dsh-client-ui-settings-general/client.js +134 -69
- package/dist/plugins/@deepseek-ai/dsh-client-ui-settings-models/client.js +575 -442
- package/dist/plugins/@deepseek-ai/dsh-client-ui-sidebar/client.js +24 -11
- package/dist/plugins/@deepseek-ai/dsh-client-ui-skill/client.js +13 -9
- package/dist/plugins/@deepseek-ai/dsh-client-ui-subagent/client.js +44 -20
- package/dist/plugins/@deepseek-ai/dsh-client-ui-theme/client.js +265 -94
- package/dist/plugins/@deepseek-ai/dsh-client-ui-tool/client.js +899 -433
- package/dist/plugins/@deepseek-ai/dsh-client-ui-trajectory/client.js +1472 -613
- package/dist/plugins/@deepseek-ai/dsh-client-ui-user-questions/client.js +249 -95
- package/dist/plugins/@deepseek-ai/dsh-client-ui-workflow-run/client.js +5 -5
- package/dist/plugins/@deepseek-ai/dsh-client-ui-workspace/client.js +425 -146
- package/dist/plugins/@deepseek-ai/dsh-typert-registry/client.js +29 -14
- package/dist/plugins/dsh-edge-client-ui/client.js +28 -26
- package/package.json +62 -58
- package/scripts/verify-packed.mjs +1 -1
- package/worker/direct/index.js +2866 -1466
- package/worker/isolated/index.js +2438 -1038
- package/dist/assets/index-C6eRlFa6.css +0 -1
- package/dist/assets/index-ClqxG24t.js +0 -96
- package/dist/assets/vendor-CjyC-hUb.css +0 -1
- package/dist/assets/vendor-D22_Mp1f.js +0 -411
- package/dist/plugins/@deepseek-ai/dsh-client-runtime/client.js +0 -10574
|
@@ -4,10 +4,160 @@ window.__ModuleLoader__.load({
|
|
|
4
4
|
var module = { exports: {} };
|
|
5
5
|
var exports = module.exports;
|
|
6
6
|
Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
|
|
7
|
-
let
|
|
7
|
+
let _deepseek_ai_cordis = require("@deepseek-ai/cordis");
|
|
8
|
+
let _deepseek_ai_dsh_client_store = require("@deepseek-ai/dsh-client-store");
|
|
8
9
|
let react_jsx_runtime = require("react/jsx-runtime");
|
|
9
10
|
let react = require("react");
|
|
10
11
|
let _deepseek_ai_dsh_client_ui_primitives = require("@deepseek-ai/dsh-client-ui-primitives");
|
|
12
|
+
//#region lib/types/client/navigation.js
|
|
13
|
+
/** Workspace archive and directory UI capability. */
|
|
14
|
+
/** Structured directory failure exposed to directory UI consumers. */
|
|
15
|
+
var DirectoryBrowseError = class extends Error {
|
|
16
|
+
rpcError;
|
|
17
|
+
name = "DirectoryBrowseError";
|
|
18
|
+
/** @param rpcError - Host directory business failure. */
|
|
19
|
+
constructor(rpcError) {
|
|
20
|
+
super(`directory browse failed: ${rpcError.code}: ${rpcError.message}`);
|
|
21
|
+
this.rpcError = rpcError;
|
|
22
|
+
}
|
|
23
|
+
};
|
|
24
|
+
/** Implements Workspace archive and directory UI operations. */
|
|
25
|
+
var UiWorkspaceService = class extends _deepseek_ai_cordis.Service {
|
|
26
|
+
directoryPicker;
|
|
27
|
+
workspaces;
|
|
28
|
+
sessions;
|
|
29
|
+
connecting = /* @__PURE__ */ new Map();
|
|
30
|
+
/**
|
|
31
|
+
* @param ctx - Client root Context.
|
|
32
|
+
* @param directoryPicker - the directory-picking Remote namespace.
|
|
33
|
+
* @param workspaces - pure Workspace Controller.
|
|
34
|
+
* @param sessions - pure Session Controller.
|
|
35
|
+
*/
|
|
36
|
+
constructor(ctx, directoryPicker, workspaces, sessions) {
|
|
37
|
+
super(ctx, "uiWorkspace");
|
|
38
|
+
this.directoryPicker = directoryPicker;
|
|
39
|
+
this.workspaces = workspaces;
|
|
40
|
+
this.sessions = sessions;
|
|
41
|
+
ctx.effect(() => this.watchNavigation(), "ui-workspace: Workspace navigation policy");
|
|
42
|
+
}
|
|
43
|
+
async connectWorkspace(workspaceId) {
|
|
44
|
+
const workspace = this.workspaces.list.getSnapshot().items.find((item) => item.workspaceId === workspaceId);
|
|
45
|
+
if (workspace === void 0) throw new Error(`uiWorkspace.connectWorkspace: unknown workspace ${workspaceId}`);
|
|
46
|
+
const inflight = this.connecting.get(workspaceId);
|
|
47
|
+
if (inflight !== void 0) return inflight;
|
|
48
|
+
const archived = this.workspaces.list.getSnapshot().archivedSessionIds;
|
|
49
|
+
const sessions = this.sessions.list.getSnapshot();
|
|
50
|
+
for (const id of sessions.ids) {
|
|
51
|
+
const summary = sessions.byId[id];
|
|
52
|
+
if (summary !== void 0 && summary.blank && summary.cwd === workspace.path && workspace.sessionIds.includes(summary.id) && !archived.includes(summary.id)) return summary.id;
|
|
53
|
+
}
|
|
54
|
+
const attempt = this.sessions.create({ workspaceId }).finally(() => {
|
|
55
|
+
this.connecting.delete(workspaceId);
|
|
56
|
+
});
|
|
57
|
+
this.connecting.set(workspaceId, attempt);
|
|
58
|
+
return attempt;
|
|
59
|
+
}
|
|
60
|
+
startSession(workspaceId) {
|
|
61
|
+
const workspace = this.workspaces.list.getSnapshot();
|
|
62
|
+
const sessions = this.sessions.list.getSnapshot();
|
|
63
|
+
const current = sessions.current;
|
|
64
|
+
const currentWorkspaceId = current === void 0 ? void 0 : workspace.items.find((item) => item.sessionIds.includes(current))?.workspaceId;
|
|
65
|
+
const recent = workspace.phase === "ready" && sessions.phase === "ready" ? recentWorkspace(workspace.items, sessions.byId) : void 0;
|
|
66
|
+
const target = workspaceId ?? currentWorkspaceId ?? recent;
|
|
67
|
+
if (target === void 0) {
|
|
68
|
+
this.sessions.clear();
|
|
69
|
+
return;
|
|
70
|
+
}
|
|
71
|
+
this.connectWorkspace(target).then((sessionId) => {
|
|
72
|
+
this.sessions.open(sessionId);
|
|
73
|
+
}, (reason) => {
|
|
74
|
+
console.warn("new session failed:", reason);
|
|
75
|
+
});
|
|
76
|
+
}
|
|
77
|
+
async archiveSession(sessionId) {
|
|
78
|
+
await this.workspaces.archiveSession(sessionId);
|
|
79
|
+
}
|
|
80
|
+
async pickDirectory() {
|
|
81
|
+
const result = await this.directoryPicker.pick();
|
|
82
|
+
if (!result.ok) throw new Error(`directory picker failed: ${result.error.message}`);
|
|
83
|
+
return result.value;
|
|
84
|
+
}
|
|
85
|
+
async listDirectory(path, signal) {
|
|
86
|
+
const result = await this.directoryPicker.list(path, signal);
|
|
87
|
+
if (!result.ok) throw new DirectoryBrowseError(result.error);
|
|
88
|
+
return result.value;
|
|
89
|
+
}
|
|
90
|
+
async createDirectory(path, name) {
|
|
91
|
+
const result = await this.directoryPicker.createDirectory(path, name);
|
|
92
|
+
if (!result.ok) throw new DirectoryBrowseError(result.error);
|
|
93
|
+
return result.value;
|
|
94
|
+
}
|
|
95
|
+
watchNavigation() {
|
|
96
|
+
let initial = "waiting";
|
|
97
|
+
let disposed = false;
|
|
98
|
+
const reconcile = () => {
|
|
99
|
+
if (disposed) return;
|
|
100
|
+
if (this.clearArchivedCurrent()) return;
|
|
101
|
+
if (initial !== "waiting") return;
|
|
102
|
+
const workspace = this.workspaces.list.getSnapshot();
|
|
103
|
+
const sessions = this.sessions.list.getSnapshot();
|
|
104
|
+
if (workspace.phase !== "ready" || sessions.phase !== "ready") return;
|
|
105
|
+
if (sessions.current !== void 0) {
|
|
106
|
+
initial = "done";
|
|
107
|
+
return;
|
|
108
|
+
}
|
|
109
|
+
const target = recentWorkspace(workspace.items, sessions.byId);
|
|
110
|
+
if (target === void 0) {
|
|
111
|
+
initial = "done";
|
|
112
|
+
return;
|
|
113
|
+
}
|
|
114
|
+
initial = "connecting";
|
|
115
|
+
this.connectWorkspace(target).then((sessionId) => {
|
|
116
|
+
if (disposed) return;
|
|
117
|
+
if (this.sessions.list.getSnapshot().current === void 0) this.sessions.open(sessionId);
|
|
118
|
+
initial = "done";
|
|
119
|
+
}, (reason) => {
|
|
120
|
+
if (disposed) return;
|
|
121
|
+
initial = "waiting";
|
|
122
|
+
console.warn("initial workspace selection failed:", reason);
|
|
123
|
+
});
|
|
124
|
+
};
|
|
125
|
+
const disposeWorkspaces = this.workspaces.list.subscribe(reconcile);
|
|
126
|
+
const disposeSessions = this.sessions.list.subscribe(reconcile);
|
|
127
|
+
reconcile();
|
|
128
|
+
return () => {
|
|
129
|
+
disposed = true;
|
|
130
|
+
disposeSessions();
|
|
131
|
+
disposeWorkspaces();
|
|
132
|
+
};
|
|
133
|
+
}
|
|
134
|
+
/** @returns true when an archived current selection was cleared. */
|
|
135
|
+
clearArchivedCurrent() {
|
|
136
|
+
const current = this.sessions.list.getSnapshot().current;
|
|
137
|
+
if (current === void 0 || !this.workspaces.list.getSnapshot().archivedSessionIds.includes(current)) return false;
|
|
138
|
+
this.sessions.clear();
|
|
139
|
+
return true;
|
|
140
|
+
}
|
|
141
|
+
};
|
|
142
|
+
/** Stable tie-breaking follows Host Workspace order. */
|
|
143
|
+
function recentWorkspace(workspaces, sessions) {
|
|
144
|
+
let selected;
|
|
145
|
+
let selectedTime = Number.NEGATIVE_INFINITY;
|
|
146
|
+
for (const workspace of workspaces) {
|
|
147
|
+
let latest = Number.NEGATIVE_INFINITY;
|
|
148
|
+
for (const sessionId of workspace.sessionIds) {
|
|
149
|
+
const session = sessions[sessionId];
|
|
150
|
+
if (session !== void 0) latest = Math.max(latest, session.updatedAt);
|
|
151
|
+
}
|
|
152
|
+
if (latest === Number.NEGATIVE_INFINITY) latest = Date.parse(workspace.createdAt);
|
|
153
|
+
if (selected === void 0 || latest > selectedTime) {
|
|
154
|
+
selected = workspace.workspaceId;
|
|
155
|
+
selectedTime = latest;
|
|
156
|
+
}
|
|
157
|
+
}
|
|
158
|
+
return selected;
|
|
159
|
+
}
|
|
160
|
+
//#endregion
|
|
11
161
|
//#region lib/types/client/stores.js
|
|
12
162
|
/**
|
|
13
163
|
* The workspace browser's viewing store: the session-list grouping mode,
|
|
@@ -23,7 +173,7 @@ window.__ModuleLoader__.load({
|
|
|
23
173
|
* @returns the store handle (spec + type + identity + factory in one).
|
|
24
174
|
*/
|
|
25
175
|
function createWorkspaceViewStore() {
|
|
26
|
-
return (0,
|
|
176
|
+
return (0, _deepseek_ai_dsh_client_store.defineStore)({
|
|
27
177
|
init: () => ({
|
|
28
178
|
groupBy: "workspace",
|
|
29
179
|
orderBy: "updated",
|
|
@@ -73,18 +223,82 @@ window.__ModuleLoader__.load({
|
|
|
73
223
|
for (var e, t, f = 0, n = "", o = arguments.length; f < o; f++) (e = arguments[f]) && (t = r(e)) && (n && (n += " "), n += t);
|
|
74
224
|
return n;
|
|
75
225
|
}
|
|
76
|
-
|
|
77
|
-
|
|
226
|
+
//#endregion
|
|
227
|
+
//#region ../../util/workspace-path/src/index.ts
|
|
228
|
+
/**
|
|
229
|
+
* Browser-safe Workspace path and display helpers.
|
|
230
|
+
* @module @deepseek-ai/dsh-util-workspace-path
|
|
231
|
+
*/
|
|
232
|
+
/** Whether a path uses a Windows drive or UNC prefix. */
|
|
233
|
+
function isWindowsStylePath(value) {
|
|
234
|
+
return /^[A-Za-z]:[/\\]/.test(value) || value.startsWith("\\\\");
|
|
235
|
+
}
|
|
236
|
+
/**
|
|
237
|
+
* Abbreviate a POSIX home directory for display.
|
|
238
|
+
* @param path - Absolute or already-short display path.
|
|
239
|
+
* @param home - Host account home; absent skips abbreviation.
|
|
240
|
+
* @returns `~` or `~/…` for the POSIX home and its descendants, otherwise `path`.
|
|
241
|
+
*/
|
|
242
|
+
function abbreviateHomePath(path, home) {
|
|
243
|
+
if (home === void 0 || home === "") return path;
|
|
244
|
+
if (isWindowsStylePath(path) || isWindowsStylePath(home)) return path;
|
|
245
|
+
const root = home.replace(/\/+$/, "");
|
|
246
|
+
if (root === "" || root === "/") return path;
|
|
247
|
+
if (path.replace(/\/+$/, "") === root) return "~";
|
|
248
|
+
if (path.startsWith(`${root}/`)) return `~${path.slice(root.length)}`;
|
|
249
|
+
return path;
|
|
250
|
+
}
|
|
251
|
+
/**
|
|
252
|
+
* Read the final non-empty segment of a Workspace path for display.
|
|
253
|
+
* Workspace-label surfaces use this helper instead of deriving another basename.
|
|
254
|
+
* @param path - Workspace directory path using POSIX or Windows separators.
|
|
255
|
+
* @returns the final segment, or an empty string for a separator-only path.
|
|
256
|
+
*/
|
|
257
|
+
function workspaceTitleOf(path) {
|
|
258
|
+
const trimmed = path.replace(/[/\\]+$/, "");
|
|
259
|
+
const separator = Math.max(trimmed.lastIndexOf("/"), trimmed.lastIndexOf("\\"));
|
|
260
|
+
return trimmed.slice(separator + 1);
|
|
261
|
+
}
|
|
262
|
+
//#endregion
|
|
263
|
+
//#region lib/types/client/subagent-lineage.js
|
|
264
|
+
/** UI Workspace-owned projection of descendant counts from Session summaries. */
|
|
265
|
+
/**
|
|
266
|
+
* Index uninterrupted subagent descendants under each ancestor.
|
|
267
|
+
* @param summaries - Session summaries keyed by id.
|
|
268
|
+
* @returns descendant totals keyed by possible parent id.
|
|
269
|
+
*/
|
|
270
|
+
function indexSubagentDescendants(summaries) {
|
|
271
|
+
const indexed = /* @__PURE__ */ new Map();
|
|
272
|
+
for (const descendant of Object.values(summaries)) {
|
|
273
|
+
if (descendant.origin !== "subagent") continue;
|
|
274
|
+
const seen = /* @__PURE__ */ new Set();
|
|
275
|
+
let current = descendant;
|
|
276
|
+
while (current?.origin === "subagent" && current.parentId !== void 0 && !seen.has(current.id)) {
|
|
277
|
+
seen.add(current.id);
|
|
278
|
+
const aggregate = indexed.get(current.parentId);
|
|
279
|
+
if (aggregate === void 0) indexed.set(current.parentId, {
|
|
280
|
+
count: 1,
|
|
281
|
+
runningCount: descendant.running ? 1 : 0
|
|
282
|
+
});
|
|
283
|
+
else {
|
|
284
|
+
aggregate.count += 1;
|
|
285
|
+
if (descendant.running) aggregate.runningCount += 1;
|
|
286
|
+
}
|
|
287
|
+
current = summaries[current.parentId];
|
|
288
|
+
}
|
|
289
|
+
}
|
|
290
|
+
return indexed;
|
|
291
|
+
}
|
|
78
292
|
/**
|
|
79
293
|
* Directory display label: basename of the path (both separators accepted).
|
|
80
294
|
* Ungrouped-bucket fallback for surfaces without a workspace title.
|
|
81
295
|
* @param cwd - directory path, or undefined for the ungrouped bucket.
|
|
82
|
-
* @returns basename, the raw cwd when it has no basename, or
|
|
296
|
+
* @returns basename, the raw cwd when it has no basename, or an empty ungrouped marker.
|
|
83
297
|
*/
|
|
84
298
|
function workspaceLabel(cwd) {
|
|
85
|
-
if (cwd === void 0 || cwd === "") return
|
|
86
|
-
const base = cwd
|
|
87
|
-
return base !==
|
|
299
|
+
if (cwd === void 0 || cwd === "") return "";
|
|
300
|
+
const base = workspaceTitleOf(cwd);
|
|
301
|
+
return base !== "" ? base : cwd;
|
|
88
302
|
}
|
|
89
303
|
/** Recency comparator: newest first, id as the deterministic tiebreak (ids are unique per group). */
|
|
90
304
|
function byRecency(a, b) {
|
|
@@ -106,7 +320,11 @@ window.__ModuleLoader__.load({
|
|
|
106
320
|
* and the renderer localizes its display label.
|
|
107
321
|
*/
|
|
108
322
|
function sessionTitle(session) {
|
|
109
|
-
return session.blank ? "
|
|
323
|
+
return session.blank ? "" : session.displayTitle;
|
|
324
|
+
}
|
|
325
|
+
/** The list projection alone owns the best-effort active-Schedule indicator. */
|
|
326
|
+
function hasActiveSchedule(session) {
|
|
327
|
+
return (session.projectionValues?.schedule?.length ?? 0) > 0;
|
|
110
328
|
}
|
|
111
329
|
/** Build one group without projecting session lineage into presentation. */
|
|
112
330
|
function buildGroup(key, workspaceId, cwd, createdAt, label, members, order) {
|
|
@@ -159,10 +377,20 @@ window.__ModuleLoader__.load({
|
|
|
159
377
|
groups.push(buildGroup(workspace.workspaceId, workspace.workspaceId, workspace.path, Date.parse(workspace.createdAt), workspace.title, members, "account"));
|
|
160
378
|
}
|
|
161
379
|
const stray = list.ids.map((id) => list.byId[id]).filter((s) => s !== void 0 && !accounted.has(s.id) && sessionVisible(s, list.current, archived));
|
|
162
|
-
if (stray.length > 0) groups.push(buildGroup("", void 0, void 0, void 0,
|
|
380
|
+
if (stray.length > 0) groups.push(buildGroup("", void 0, void 0, void 0, "", ungroupedOrder === void 0 ? stray : orderedUngrouped(stray, ungroupedOrder), ungroupedOrder === void 0 ? "recency" : "account"));
|
|
163
381
|
return groups;
|
|
164
382
|
}
|
|
165
|
-
|
|
383
|
+
/** Keep navigation presentation independent from domain-owned interaction objects. */
|
|
384
|
+
function visiblePendingKind(kind) {
|
|
385
|
+
switch (kind) {
|
|
386
|
+
case "approval":
|
|
387
|
+
case "plan-review":
|
|
388
|
+
case "question": return kind;
|
|
389
|
+
default: return;
|
|
390
|
+
}
|
|
391
|
+
}
|
|
392
|
+
function sessionNode(s, descendants, pendingInteractions) {
|
|
393
|
+
const pendingInteraction = visiblePendingKind(pendingInteractions.get(s.id)?.kind);
|
|
166
394
|
return {
|
|
167
395
|
id: s.id,
|
|
168
396
|
title: sessionTitle(s),
|
|
@@ -170,8 +398,9 @@ window.__ModuleLoader__.load({
|
|
|
170
398
|
running: s.running,
|
|
171
399
|
runningSubagentCount: descendants.get(s.id)?.runningCount ?? 0,
|
|
172
400
|
completed: s.completed === true,
|
|
401
|
+
hasActiveSchedule: hasActiveSchedule(s),
|
|
173
402
|
updatedAt: s.updatedAt,
|
|
174
|
-
...
|
|
403
|
+
...pendingInteraction === void 0 ? {} : { pendingInteraction }
|
|
175
404
|
};
|
|
176
405
|
}
|
|
177
406
|
/**
|
|
@@ -185,13 +414,14 @@ window.__ModuleLoader__.load({
|
|
|
185
414
|
* @param list - sessions list snapshot (`current` feeds containsCurrent).
|
|
186
415
|
* @param workspaces - real workspaces in stable Host order.
|
|
187
416
|
* @param archivedSessionIds - registry-global archive set.
|
|
417
|
+
* @param pendingInteractions - pending UI interactions by Session.
|
|
188
418
|
* @param view - local expansion arrays.
|
|
189
419
|
* @returns group sections in render order.
|
|
190
420
|
*/
|
|
191
|
-
function deriveGroups(list, workspaces, archivedSessionIds, view) {
|
|
421
|
+
function deriveGroups(list, workspaces, archivedSessionIds, pendingInteractions, view) {
|
|
192
422
|
const archived = new Set(archivedSessionIds);
|
|
193
423
|
const expandedGroups = new Set(view.expandedGroups);
|
|
194
|
-
const descendants =
|
|
424
|
+
const descendants = indexSubagentDescendants(list.byId);
|
|
195
425
|
const currentGroup = list.current === void 0 ? void 0 : workspaces.find((w) => w.sessionIds.includes(list.current))?.workspaceId ?? "";
|
|
196
426
|
const groups = [];
|
|
197
427
|
for (const g of groupByWorkspace(list, workspaces, archived, view.ungroupedOrder)) {
|
|
@@ -205,7 +435,7 @@ window.__ModuleLoader__.load({
|
|
|
205
435
|
sessionCount: g.sessions.length,
|
|
206
436
|
expanded,
|
|
207
437
|
containsCurrent: g.key === currentGroup,
|
|
208
|
-
sessions: expanded ? g.sessions.map((session) => sessionNode(session, descendants)) : []
|
|
438
|
+
sessions: expanded ? g.sessions.map((session) => sessionNode(session, descendants, pendingInteractions)) : []
|
|
209
439
|
});
|
|
210
440
|
}
|
|
211
441
|
return groups;
|
|
@@ -217,11 +447,12 @@ window.__ModuleLoader__.load({
|
|
|
217
447
|
* (see {@link deriveSearchResults}).
|
|
218
448
|
* @param list - sessions list snapshot.
|
|
219
449
|
* @param archivedSessionIds - registry-global archive set.
|
|
450
|
+
* @param pendingInteractions - pending UI interactions by Session.
|
|
220
451
|
* @returns flat rows in render order.
|
|
221
452
|
*/
|
|
222
|
-
function deriveFlat(list, archivedSessionIds) {
|
|
453
|
+
function deriveFlat(list, archivedSessionIds, pendingInteractions) {
|
|
223
454
|
const archived = new Set(archivedSessionIds);
|
|
224
|
-
const descendants =
|
|
455
|
+
const descendants = indexSubagentDescendants(list.byId);
|
|
225
456
|
const rows = [];
|
|
226
457
|
for (const id of list.ids) {
|
|
227
458
|
const s = list.byId[id];
|
|
@@ -229,7 +460,7 @@ window.__ModuleLoader__.load({
|
|
|
229
460
|
rows.push(s);
|
|
230
461
|
}
|
|
231
462
|
rows.sort(byRecency);
|
|
232
|
-
return rows.map((session) => sessionNode(session, descendants));
|
|
463
|
+
return rows.map((session) => sessionNode(session, descendants, pendingInteractions));
|
|
233
464
|
}
|
|
234
465
|
/**
|
|
235
466
|
* Merge immediate title/Workspace substring matches with ranked Host content
|
|
@@ -239,18 +470,19 @@ window.__ModuleLoader__.load({
|
|
|
239
470
|
* @param workspaces - Workspace membership and display labels.
|
|
240
471
|
* @param query - caller text; surrounding whitespace is ignored.
|
|
241
472
|
* @param archivedSessionIds - registry-global archive set (members never match).
|
|
473
|
+
* @param pendingInteractions - pending UI interactions by Session.
|
|
242
474
|
* @param content - ranked Host content-search page.
|
|
243
475
|
* @param limit - protocol-owned maximum merged row count.
|
|
244
476
|
* @returns bounded deduplicated flat rows and a refine-query hint bit.
|
|
245
477
|
*/
|
|
246
|
-
function deriveSearchResults(list, workspaces, query, archivedSessionIds, content, limit) {
|
|
478
|
+
function deriveSearchResults(list, workspaces, query, archivedSessionIds, pendingInteractions, content, limit) {
|
|
247
479
|
const q = query.trim().toLowerCase();
|
|
248
480
|
if (q === "") return {
|
|
249
481
|
items: [],
|
|
250
482
|
hasMore: false
|
|
251
483
|
};
|
|
252
484
|
const archived = new Set(archivedSessionIds);
|
|
253
|
-
const descendants =
|
|
485
|
+
const descendants = indexSubagentDescendants(list.byId);
|
|
254
486
|
const workspaceBySession = /* @__PURE__ */ new Map();
|
|
255
487
|
for (const workspace of workspaces) for (const sessionId of workspace.sessionIds) if (!workspaceBySession.has(sessionId)) workspaceBySession.set(sessionId, workspace.title);
|
|
256
488
|
const labelOf = (summary) => workspaceBySession.get(summary.id) ?? workspaceLabel(summary.cwd);
|
|
@@ -278,60 +510,25 @@ window.__ModuleLoader__.load({
|
|
|
278
510
|
return {
|
|
279
511
|
items: ordered.slice(0, limit).map((summary) => {
|
|
280
512
|
const match = contentBySession.get(summary.id);
|
|
513
|
+
const pendingInteraction = visiblePendingKind(pendingInteractions.get(summary.id)?.kind);
|
|
281
514
|
return {
|
|
282
515
|
id: summary.id,
|
|
283
516
|
title: sessionTitle(summary),
|
|
284
517
|
workspace: labelOf(summary),
|
|
285
518
|
running: summary.running,
|
|
286
519
|
runningSubagentCount: descendants.get(summary.id)?.runningCount ?? 0,
|
|
287
|
-
...
|
|
520
|
+
...pendingInteraction === void 0 ? {} : { pendingInteraction },
|
|
288
521
|
completed: summary.completed === true,
|
|
522
|
+
hasActiveSchedule: hasActiveSchedule(summary),
|
|
289
523
|
...match === void 0 ? {} : { snippet: match.snippet }
|
|
290
524
|
};
|
|
291
525
|
}),
|
|
292
526
|
hasMore: content.hasMore || ordered.length > limit
|
|
293
527
|
};
|
|
294
528
|
}
|
|
295
|
-
/**
|
|
296
|
-
* Compact relative time for session rows, as a structured bucket the
|
|
297
|
-
* renderer localizes ("now"/"5min"/"3h"/"2d"/"4mo"/"1y" in en).
|
|
298
|
-
* @param updatedAt - epoch ms of the session's last activity.
|
|
299
|
-
* @param now - current epoch ms (injected for pure rendering).
|
|
300
|
-
* @returns the row's trailing time bucket and magnitude.
|
|
301
|
-
*/
|
|
302
|
-
function relativeTime(updatedAt, now) {
|
|
303
|
-
const MIN = 6e4;
|
|
304
|
-
const HOUR = 36e5;
|
|
305
|
-
const DAY = 864e5;
|
|
306
|
-
const diff = Math.max(0, now - updatedAt);
|
|
307
|
-
if (diff < MIN) return {
|
|
308
|
-
unit: "now",
|
|
309
|
-
n: 0
|
|
310
|
-
};
|
|
311
|
-
if (diff < HOUR) return {
|
|
312
|
-
unit: "minutes",
|
|
313
|
-
n: Math.floor(diff / MIN)
|
|
314
|
-
};
|
|
315
|
-
if (diff < DAY) return {
|
|
316
|
-
unit: "hours",
|
|
317
|
-
n: Math.floor(diff / HOUR)
|
|
318
|
-
};
|
|
319
|
-
if (diff < 30 * DAY) return {
|
|
320
|
-
unit: "days",
|
|
321
|
-
n: Math.floor(diff / DAY)
|
|
322
|
-
};
|
|
323
|
-
if (diff < 365 * DAY) return {
|
|
324
|
-
unit: "months",
|
|
325
|
-
n: Math.floor(diff / (30 * DAY))
|
|
326
|
-
};
|
|
327
|
-
return {
|
|
328
|
-
unit: "years",
|
|
329
|
-
n: Math.floor(diff / (365 * DAY))
|
|
330
|
-
};
|
|
331
|
-
}
|
|
332
529
|
//#endregion
|
|
333
530
|
//#region \0dsh-css:/home/runner/work/deepseek-harness/deepseek-harness/packages/client/ui-workspace/src/client/rows/Rows.module.css.mjs
|
|
334
|
-
const css$2 = ".YDXeBa_projectRow,.YDXeBa_sessionRow{cursor:pointer;user-select:none;color:var(--dsw-alias-label-primary);border-radius:8px;align-items:center;gap:6px;padding:0 8px;display:flex}.YDXeBa_projectRow:hover,.YDXeBa_sessionRow:hover,.YDXeBa_sessionRow.YDXeBa_selected{background:var(--dsw-alias-interactive-bg-hover)}.YDXeBa_searchResultRow{box-sizing:border-box;cursor:pointer;text-align:left;width:100%;min-height:48px;color:var(--dsw-alias-label-primary);background:0 0;border:none;border-radius:8px;flex-direction:column;align-items:stretch;padding:4px 8px;display:flex}.YDXeBa_searchResultRow:hover,.YDXeBa_searchResultRow.YDXeBa_selected{background:var(--dsw-alias-interactive-bg-hover)}.YDXeBa_searchResultHeading{align-items:center;min-width:0;display:flex}.YDXeBa_searchResultTitle{text-overflow:ellipsis;white-space:nowrap;min-width:0;margin-left:4px;font-size:14px;line-height:20px;overflow:hidden}.YDXeBa_searchResultMeta{align-items:center;gap:6px;min-width:0;margin-left:20px;display:flex}.YDXeBa_searchResultWorkspace,.YDXeBa_searchResultSnippet{text-overflow:ellipsis;white-space:nowrap;font-size:12px;line-height:17px;overflow:hidden}.YDXeBa_searchResultWorkspace{max-width:40%;color:var(--dsw-alias-label-tertiary);flex:none}.YDXeBa_searchResultSnippet{min-width:0;color:var(--dsw-alias-label-secondary);flex:1}.YDXeBa_projectRow{box-sizing:border-box;align-items:center;height:34px}.YDXeBa_projectRow .YDXeBa_rowActions{height:20px}.YDXeBa_sessionRow{height:32px;animation:YDXeBa_row-in .15s var(--ds-ease-in-out);gap:0}.YDXeBa_sessionRow .YDXeBa_title{margin:0 6px 0 4px}.YDXeBa_flatSessionRowWithoutStatus .YDXeBa_title{margin-left:0}@keyframes YDXeBa_row-in{0%{opacity:0}}.YDXeBa_slot{width:16px;height:20px;color:var(--dsw-alias-label-tertiary);flex:none;justify-content:center;align-items:center;display:inline-flex}.YDXeBa_visuallyHidden{clip:rect(0 0 0 0);white-space:nowrap;width:1px;height:1px;position:absolute;overflow:hidden}.YDXeBa_folderActive{color:var(--dsw-alias-state-business-primary)}.YDXeBa_projectRow .YDXeBa_chevron{display:none}.YDXeBa_projectRow:hover .YDXeBa_chevron{display:inline-flex}.YDXeBa_projectRow:hover .YDXeBa_folder{display:none}.YDXeBa_arrow{transition:transform .15s var(--ds-ease-in-out)}.YDXeBa_arrowOpen{transform:rotate(90deg)}.YDXeBa_projectText{flex-direction:column;flex:1;gap:2px;min-width:0;display:flex}.YDXeBa_title{text-overflow:ellipsis;white-space:nowrap;min-width:0;font-size:14px;line-height:20px;overflow:hidden}.YDXeBa_renameInput{border
|
|
531
|
+
const css$2 = ".YDXeBa_projectRow,.YDXeBa_sessionRow{cursor:pointer;user-select:none;color:var(--dsw-alias-label-primary);border-radius:8px;align-items:center;gap:6px;padding:0 8px;display:flex}.YDXeBa_projectRow:hover,.YDXeBa_sessionRow:hover,.YDXeBa_sessionRow.YDXeBa_selected{background:var(--dsw-alias-interactive-bg-hover)}.YDXeBa_searchResultRow{box-sizing:border-box;cursor:pointer;text-align:left;width:100%;min-height:48px;color:var(--dsw-alias-label-primary);background:0 0;border:none;border-radius:8px;flex-direction:column;align-items:stretch;padding:4px 8px;display:flex}.YDXeBa_searchResultRow:hover,.YDXeBa_searchResultRow.YDXeBa_selected{background:var(--dsw-alias-interactive-bg-hover)}.YDXeBa_searchResultHeading{align-items:center;min-width:0;display:flex}.YDXeBa_searchResultTitle{text-overflow:ellipsis;white-space:nowrap;flex:0 auto;min-width:0;margin-left:4px;font-size:14px;line-height:20px;overflow:hidden}.YDXeBa_searchResultMeta{align-items:center;gap:6px;min-width:0;margin-left:20px;display:flex}.YDXeBa_searchResultWorkspace,.YDXeBa_searchResultSnippet{text-overflow:ellipsis;white-space:nowrap;font-size:12px;line-height:17px;overflow:hidden}.YDXeBa_searchResultWorkspace{max-width:40%;color:var(--dsw-alias-label-tertiary);flex:none}.YDXeBa_searchResultSnippet{min-width:0;color:var(--dsw-alias-label-secondary);flex:1}.YDXeBa_projectRow{box-sizing:border-box;align-items:center;height:34px}.YDXeBa_projectRow .YDXeBa_rowActions{height:20px}.YDXeBa_sessionRow{height:32px;animation:YDXeBa_row-in .15s var(--ds-ease-in-out);gap:0}.YDXeBa_sessionRow .YDXeBa_title{margin:0 6px 0 4px}.YDXeBa_flatSessionRowWithoutStatus .YDXeBa_title{margin-left:0}@keyframes YDXeBa_row-in{0%{opacity:0}}.YDXeBa_slot{width:16px;height:20px;color:var(--dsw-alias-label-tertiary);flex:none;justify-content:center;align-items:center;display:inline-flex}.YDXeBa_visuallyHidden{clip:rect(0 0 0 0);white-space:nowrap;width:1px;height:1px;position:absolute;overflow:hidden}.YDXeBa_folderActive{color:var(--dsw-alias-state-business-primary)}.YDXeBa_projectRow .YDXeBa_chevron{display:none}.YDXeBa_projectRow:hover .YDXeBa_chevron{display:inline-flex}.YDXeBa_projectRow:hover .YDXeBa_folder{display:none}.YDXeBa_arrow{transition:transform .15s var(--ds-ease-in-out)}.YDXeBa_arrowOpen{transform:rotate(90deg)}.YDXeBa_projectText{flex-direction:column;flex:1;gap:2px;min-width:0;display:flex}.YDXeBa_title{text-overflow:ellipsis;white-space:nowrap;min-width:0;font-size:14px;line-height:20px;overflow:hidden}.YDXeBa_renameInput{border:.5px solid var(--dsw-alias-border-l4);background:var(--dsw-alias-button-elevated-fill);min-width:0;color:inherit;border-radius:4px;outline:none;padding:0 2px;font-size:14px;line-height:20px}.YDXeBa_sessionRow .YDXeBa_title{flex:1}.YDXeBa_meta{text-overflow:ellipsis;white-space:nowrap;color:var(--dsw-alias-label-tertiary);font-size:12px;line-height:20px;overflow:hidden}.YDXeBa_time{color:var(--dsw-alias-label-tertiary);flex:none;font-size:12px;line-height:20px}.YDXeBa_scheduleIndicator{width:16px;height:20px;color:var(--dsw-alias-label-tertiary);flex:none;justify-content:center;align-items:center;margin-right:6px;display:inline-flex}.YDXeBa_searchScheduleIndicator{margin-left:4px;margin-right:0}.YDXeBa_dot{flex:none}.YDXeBa_rowActions{flex:none;align-items:center;gap:12px;display:none}.YDXeBa_projectRow:hover .YDXeBa_rowActions,.YDXeBa_sessionRow:hover .YDXeBa_rowActions,.YDXeBa_projectRow.YDXeBa_menuOpen .YDXeBa_rowActions,.YDXeBa_sessionRow.YDXeBa_menuOpen .YDXeBa_rowActions{display:inline-flex}.YDXeBa_sessionRow:hover .YDXeBa_time,.YDXeBa_sessionRow.YDXeBa_menuOpen .YDXeBa_time{display:none}.YDXeBa_projectRow.YDXeBa_menuOpen,.YDXeBa_sessionRow.YDXeBa_menuOpen{background:var(--dsw-alias-interactive-bg-hover)}.YDXeBa_sessionRow.YDXeBa_dropBefore,.YDXeBa_sessionRow.YDXeBa_dropAfter{position:relative}.YDXeBa_sessionRow.YDXeBa_dropBefore:before,.YDXeBa_sessionRow.YDXeBa_dropAfter:after{content:\"\";z-index:1;background:linear-gradient(55deg, transparent calc(50% - 1px), var(--dsw-alias-state-business-primary) calc(50% - 1px) calc(50% + 1px), transparent calc(50% + 1px)) 0 0 / 5px 7px no-repeat, linear-gradient(125deg, transparent calc(50% - 1px), var(--dsw-alias-state-business-primary) calc(50% - 1px) calc(50% + 1px), transparent calc(50% + 1px)) 0 5px / 5px 7px no-repeat, linear-gradient(var(--dsw-alias-state-business-primary) 0 0) 4px 5px / calc(100% - 4px) 2px no-repeat;pointer-events:none;height:12px;position:absolute;left:0;right:4px}.YDXeBa_sessionRow.YDXeBa_dropBefore:before{top:-7px}.YDXeBa_sessionRow.YDXeBa_dropAfter:after{bottom:-7px}.YDXeBa_hoverContent{flex-direction:column;gap:8px;display:flex}.YDXeBa_hoverTitle{color:#fff;overflow-wrap:break-word;font-size:14px;line-height:20px}.YDXeBa_hoverPath{color:#cfd3d6;word-break:break-all;font-size:12px;line-height:16px}.YDXeBa_hoverTime{color:#cfd3d6;font-size:12px;line-height:16px}.YDXeBa_hoverStatus{color:#adb2b8;align-items:center;gap:8px;font-size:12px;line-height:20px;display:flex}.YDXeBa_iconButton{cursor:pointer;width:16px;height:16px;color:var(--dsw-alias-label-tertiary);background:0 0;border:none;border-radius:4px;flex:none;justify-content:center;align-items:center;padding:0;display:inline-flex}.YDXeBa_iconButton:hover{color:var(--dsw-alias-label-primary)}.YDXeBa_chevron{color:var(--dsw-alias-label-caption)}@media (prefers-reduced-motion:reduce){.YDXeBa_sessionRow,.YDXeBa_arrow{transition:none;animation:none}}";
|
|
335
532
|
const tagId$2 = "@deepseek-ai/dsh-client-ui-workspace/Rows.module.css";
|
|
336
533
|
if (typeof document !== "undefined" && document.querySelector("style[data-plugin-css=" + JSON.stringify(tagId$2) + "]") === null) {
|
|
337
534
|
const tag = document.createElement("style");
|
|
@@ -363,12 +560,14 @@ window.__ModuleLoader__.load({
|
|
|
363
560
|
"renameInput": "YDXeBa_renameInput",
|
|
364
561
|
"row-in": "YDXeBa_row-in",
|
|
365
562
|
"rowActions": "YDXeBa_rowActions",
|
|
563
|
+
"scheduleIndicator": "YDXeBa_scheduleIndicator",
|
|
366
564
|
"searchResultHeading": "YDXeBa_searchResultHeading",
|
|
367
565
|
"searchResultMeta": "YDXeBa_searchResultMeta",
|
|
368
566
|
"searchResultRow": "YDXeBa_searchResultRow",
|
|
369
567
|
"searchResultSnippet": "YDXeBa_searchResultSnippet",
|
|
370
568
|
"searchResultTitle": "YDXeBa_searchResultTitle",
|
|
371
569
|
"searchResultWorkspace": "YDXeBa_searchResultWorkspace",
|
|
570
|
+
"searchScheduleIndicator": "YDXeBa_searchScheduleIndicator",
|
|
372
571
|
"selected": "YDXeBa_selected",
|
|
373
572
|
"sessionRow": "YDXeBa_sessionRow",
|
|
374
573
|
"slot": "YDXeBa_slot",
|
|
@@ -391,12 +590,12 @@ window.__ModuleLoader__.load({
|
|
|
391
590
|
}
|
|
392
591
|
/** Localized compact relative time ("刚刚"/"5分钟" in zh, "now"/"5min" in en). */
|
|
393
592
|
function timeLabel(updatedAt, now, t) {
|
|
394
|
-
const { unit, n } = relativeTime(updatedAt, now);
|
|
593
|
+
const { unit, n } = (0, _deepseek_ai_dsh_client_ui_primitives.relativeTime)(updatedAt, now);
|
|
395
594
|
return unit === "now" ? t("time.now") : t(`time.${unit}`, { n });
|
|
396
595
|
}
|
|
397
596
|
/** Hover-card variant: distances wrap in the ago template; the now bucket stays bare (no "now ago"). */
|
|
398
597
|
function hoverTimeLabel(updatedAt, now, t) {
|
|
399
|
-
const { unit, n } = relativeTime(updatedAt, now);
|
|
598
|
+
const { unit, n } = (0, _deepseek_ai_dsh_client_ui_primitives.relativeTime)(updatedAt, now);
|
|
400
599
|
return unit === "now" ? t("time.now") : t("time.ago", { t: t(`time.${unit}`, { n }) });
|
|
401
600
|
}
|
|
402
601
|
/**
|
|
@@ -504,7 +703,7 @@ window.__ModuleLoader__.load({
|
|
|
504
703
|
items: workspaceMenuItems,
|
|
505
704
|
onSelect: (id) => {
|
|
506
705
|
setMenuOpen(false);
|
|
507
|
-
/* v8 ignore next --
|
|
706
|
+
/* v8 ignore next -- Menu can emit only the rename and delete rows supplied above. */
|
|
508
707
|
if (id !== "rename" && id !== "delete") return;
|
|
509
708
|
if (id === "rename") actions.rename();
|
|
510
709
|
else actions.delete();
|
|
@@ -539,7 +738,7 @@ window.__ModuleLoader__.load({
|
|
|
539
738
|
anchor: ownRow,
|
|
540
739
|
content: (0, react_jsx_runtime.jsx)(WorkspaceHoverContent, {
|
|
541
740
|
label: row.label,
|
|
542
|
-
cwd: row.cwd === void 0 ? void 0 :
|
|
741
|
+
cwd: row.cwd === void 0 ? void 0 : abbreviateHomePath(row.cwd, home),
|
|
543
742
|
createdAt: row.createdAt,
|
|
544
743
|
t
|
|
545
744
|
}),
|
|
@@ -611,6 +810,17 @@ window.__ModuleLoader__.load({
|
|
|
611
810
|
children: status.label
|
|
612
811
|
}, status.label))] });
|
|
613
812
|
}
|
|
813
|
+
/** Non-interactive active-Schedule marker; the enclosing row remains the only action. */
|
|
814
|
+
function ActiveScheduleIndicator({ t, search = false }) {
|
|
815
|
+
const label = t("schedule.active");
|
|
816
|
+
return (0, react_jsx_runtime.jsx)("span", {
|
|
817
|
+
className: clsx(Rows_module_css_default.scheduleIndicator, search && Rows_module_css_default.searchScheduleIndicator),
|
|
818
|
+
role: "img",
|
|
819
|
+
"aria-label": label,
|
|
820
|
+
title: label,
|
|
821
|
+
children: (0, react_jsx_runtime.jsx)(_deepseek_ai_dsh_client_ui_primitives.IconAlarmClockOutline16, {})
|
|
822
|
+
});
|
|
823
|
+
}
|
|
614
824
|
/** Hover-card body: full title, relative time, and every relevant live status. */
|
|
615
825
|
function SessionHoverContent({ node, now, t }) {
|
|
616
826
|
const statuses = sessionStatuses(node, t);
|
|
@@ -656,18 +866,25 @@ window.__ModuleLoader__.load({
|
|
|
656
866
|
},
|
|
657
867
|
children: [(0, react_jsx_runtime.jsxs)("span", {
|
|
658
868
|
className: Rows_module_css_default.searchResultHeading,
|
|
659
|
-
children: [
|
|
660
|
-
|
|
661
|
-
|
|
662
|
-
|
|
663
|
-
|
|
664
|
-
|
|
665
|
-
|
|
869
|
+
children: [
|
|
870
|
+
(0, react_jsx_runtime.jsx)("span", {
|
|
871
|
+
className: Rows_module_css_default.slot,
|
|
872
|
+
children: (primaryStatus.state !== "done" || result.completed) && (0, react_jsx_runtime.jsx)(SessionStatusDots, { statuses })
|
|
873
|
+
}),
|
|
874
|
+
(0, react_jsx_runtime.jsx)("span", {
|
|
875
|
+
className: Rows_module_css_default.searchResultTitle,
|
|
876
|
+
children: result.title
|
|
877
|
+
}),
|
|
878
|
+
result.hasActiveSchedule && (0, react_jsx_runtime.jsx)(ActiveScheduleIndicator, {
|
|
879
|
+
t,
|
|
880
|
+
search: true
|
|
881
|
+
})
|
|
882
|
+
]
|
|
666
883
|
}), (0, react_jsx_runtime.jsxs)("span", {
|
|
667
884
|
className: Rows_module_css_default.searchResultMeta,
|
|
668
885
|
children: [(0, react_jsx_runtime.jsx)("span", {
|
|
669
886
|
className: Rows_module_css_default.searchResultWorkspace,
|
|
670
|
-
children: result.workspace
|
|
887
|
+
children: result.workspace || t("group.ungrouped")
|
|
671
888
|
}), result.snippet !== void 0 && (0, react_jsx_runtime.jsx)("span", {
|
|
672
889
|
className: Rows_module_css_default.searchResultSnippet,
|
|
673
890
|
children: result.snippet
|
|
@@ -749,6 +966,7 @@ window.__ModuleLoader__.load({
|
|
|
749
966
|
className: Rows_module_css_default.title,
|
|
750
967
|
children: title
|
|
751
968
|
}),
|
|
969
|
+
row.hasActiveSchedule && (0, react_jsx_runtime.jsx)(ActiveScheduleIndicator, { t }),
|
|
752
970
|
!row.blank && (0, react_jsx_runtime.jsx)("span", {
|
|
753
971
|
className: Rows_module_css_default.time,
|
|
754
972
|
children: timeLabel(row.updatedAt, now, t)
|
|
@@ -965,8 +1183,8 @@ window.__ModuleLoader__.load({
|
|
|
965
1183
|
});
|
|
966
1184
|
}
|
|
967
1185
|
//#endregion
|
|
968
|
-
//#region \0dsh-css:/home/runner/work/deepseek-harness/deepseek-harness/packages/client/ui-workspace/src/client/WorkspaceBrowser.module.css.mjs
|
|
969
|
-
const css = ".
|
|
1186
|
+
//#region \0dsh-css:/home/runner/work/deepseek-harness/deepseek-harness/packages/client/ui-workspace/src/client/rows/WorkspaceBrowser.module.css.mjs
|
|
1187
|
+
const css = ".bhn1Oq_root{--dsh-session-list-edge-inset:var(--dsh-sidebar-inline-padding);--dsh-session-list-scrollbar-width:8px;--dsh-session-list-scrollbar-offset:2px;box-sizing:border-box;min-height:0;padding-right:var(--dsh-session-list-edge-inset);flex-direction:column;flex:1;display:flex}.bhn1Oq_root.bhn1Oq_rail{padding-right:0}.bhn1Oq_iconButton{corner-shape:round;cursor:pointer;width:28px;height:28px;color:var(--dsw-alias-label-secondary);background:0 0;border:none;border-radius:50%;flex:none;justify-content:center;align-items:center;padding:0;display:inline-flex}.bhn1Oq_iconButton:hover{background:var(--dsw-alias-interactive-bg-hover)}.bhn1Oq_sectionHeader{box-sizing:border-box;height:36px;color:var(--dsw-alias-label-tertiary);border-radius:12px;flex:none;justify-content:flex-end;align-items:center;gap:4px;margin-bottom:4px;padding-left:4px;display:flex;overflow:hidden}.bhn1Oq_root:not(.bhn1Oq_rail) .bhn1Oq_sectionHeader{margin-top:2px;margin-right:-4px}.bhn1Oq_sectionLabel{white-space:nowrap;opacity:1;visibility:visible;min-width:0;max-width:45%;transition:max-width .18s var(--ds-ease-in-out), margin-right .18s var(--ds-ease-in-out), opacity .12s var(--ds-ease-in-out), transform .18s var(--ds-ease-in-out), visibility 0s linear;flex:none;line-height:20px;overflow:hidden}.bhn1Oq_sectionLabelHidden{opacity:0;visibility:hidden;max-width:0;margin-right:-4px;transition-delay:0s,0s,0s,0s,.18s;transform:translate(-4px)}.bhn1Oq_searchSlot{box-sizing:border-box;min-width:0;max-width:28px;transition:max-width .18s var(--ds-ease-in-out), padding-left .18s var(--ds-ease-in-out);flex:1;align-items:center;margin-left:auto;padding-left:0;display:flex}.bhn1Oq_searchSlotExpanded{max-width:100%;padding-left:0}.bhn1Oq_headerActions{opacity:1;visibility:visible;max-width:60px;transition:max-width .18s var(--ds-ease-in-out), opacity .12s var(--ds-ease-in-out), transform .18s var(--ds-ease-in-out), visibility 0s linear;flex:none;align-items:center;gap:4px;display:flex;overflow:hidden}.bhn1Oq_headerActionsHidden{opacity:0;visibility:hidden;pointer-events:none;max-width:0;transition-delay:0s,0s,0s,.18s;transform:translate(4px)}.bhn1Oq_search{box-sizing:border-box;corner-shape:round;cursor:text;width:100%;height:28px;color:var(--dsw-alias-label-secondary);transition:width .18s var(--ds-ease-in-out), padding .18s var(--ds-ease-in-out), border-color .18s var(--ds-ease-in-out), background-color .18s var(--ds-ease-in-out);background:0 0;border:none;border-radius:50%;flex:none;align-items:center;gap:0;margin:0;padding:0;display:flex;overflow:hidden}.bhn1Oq_searchExpanded{border:.5px solid var(--dsw-alias-border-l4);width:calc(100% + 4px);height:30px;color:var(--dsw-alias-label-caption);background:0 0;border-radius:10px;margin-inline:-2px;padding:0 4px 0 0}.bhn1Oq_searchButton{corner-shape:round;cursor:pointer;width:28px;height:28px;color:inherit;background:0 0;border:none;border-radius:50%;flex:none;justify-content:center;align-items:center;padding:0;display:inline-flex}.bhn1Oq_searchExpanded .bhn1Oq_searchButton{width:28px;height:30px}.bhn1Oq_searchButton:hover{background:var(--dsw-alias-interactive-bg-hover)}.bhn1Oq_searchExpanded .bhn1Oq_searchButton:hover{background:0 0}.bhn1Oq_searchInput{opacity:0;pointer-events:none;width:0;min-width:0;color:var(--dsw-alias-label-primary);transition:opacity .12s var(--ds-ease-in-out);background:0 0;border:none;outline:none;flex:1;font-size:13px;line-height:18px}.bhn1Oq_searchExpanded .bhn1Oq_searchInput{opacity:1;pointer-events:auto;margin-left:-2px}.bhn1Oq_searchInput::placeholder{color:var(--dsw-alias-label-tertiary)}.bhn1Oq_clearButton{corner-shape:round;cursor:pointer;width:24px;height:24px;color:var(--dsw-alias-label-secondary);background:0 0;border:none;border-radius:50%;flex:none;justify-content:center;align-items:center;padding:0;display:inline-flex}.bhn1Oq_clearButton:hover{background:var(--dsw-alias-interactive-bg-hover)}.bhn1Oq_rail .bhn1Oq_sectionHeader{justify-content:flex-start;gap:0;margin-bottom:12px;padding-left:0}.bhn1Oq_rail .bhn1Oq_headerActions{max-width:none}.bhn1Oq_rail .bhn1Oq_iconButton{width:36px;height:36px;color:var(--dsw-alias-label-primary)}.bhn1Oq_rail .bhn1Oq_search{background:0 0;border-color:#0000;gap:0;width:36px;height:36px;margin:0 0 12px;padding:0}.bhn1Oq_rail .bhn1Oq_searchButton{width:36px;height:36px;color:var(--dsw-alias-label-primary)}.bhn1Oq_rail .bhn1Oq_searchButton:hover{background:var(--dsw-alias-interactive-bg-hover)}.bhn1Oq_listArea{min-height:0;margin-left:-4px;margin-right:calc(-1 * var(--dsh-session-list-edge-inset));flex-direction:column;flex:1;padding-left:4px;display:flex;overflow:visible}.bhn1Oq_rail .bhn1Oq_listArea{margin-left:0;margin-right:0;padding-left:0}.bhn1Oq_treeBody{flex-direction:column;flex:1;min-height:0;display:flex;position:relative}.bhn1Oq_fade{left:0;right:var(--dsh-session-list-edge-inset);background:linear-gradient(to bottom, transparent, var(--dsw-specific-sidebar-fill));pointer-events:none;height:24px;position:absolute;bottom:0}.bhn1Oq_wide{animation:bhn1Oq_wide-in .2s var(--ds-ease-in-out)}@keyframes bhn1Oq_wide-in{0%{opacity:0}}.bhn1Oq_list{min-height:0;margin-left:-4px;margin-right:var(--dsh-session-list-scrollbar-offset);padding-left:4px;padding-right:calc(var(--dsh-session-list-edge-inset) - var(--dsh-session-list-scrollbar-width) - var(--dsh-session-list-scrollbar-offset));scrollbar-gutter:stable;flex:1;padding-bottom:16px;overflow-y:auto}.bhn1Oq_flatList>*+*,.bhn1Oq_searchTree>[role=treeitem]+[role=treeitem],.bhn1Oq_groupSection>*+*{margin-top:2px}.bhn1Oq_searchStatus,.bhn1Oq_searchWarning{color:var(--dsw-alias-label-tertiary);padding:10px 12px;font-size:12px;line-height:18px}.bhn1Oq_searchWarning{color:var(--dsw-alias-label-secondary)}.bhn1Oq_groupSection{position:relative}.bhn1Oq_groupSection+.bhn1Oq_groupSection{margin-top:4px}.bhn1Oq_listTopDropIndicator,.bhn1Oq_workspaceDropBefore:before,.bhn1Oq_workspaceDropAfter:after{content:\"\";z-index:1;background:linear-gradient(55deg, transparent calc(50% - 1px), var(--dsw-alias-state-business-primary) calc(50% - 1px) calc(50% + 1px), transparent calc(50% + 1px)) 0 0 / 5px 7px no-repeat, linear-gradient(125deg, transparent calc(50% - 1px), var(--dsw-alias-state-business-primary) calc(50% - 1px) calc(50% + 1px), transparent calc(50% + 1px)) 0 5px / 5px 7px no-repeat, linear-gradient(var(--dsw-alias-state-business-primary) 0 0) 4px 5px / calc(100% - 4px) 2px no-repeat;pointer-events:none;height:12px;position:absolute;left:0;right:0}.bhn1Oq_listTopDropIndicator{top:-8px;left:0;right:var(--dsh-session-list-edge-inset)}.bhn1Oq_listTopDropActive>.bhn1Oq_workspaceDropBefore:first-child:before{display:none}.bhn1Oq_workspaceDropBefore:before{top:-8px}.bhn1Oq_workspaceDropAfter:after{bottom:-8px}.bhn1Oq_sessionOverflowButton{cursor:pointer;text-align:left;width:100%;height:28px;color:var(--dsw-alias-label-tertiary);background:0 0;border:none;border-radius:8px;padding:0 12px 0 28px;font-size:12px}.bhn1Oq_groupSection>.bhn1Oq_sessionOverflowButton{margin-top:0}.bhn1Oq_sessionOverflowButton:hover{color:var(--dsw-alias-label-secondary);background:0 0}.bhn1Oq_empty{color:var(--dsw-alias-label-tertiary);padding:16px 12px;font-size:13px}.bhn1Oq_renameInput{box-sizing:border-box;border:.5px solid var(--dsw-alias-border-l4);width:100%;height:44px;color:var(--dsw-alias-label-primary);background:0 0;border-radius:22px;outline:none;padding:7px 14px;font-size:14px;font-weight:400;line-height:22px}.bhn1Oq_renameInput:disabled{color:var(--dsw-alias-label-dimmed)}.bhn1Oq_renameError{color:var(--dsw-alias-state-error-primary);margin-top:8px;font-size:12px;line-height:18px}.bhn1Oq_deleteAction:not(:disabled){color:var(--dsw-alias-state-error-primary)}.bhn1Oq_deleteStatus{color:var(--dsw-alias-label-secondary);font-size:12px;line-height:18px}@media (prefers-reduced-motion:reduce){.bhn1Oq_wide{animation:none}.bhn1Oq_search,.bhn1Oq_sectionLabel,.bhn1Oq_searchSlot,.bhn1Oq_searchInput,.bhn1Oq_headerActions{transition:none}}";
|
|
970
1188
|
const tagId = "@deepseek-ai/dsh-client-ui-workspace/WorkspaceBrowser.module.css";
|
|
971
1189
|
if (typeof document !== "undefined" && document.querySelector("style[data-plugin-css=" + JSON.stringify(tagId) + "]") === null) {
|
|
972
1190
|
const tag = document.createElement("style");
|
|
@@ -976,45 +1194,45 @@ window.__ModuleLoader__.load({
|
|
|
976
1194
|
document.head.appendChild(tag);
|
|
977
1195
|
}
|
|
978
1196
|
var WorkspaceBrowser_module_css_default = {
|
|
979
|
-
"clearButton": "
|
|
980
|
-
"deleteAction": "
|
|
981
|
-
"deleteStatus": "
|
|
982
|
-
"empty": "
|
|
983
|
-
"fade": "
|
|
984
|
-
"flatList": "
|
|
985
|
-
"groupSection": "
|
|
986
|
-
"headerActions": "
|
|
987
|
-
"headerActionsHidden": "
|
|
988
|
-
"iconButton": "
|
|
989
|
-
"list": "
|
|
990
|
-
"listArea": "
|
|
991
|
-
"listTopDropActive": "
|
|
992
|
-
"listTopDropIndicator": "
|
|
993
|
-
"rail": "
|
|
994
|
-
"renameError": "
|
|
995
|
-
"renameInput": "
|
|
996
|
-
"root": "
|
|
997
|
-
"search": "
|
|
998
|
-
"searchButton": "
|
|
999
|
-
"searchExpanded": "
|
|
1000
|
-
"searchInput": "
|
|
1001
|
-
"searchSlot": "
|
|
1002
|
-
"searchSlotExpanded": "
|
|
1003
|
-
"searchStatus": "
|
|
1004
|
-
"searchTree": "
|
|
1005
|
-
"searchWarning": "
|
|
1006
|
-
"sectionHeader": "
|
|
1007
|
-
"sectionLabel": "
|
|
1008
|
-
"sectionLabelHidden": "
|
|
1009
|
-
"sessionOverflowButton": "
|
|
1010
|
-
"treeBody": "
|
|
1011
|
-
"wide": "
|
|
1012
|
-
"wide-in": "
|
|
1013
|
-
"workspaceDropAfter": "
|
|
1014
|
-
"workspaceDropBefore": "
|
|
1197
|
+
"clearButton": "bhn1Oq_clearButton",
|
|
1198
|
+
"deleteAction": "bhn1Oq_deleteAction",
|
|
1199
|
+
"deleteStatus": "bhn1Oq_deleteStatus",
|
|
1200
|
+
"empty": "bhn1Oq_empty",
|
|
1201
|
+
"fade": "bhn1Oq_fade",
|
|
1202
|
+
"flatList": "bhn1Oq_flatList",
|
|
1203
|
+
"groupSection": "bhn1Oq_groupSection",
|
|
1204
|
+
"headerActions": "bhn1Oq_headerActions",
|
|
1205
|
+
"headerActionsHidden": "bhn1Oq_headerActionsHidden",
|
|
1206
|
+
"iconButton": "bhn1Oq_iconButton",
|
|
1207
|
+
"list": "bhn1Oq_list",
|
|
1208
|
+
"listArea": "bhn1Oq_listArea",
|
|
1209
|
+
"listTopDropActive": "bhn1Oq_listTopDropActive",
|
|
1210
|
+
"listTopDropIndicator": "bhn1Oq_listTopDropIndicator",
|
|
1211
|
+
"rail": "bhn1Oq_rail",
|
|
1212
|
+
"renameError": "bhn1Oq_renameError",
|
|
1213
|
+
"renameInput": "bhn1Oq_renameInput",
|
|
1214
|
+
"root": "bhn1Oq_root",
|
|
1215
|
+
"search": "bhn1Oq_search",
|
|
1216
|
+
"searchButton": "bhn1Oq_searchButton",
|
|
1217
|
+
"searchExpanded": "bhn1Oq_searchExpanded",
|
|
1218
|
+
"searchInput": "bhn1Oq_searchInput",
|
|
1219
|
+
"searchSlot": "bhn1Oq_searchSlot",
|
|
1220
|
+
"searchSlotExpanded": "bhn1Oq_searchSlotExpanded",
|
|
1221
|
+
"searchStatus": "bhn1Oq_searchStatus",
|
|
1222
|
+
"searchTree": "bhn1Oq_searchTree",
|
|
1223
|
+
"searchWarning": "bhn1Oq_searchWarning",
|
|
1224
|
+
"sectionHeader": "bhn1Oq_sectionHeader",
|
|
1225
|
+
"sectionLabel": "bhn1Oq_sectionLabel",
|
|
1226
|
+
"sectionLabelHidden": "bhn1Oq_sectionLabelHidden",
|
|
1227
|
+
"sessionOverflowButton": "bhn1Oq_sessionOverflowButton",
|
|
1228
|
+
"treeBody": "bhn1Oq_treeBody",
|
|
1229
|
+
"wide": "bhn1Oq_wide",
|
|
1230
|
+
"wide-in": "bhn1Oq_wide-in",
|
|
1231
|
+
"workspaceDropAfter": "bhn1Oq_workspaceDropAfter",
|
|
1232
|
+
"workspaceDropBefore": "bhn1Oq_workspaceDropBefore"
|
|
1015
1233
|
};
|
|
1016
1234
|
//#endregion
|
|
1017
|
-
//#region lib/types/client/WorkspaceBrowser.js
|
|
1235
|
+
//#region lib/types/client/rows/WorkspaceBrowser.js
|
|
1018
1236
|
/**
|
|
1019
1237
|
* The workspace/session browsing region filling the sidebar shell's
|
|
1020
1238
|
* `sidebar.workspaces` hole: section header (title + view options + add
|
|
@@ -1037,6 +1255,20 @@ window.__ModuleLoader__.load({
|
|
|
1037
1255
|
const SEARCH_QUERY_MAX_CODE_UNITS = 500;
|
|
1038
1256
|
/** Session rows visible per Workspace before the local overflow control. */
|
|
1039
1257
|
const COLLAPSED_SESSION_LIMIT = 5;
|
|
1258
|
+
/** Fold one Workspace without charging its provisional New Session against the ordinary-row limit. */
|
|
1259
|
+
function collapsedSessionRows(sessions) {
|
|
1260
|
+
let ordinaryCount = 0;
|
|
1261
|
+
const rows = sessions.filter((session) => {
|
|
1262
|
+
if (session.blank) return true;
|
|
1263
|
+
if (ordinaryCount >= COLLAPSED_SESSION_LIMIT) return false;
|
|
1264
|
+
ordinaryCount += 1;
|
|
1265
|
+
return true;
|
|
1266
|
+
});
|
|
1267
|
+
return {
|
|
1268
|
+
rows,
|
|
1269
|
+
hiddenCount: sessions.length - rows.length
|
|
1270
|
+
};
|
|
1271
|
+
}
|
|
1040
1272
|
/** Keep controlled input and RPC payload inside the session.search wire contract. */
|
|
1041
1273
|
function sanitizeSearchQuery(value) {
|
|
1042
1274
|
const withoutNul = value.replaceAll("\0", "");
|
|
@@ -1197,8 +1429,9 @@ window.__ModuleLoader__.load({
|
|
|
1197
1429
|
return e.clientY < rect.top + rect.height / 2 ? "before" : "after";
|
|
1198
1430
|
}
|
|
1199
1431
|
/** The scrolling session tree; unmounting drops the sessions subscription and expand-all state. */
|
|
1200
|
-
function SessionTree({ useSessions, startSession, open, forkSession, workspaces, archivedSessionIds, onRenameRequest, onDeleteRequest, onSessionRename, onSessionArchive, insertWorkspaceBefore, insertSessionBefore, orderBy, groupExpansion, setGroupExpanded, sessionOrderByAccount, sessionUpdatedAtByAccount, syncSessionOrderAccount, setSessionOrder, home, t }) {
|
|
1432
|
+
function SessionTree({ useSessions, useSessionPendingInteraction, startSession, open, forkSession, workspaces, archivedSessionIds, onRenameRequest, onDeleteRequest, onSessionRename, onSessionArchive, insertWorkspaceBefore, insertSessionBefore, orderBy, groupExpansion, setGroupExpanded, sessionOrderByAccount, sessionUpdatedAtByAccount, syncSessionOrderAccount, setSessionOrder, home, t }) {
|
|
1201
1433
|
const list = useSessions((s) => s);
|
|
1434
|
+
const pendingInteractions = useSessionPendingInteraction((s) => s);
|
|
1202
1435
|
const current = list.current;
|
|
1203
1436
|
const [expandedSessionGroups, setExpandedSessionGroups] = (0, react.useState)([]);
|
|
1204
1437
|
const [drag, setDrag] = (0, react.useState)(null);
|
|
@@ -1265,13 +1498,14 @@ window.__ModuleLoader__.load({
|
|
|
1265
1498
|
});
|
|
1266
1499
|
}, [sessionOrderByAccount, workspaces]);
|
|
1267
1500
|
const orderedUngroupedSessionIds = (0, react.useMemo)(() => reconciledSessionOrder(ungroupedSessionIds, sessionOrderByAccount[""]), [sessionOrderByAccount, ungroupedSessionIds]);
|
|
1268
|
-
const groups = (0, react.useMemo)(() => deriveGroups(list, orderedWorkspaces, archivedSessionIds, {
|
|
1501
|
+
const groups = (0, react.useMemo)(() => deriveGroups(list, orderedWorkspaces, archivedSessionIds, pendingInteractions, {
|
|
1269
1502
|
expandedGroups,
|
|
1270
1503
|
...sessionOrderByAccount[""] === void 0 ? {} : { ungroupedOrder: sessionOrderByAccount[""] }
|
|
1271
1504
|
}), [
|
|
1272
1505
|
list,
|
|
1273
1506
|
orderedWorkspaces,
|
|
1274
1507
|
archivedSessionIds,
|
|
1508
|
+
pendingInteractions,
|
|
1275
1509
|
expandedGroups,
|
|
1276
1510
|
sessionOrderByAccount
|
|
1277
1511
|
]);
|
|
@@ -1282,18 +1516,40 @@ window.__ModuleLoader__.load({
|
|
|
1282
1516
|
setDrag(null);
|
|
1283
1517
|
const group = groups.find((candidate) => candidate.key === activeDrag.accountKey);
|
|
1284
1518
|
if (group === void 0) return;
|
|
1285
|
-
const
|
|
1519
|
+
const sessionsExpanded = expandedSessionGroups.includes(group.key);
|
|
1520
|
+
const renderedSessions = sessionsExpanded ? group.sessions : collapsedSessionRows(group.sessions).rows;
|
|
1521
|
+
const targetIndex = renderedSessions.findIndex((session) => session.id === over.id);
|
|
1286
1522
|
if (targetIndex === -1) return;
|
|
1287
|
-
const
|
|
1288
|
-
if (
|
|
1289
|
-
const
|
|
1290
|
-
const
|
|
1291
|
-
if (
|
|
1523
|
+
const sourceIndex = renderedSessions.findIndex((session) => session.id === activeDrag.sessionId);
|
|
1524
|
+
if (over.id === activeDrag.sessionId) return;
|
|
1525
|
+
const withoutSource = renderedSessions.filter((session) => session.id !== activeDrag.sessionId);
|
|
1526
|
+
const targetWithoutSourceIndex = withoutSource.findIndex((session) => session.id === over.id);
|
|
1527
|
+
if (targetWithoutSourceIndex === -1) return;
|
|
1528
|
+
const visibleInsertAt = over.half === "before" ? targetWithoutSourceIndex : targetWithoutSourceIndex + 1;
|
|
1529
|
+
if (sourceIndex !== -1 && visibleInsertAt === sourceIndex) return;
|
|
1292
1530
|
const accountSessionIds = activeDrag.accountKey === "" ? orderedUngroupedSessionIds : orderedWorkspaces.find((workspace) => workspace.workspaceId === activeDrag.accountKey)?.sessionIds;
|
|
1293
1531
|
if (accountSessionIds === void 0) return;
|
|
1294
1532
|
const nextOrder = accountSessionIds.filter((id) => id !== activeDrag.sessionId);
|
|
1533
|
+
let anchor;
|
|
1534
|
+
if (sessionsExpanded) anchor = over.half === "before" ? over.id : renderedSessions[targetIndex + 1]?.id;
|
|
1535
|
+
else {
|
|
1536
|
+
const previousVisible = withoutSource[visibleInsertAt - 1]?.id;
|
|
1537
|
+
if (previousVisible === void 0) anchor = nextOrder[0];
|
|
1538
|
+
else {
|
|
1539
|
+
const previousIndex = nextOrder.indexOf(previousVisible);
|
|
1540
|
+
if (previousIndex === -1) return;
|
|
1541
|
+
anchor = nextOrder[previousIndex + 1];
|
|
1542
|
+
}
|
|
1543
|
+
}
|
|
1295
1544
|
const insertAt = anchor === void 0 ? nextOrder.length : nextOrder.indexOf(anchor);
|
|
1296
1545
|
nextOrder.splice(insertAt === -1 ? nextOrder.length : insertAt, 0, activeDrag.sessionId);
|
|
1546
|
+
if (!sessionsExpanded && sourceIndex !== -1) {
|
|
1547
|
+
const nodes = new Map(group.sessions.map((node) => [node.id, node]));
|
|
1548
|
+
if (!collapsedSessionRows(nextOrder.flatMap((id) => {
|
|
1549
|
+
const node = nodes.get(id);
|
|
1550
|
+
return node === void 0 ? [] : [node];
|
|
1551
|
+
})).rows.some((node) => node.id === activeDrag.sessionId)) return;
|
|
1552
|
+
}
|
|
1297
1553
|
setSessionOrder(activeDrag.accountKey, nextOrder.map((id) => id));
|
|
1298
1554
|
if (orderBy === "updated" || activeDrag.accountKey === "") return;
|
|
1299
1555
|
insertSessionBefore(activeDrag.accountKey, activeDrag.sessionId, anchor).catch((reason) => {
|
|
@@ -1332,6 +1588,8 @@ window.__ModuleLoader__.load({
|
|
|
1332
1588
|
children: t("empty.none")
|
|
1333
1589
|
}), groups.map((group) => {
|
|
1334
1590
|
const workspaceId = group.workspaceId;
|
|
1591
|
+
const collapsed = collapsedSessionRows(group.sessions);
|
|
1592
|
+
const sessionsExpanded = expandedSessionGroups.includes(group.key);
|
|
1335
1593
|
const workspaceMarker = workspaceId !== void 0 && workspaceDrag?.over?.id === workspaceId ? workspaceDrag.over.half : null;
|
|
1336
1594
|
const workspaceDragProps = workspaceId === void 0 ? void 0 : {
|
|
1337
1595
|
start: () => {
|
|
@@ -1401,7 +1659,7 @@ window.__ModuleLoader__.load({
|
|
|
1401
1659
|
}
|
|
1402
1660
|
}
|
|
1403
1661
|
}),
|
|
1404
|
-
(
|
|
1662
|
+
(sessionsExpanded ? group.sessions : collapsed.rows).map((node) => {
|
|
1405
1663
|
const sameGroupDrag = drag !== null && drag.accountKey === group.key;
|
|
1406
1664
|
return (0, react_jsx_runtime.jsx)(SessionNodeItem, {
|
|
1407
1665
|
node,
|
|
@@ -1449,14 +1707,14 @@ window.__ModuleLoader__.load({
|
|
|
1449
1707
|
t
|
|
1450
1708
|
}, node.id);
|
|
1451
1709
|
}),
|
|
1452
|
-
|
|
1710
|
+
collapsed.hiddenCount > 0 && (0, react_jsx_runtime.jsx)("button", {
|
|
1453
1711
|
type: "button",
|
|
1454
1712
|
className: WorkspaceBrowser_module_css_default.sessionOverflowButton,
|
|
1455
|
-
"aria-expanded":
|
|
1713
|
+
"aria-expanded": sessionsExpanded,
|
|
1456
1714
|
onClick: () => {
|
|
1457
1715
|
setExpandedSessionGroups((keys) => toggled(keys, group.key));
|
|
1458
1716
|
},
|
|
1459
|
-
children:
|
|
1717
|
+
children: sessionsExpanded ? t("sessions.collapse") : t("sessions.expand", { n: collapsed.hiddenCount })
|
|
1460
1718
|
})
|
|
1461
1719
|
]
|
|
1462
1720
|
}, group.key);
|
|
@@ -1467,9 +1725,14 @@ window.__ModuleLoader__.load({
|
|
|
1467
1725
|
});
|
|
1468
1726
|
}
|
|
1469
1727
|
/** The flat "In one list" body: every session is one draggable top-level row. */
|
|
1470
|
-
function FlatList({ useSessions, open, forkSession, onSessionRename, onSessionArchive, archivedSessionIds, orderBy, sessionOrderByAccount, sessionUpdatedAtByAccount, syncSessionOrderAccount, setSessionOrder, t }) {
|
|
1728
|
+
function FlatList({ useSessions, useSessionPendingInteraction, open, forkSession, onSessionRename, onSessionArchive, archivedSessionIds, orderBy, sessionOrderByAccount, sessionUpdatedAtByAccount, syncSessionOrderAccount, setSessionOrder, t }) {
|
|
1471
1729
|
const list = useSessions((s) => s);
|
|
1472
|
-
const
|
|
1730
|
+
const pendingInteractions = useSessionPendingInteraction((s) => s);
|
|
1731
|
+
const baseRows = (0, react.useMemo)(() => deriveFlat(list, archivedSessionIds, pendingInteractions), [
|
|
1732
|
+
list,
|
|
1733
|
+
archivedSessionIds,
|
|
1734
|
+
pendingInteractions
|
|
1735
|
+
]);
|
|
1473
1736
|
const sessionIds = (0, react.useMemo)(() => baseRows.map((row) => row.id), [baseRows]);
|
|
1474
1737
|
const previousOrderBy = (0, react.useRef)(orderBy);
|
|
1475
1738
|
(0, react.useEffect)(() => {
|
|
@@ -1585,19 +1848,21 @@ window.__ModuleLoader__.load({
|
|
|
1585
1848
|
});
|
|
1586
1849
|
}
|
|
1587
1850
|
/** Flat search body: local metadata matches plus the current Host result page. */
|
|
1588
|
-
function SearchResults({ useSessions, open, workspaces, archivedSessionIds, query, remote, resultLimit, t }) {
|
|
1851
|
+
function SearchResults({ useSessions, useSessionPendingInteraction, open, workspaces, archivedSessionIds, query, remote, resultLimit, t }) {
|
|
1589
1852
|
const list = useSessions((s) => s);
|
|
1853
|
+
const pendingInteractions = useSessionPendingInteraction((s) => s);
|
|
1590
1854
|
const currentRemote = remote.query === query ? remote : {
|
|
1591
1855
|
query,
|
|
1592
1856
|
status: "loading",
|
|
1593
1857
|
items: [],
|
|
1594
1858
|
hasMore: false
|
|
1595
1859
|
};
|
|
1596
|
-
const results = (0, react.useMemo)(() => deriveSearchResults(list, workspaces, query, archivedSessionIds, currentRemote, resultLimit), [
|
|
1860
|
+
const results = (0, react.useMemo)(() => deriveSearchResults(list, workspaces, query, archivedSessionIds, pendingInteractions, currentRemote, resultLimit), [
|
|
1597
1861
|
list,
|
|
1598
1862
|
workspaces,
|
|
1599
1863
|
query,
|
|
1600
1864
|
archivedSessionIds,
|
|
1865
|
+
pendingInteractions,
|
|
1601
1866
|
currentRemote,
|
|
1602
1867
|
resultLimit
|
|
1603
1868
|
]);
|
|
@@ -1646,8 +1911,8 @@ window.__ModuleLoader__.load({
|
|
|
1646
1911
|
* @param props - composed slot props (shell owner share + store + injected actions).
|
|
1647
1912
|
* @returns the region element tree.
|
|
1648
1913
|
*/
|
|
1649
|
-
function WorkspaceBrowser({ wide, expandSidebar, useSessions, useWorkspaces, useStore, actions, startSession, open, renameSession, forkSession, renameWorkspace, deleteWorkspace, insertWorkspaceBefore, archiveSession, insertSessionBefore, createWorkspace, searchSessions, searchResultLimit, useDirectoryFlow,
|
|
1650
|
-
const home =
|
|
1914
|
+
function WorkspaceBrowser({ wide, expandSidebar, useSessions, useSessionPendingInteraction, useWorkspaces, useStore, actions, startSession, open, renameSession, forkSession, renameWorkspace, deleteWorkspace, insertWorkspaceBefore, archiveSession, insertSessionBefore, createWorkspace, searchSessions, searchResultLimit, useDirectoryFlow, useHostInfo, renderSlot, t }) {
|
|
1915
|
+
const home = useHostInfo((info) => info.home);
|
|
1651
1916
|
const workspaces = useWorkspaces((state) => state.items);
|
|
1652
1917
|
const workspacePhase = useWorkspaces((state) => state.phase);
|
|
1653
1918
|
const archivedSessionIds = useWorkspaces((state) => state.archivedSessionIds);
|
|
@@ -1668,7 +1933,8 @@ window.__ModuleLoader__.load({
|
|
|
1668
1933
|
promotedBlank.current = void 0;
|
|
1669
1934
|
return;
|
|
1670
1935
|
}
|
|
1671
|
-
|
|
1936
|
+
const promoted = promotedBlank.current;
|
|
1937
|
+
if (promoted !== void 0 && promoted.sessionId === currentBlankSessionId && promoted.accountKey === currentBlankAccount) return;
|
|
1672
1938
|
promotedBlank.current = {
|
|
1673
1939
|
sessionId: currentBlankSessionId,
|
|
1674
1940
|
accountKey: currentBlankAccount
|
|
@@ -2014,6 +2280,7 @@ window.__ModuleLoader__.load({
|
|
|
2014
2280
|
className: WorkspaceBrowser_module_css_default.listArea,
|
|
2015
2281
|
children: wide && (normalizedQuery !== "" ? (0, react_jsx_runtime.jsx)(SearchResults, {
|
|
2016
2282
|
useSessions,
|
|
2283
|
+
useSessionPendingInteraction,
|
|
2017
2284
|
open,
|
|
2018
2285
|
workspaces,
|
|
2019
2286
|
archivedSessionIds,
|
|
@@ -2023,6 +2290,7 @@ window.__ModuleLoader__.load({
|
|
|
2023
2290
|
t
|
|
2024
2291
|
}) : groupBy === "flat" ? (0, react_jsx_runtime.jsx)(FlatList, {
|
|
2025
2292
|
useSessions,
|
|
2293
|
+
useSessionPendingInteraction,
|
|
2026
2294
|
open,
|
|
2027
2295
|
forkSession,
|
|
2028
2296
|
onSessionRename,
|
|
@@ -2036,6 +2304,7 @@ window.__ModuleLoader__.load({
|
|
|
2036
2304
|
t
|
|
2037
2305
|
}) : (0, react_jsx_runtime.jsx)(SessionTree, {
|
|
2038
2306
|
useSessions,
|
|
2307
|
+
useSessionPendingInteraction,
|
|
2039
2308
|
onSessionRename,
|
|
2040
2309
|
onSessionArchive,
|
|
2041
2310
|
forkSession,
|
|
@@ -2265,6 +2534,7 @@ window.__ModuleLoader__.load({
|
|
|
2265
2534
|
"status.planReview": "计划待审",
|
|
2266
2535
|
"status.waitingAnswer": "等待回答",
|
|
2267
2536
|
"status.completed": "已完成",
|
|
2537
|
+
"schedule.active": "有活动定时任务",
|
|
2268
2538
|
"hover.created": "创建于 {time}",
|
|
2269
2539
|
"hover.copied": "已复制",
|
|
2270
2540
|
"date.ymd": "{y}年{m}月{d}日",
|
|
@@ -2330,6 +2600,7 @@ window.__ModuleLoader__.load({
|
|
|
2330
2600
|
"status.planReview": "Plan awaiting review",
|
|
2331
2601
|
"status.waitingAnswer": "Waiting for answer",
|
|
2332
2602
|
"status.completed": "Completed",
|
|
2603
|
+
"schedule.active": "Has active scheduled task",
|
|
2333
2604
|
"hover.created": "Created {time}",
|
|
2334
2605
|
"hover.copied": "Copied",
|
|
2335
2606
|
"date.ymd": "{y}-{m}-{d}",
|
|
@@ -2358,7 +2629,8 @@ window.__ModuleLoader__.load({
|
|
|
2358
2629
|
"sessions",
|
|
2359
2630
|
"workspaces",
|
|
2360
2631
|
"locale",
|
|
2361
|
-
"
|
|
2632
|
+
"remote",
|
|
2633
|
+
"remote.directoryPicker"
|
|
2362
2634
|
];
|
|
2363
2635
|
/**
|
|
2364
2636
|
* Register the browser and picker once their slot declarations are on the
|
|
@@ -2367,13 +2639,16 @@ window.__ModuleLoader__.load({
|
|
|
2367
2639
|
* @param ctx - client root context.
|
|
2368
2640
|
*/
|
|
2369
2641
|
function apply(ctx) {
|
|
2370
|
-
const
|
|
2642
|
+
const sessions = ctx.get("sessions");
|
|
2643
|
+
const workspaces = ctx.get("workspaces");
|
|
2644
|
+
const uiWorkspace = new UiWorkspaceService(ctx, ctx.remote.directoryPicker, workspaces, sessions);
|
|
2645
|
+
ctx.slots.provideRoot({ hooks: { workspaces: workspaces.list } });
|
|
2371
2646
|
ctx.effect(() => ctx.locale.register(NS, {
|
|
2372
2647
|
zh,
|
|
2373
2648
|
en
|
|
2374
2649
|
}), "ui-workspace: dictionaries");
|
|
2375
2650
|
const searchSessions = async (query, signal) => {
|
|
2376
|
-
const result = await
|
|
2651
|
+
const result = await sessions.search(query, signal);
|
|
2377
2652
|
if (!result.ok) throw new Error(result.error.message);
|
|
2378
2653
|
return result.value;
|
|
2379
2654
|
};
|
|
@@ -2382,53 +2657,57 @@ window.__ModuleLoader__.load({
|
|
|
2382
2657
|
subscribe: (listener) => ctx.slots.subscribe(hole, listener)
|
|
2383
2658
|
});
|
|
2384
2659
|
const browserFlowSource = flowSource("sidebar.workspaces.directoryFlow");
|
|
2660
|
+
const hostInfo = {
|
|
2661
|
+
getSnapshot: () => ctx.remote.$host,
|
|
2662
|
+
subscribe: (listener) => ctx.on("connection/reset", listener)
|
|
2663
|
+
};
|
|
2385
2664
|
const pickerFlowSource = flowSource("conversation.hero.workspace.directoryFlow");
|
|
2386
2665
|
const browserInjected = () => ({
|
|
2387
2666
|
startSession: (workspaceId) => {
|
|
2388
|
-
|
|
2667
|
+
uiWorkspace.startSession(workspaceId);
|
|
2389
2668
|
},
|
|
2390
2669
|
open: (sessionId) => {
|
|
2391
|
-
|
|
2670
|
+
sessions.open(sessionId);
|
|
2392
2671
|
},
|
|
2393
2672
|
searchSessions,
|
|
2394
|
-
searchResultLimit:
|
|
2673
|
+
searchResultLimit: sessions.searchResultLimit,
|
|
2395
2674
|
renameSession: async (sessionId, title) => {
|
|
2396
|
-
const session =
|
|
2675
|
+
const session = sessions.binding(sessionId)?.session;
|
|
2397
2676
|
if (session === void 0) throw new Error(`unknown session "${sessionId}"`);
|
|
2398
2677
|
const result = await session.rename(title);
|
|
2399
2678
|
if (!result.ok) throw new Error(result.error.message);
|
|
2400
2679
|
},
|
|
2401
2680
|
forkSession: (sessionId) => {
|
|
2402
|
-
|
|
2681
|
+
sessions.fork({
|
|
2403
2682
|
sessionId,
|
|
2404
2683
|
increaseTitle: true
|
|
2405
2684
|
}).then((childId) => {
|
|
2406
|
-
|
|
2685
|
+
sessions.open(childId);
|
|
2407
2686
|
}).catch(() => {});
|
|
2408
2687
|
},
|
|
2409
2688
|
renameWorkspace: async (workspaceId, title) => {
|
|
2410
|
-
await
|
|
2689
|
+
await workspaces.rename(workspaceId, title);
|
|
2411
2690
|
},
|
|
2412
2691
|
deleteWorkspace: async (workspaceId) => {
|
|
2413
|
-
await
|
|
2692
|
+
await workspaces.delete(workspaceId);
|
|
2414
2693
|
},
|
|
2415
2694
|
insertWorkspaceBefore: async (workspaceId, beforeWorkspaceId) => {
|
|
2416
|
-
await
|
|
2695
|
+
await workspaces.insertBefore(workspaceId, beforeWorkspaceId);
|
|
2417
2696
|
},
|
|
2418
2697
|
archiveSession: async (sessionId) => {
|
|
2419
|
-
await
|
|
2698
|
+
await uiWorkspace.archiveSession(sessionId);
|
|
2420
2699
|
},
|
|
2421
2700
|
insertSessionBefore: async (workspaceId, sessionId, beforeSessionId) => {
|
|
2422
|
-
await
|
|
2701
|
+
await workspaces.insertSessionBefore(workspaceId, sessionId, beforeSessionId);
|
|
2423
2702
|
},
|
|
2424
|
-
createWorkspace: (input) =>
|
|
2703
|
+
createWorkspace: (input) => workspaces.create(input),
|
|
2425
2704
|
hooks: {
|
|
2426
2705
|
directoryFlow: browserFlowSource,
|
|
2427
|
-
|
|
2706
|
+
hostInfo
|
|
2428
2707
|
}
|
|
2429
2708
|
});
|
|
2430
2709
|
const pickerInjected = () => ({
|
|
2431
|
-
createWorkspace: (input) =>
|
|
2710
|
+
createWorkspace: (input) => workspaces.create(input),
|
|
2432
2711
|
hooks: { directoryFlow: pickerFlowSource }
|
|
2433
2712
|
});
|
|
2434
2713
|
ctx.slots.inject("sidebar.workspaces", () => ctx.slots.register({
|