@wowyuarm/dsh-agent-team 0.1.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.
Files changed (125) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +103 -0
  3. package/README.zh.md +103 -0
  4. package/cordis.patch.yml +36 -0
  5. package/package.json +152 -0
  6. package/packages/agent-team/README.md +58 -0
  7. package/packages/agent-team/README.zh.md +57 -0
  8. package/packages/agent-team/lib/index.js +841 -0
  9. package/packages/agent-team/lib/invariant.js +24 -0
  10. package/packages/agent-team/lib/ledger.js +2161 -0
  11. package/packages/agent-team/lib/member-context.js +69 -0
  12. package/packages/agent-team/lib/preset-roster.js +14 -0
  13. package/packages/agent-team/lib/spec.js +347 -0
  14. package/packages/agent-team/lib/typert.host.d.ts +3 -0
  15. package/packages/agent-team/lib/typert.host.js +2084 -0
  16. package/packages/agent-team/lib/typert.remote-client.d.ts +54 -0
  17. package/packages/agent-team/lib/typert.remote-client.d.ts.map +1 -0
  18. package/packages/agent-team/lib/typert.remote-client.js +1218 -0
  19. package/packages/agent-team/lib/types/index.d.ts +156 -0
  20. package/packages/agent-team/lib/types/index.d.ts.map +1 -0
  21. package/packages/agent-team/lib/types/invariant.d.ts +13 -0
  22. package/packages/agent-team/lib/types/invariant.d.ts.map +1 -0
  23. package/packages/agent-team/lib/types/ledger.d.ts +271 -0
  24. package/packages/agent-team/lib/types/ledger.d.ts.map +1 -0
  25. package/packages/agent-team/lib/types/member-context.d.ts +7 -0
  26. package/packages/agent-team/lib/types/member-context.d.ts.map +1 -0
  27. package/packages/agent-team/lib/types/preset-roster.d.ts +5 -0
  28. package/packages/agent-team/lib/types/preset-roster.d.ts.map +1 -0
  29. package/packages/agent-team/lib/types/spec.d.ts +13 -0
  30. package/packages/agent-team/lib/types/spec.d.ts.map +1 -0
  31. package/packages/agent-team/lib/types/types.d.ts +818 -0
  32. package/packages/agent-team/lib/types/types.d.ts.map +1 -0
  33. package/packages/agent-team/lib/types.js +1 -0
  34. package/packages/agent-team/preset/team-member/agent.cordis.yml +89 -0
  35. package/packages/client-agent-team/README.md +39 -0
  36. package/packages/client-agent-team/README.zh.md +39 -0
  37. package/packages/client-agent-team/lib/client.js +9633 -0
  38. package/packages/client-agent-team/lib/client.js.map +1 -0
  39. package/packages/client-agent-team/lib/index.js +5 -0
  40. package/packages/client-agent-team/lib/types/client/TeamAgentsPanel.d.ts +20 -0
  41. package/packages/client-agent-team/lib/types/client/TeamAgentsPanel.d.ts.map +1 -0
  42. package/packages/client-agent-team/lib/types/client/TeamAgentsPanel.js +274 -0
  43. package/packages/client-agent-team/lib/types/client/TeamChannelPage.d.ts +19 -0
  44. package/packages/client-agent-team/lib/types/client/TeamChannelPage.d.ts.map +1 -0
  45. package/packages/client-agent-team/lib/types/client/TeamChannelPage.js +243 -0
  46. package/packages/client-agent-team/lib/types/client/TeamChannelsPanel.d.ts +21 -0
  47. package/packages/client-agent-team/lib/types/client/TeamChannelsPanel.d.ts.map +1 -0
  48. package/packages/client-agent-team/lib/types/client/TeamChannelsPanel.js +196 -0
  49. package/packages/client-agent-team/lib/types/client/TeamComposer.d.ts +15 -0
  50. package/packages/client-agent-team/lib/types/client/TeamComposer.d.ts.map +1 -0
  51. package/packages/client-agent-team/lib/types/client/TeamComposer.js +144 -0
  52. package/packages/client-agent-team/lib/types/client/TeamConversation.d.ts +3 -0
  53. package/packages/client-agent-team/lib/types/client/TeamConversation.d.ts.map +1 -0
  54. package/packages/client-agent-team/lib/types/client/TeamConversation.js +20 -0
  55. package/packages/client-agent-team/lib/types/client/TeamFooterAction.d.ts +3 -0
  56. package/packages/client-agent-team/lib/types/client/TeamFooterAction.d.ts.map +1 -0
  57. package/packages/client-agent-team/lib/types/client/TeamFooterAction.js +19 -0
  58. package/packages/client-agent-team/lib/types/client/TeamInboxPanel.d.ts +13 -0
  59. package/packages/client-agent-team/lib/types/client/TeamInboxPanel.d.ts.map +1 -0
  60. package/packages/client-agent-team/lib/types/client/TeamInboxPanel.js +90 -0
  61. package/packages/client-agent-team/lib/types/client/TeamMemberAvatar.d.ts +12 -0
  62. package/packages/client-agent-team/lib/types/client/TeamMemberAvatar.d.ts.map +1 -0
  63. package/packages/client-agent-team/lib/types/client/TeamMemberAvatar.js +15 -0
  64. package/packages/client-agent-team/lib/types/client/TeamMembersAction.d.ts +5 -0
  65. package/packages/client-agent-team/lib/types/client/TeamMembersAction.d.ts.map +1 -0
  66. package/packages/client-agent-team/lib/types/client/TeamMembersAction.js +32 -0
  67. package/packages/client-agent-team/lib/types/client/TeamMessage.d.ts +19 -0
  68. package/packages/client-agent-team/lib/types/client/TeamMessage.d.ts.map +1 -0
  69. package/packages/client-agent-team/lib/types/client/TeamMessage.js +24 -0
  70. package/packages/client-agent-team/lib/types/client/TeamPresenceDot.d.ts +11 -0
  71. package/packages/client-agent-team/lib/types/client/TeamPresenceDot.d.ts.map +1 -0
  72. package/packages/client-agent-team/lib/types/client/TeamPresenceDot.js +20 -0
  73. package/packages/client-agent-team/lib/types/client/TeamRowMenu.d.ts +15 -0
  74. package/packages/client-agent-team/lib/types/client/TeamRowMenu.d.ts.map +1 -0
  75. package/packages/client-agent-team/lib/types/client/TeamRowMenu.js +23 -0
  76. package/packages/client-agent-team/lib/types/client/TeamSettings.d.ts +3 -0
  77. package/packages/client-agent-team/lib/types/client/TeamSettings.d.ts.map +1 -0
  78. package/packages/client-agent-team/lib/types/client/TeamSettings.js +5 -0
  79. package/packages/client-agent-team/lib/types/client/TeamSidebarSection.d.ts +9 -0
  80. package/packages/client-agent-team/lib/types/client/TeamSidebarSection.d.ts.map +1 -0
  81. package/packages/client-agent-team/lib/types/client/TeamSidebarSection.js +9 -0
  82. package/packages/client-agent-team/lib/types/client/TeamThreadPage.d.ts +22 -0
  83. package/packages/client-agent-team/lib/types/client/TeamThreadPage.d.ts.map +1 -0
  84. package/packages/client-agent-team/lib/types/client/TeamThreadPage.js +464 -0
  85. package/packages/client-agent-team/lib/types/client/TeamWorkspaceBrowser.d.ts +3 -0
  86. package/packages/client-agent-team/lib/types/client/TeamWorkspaceBrowser.d.ts.map +1 -0
  87. package/packages/client-agent-team/lib/types/client/TeamWorkspaceBrowser.js +39 -0
  88. package/packages/client-agent-team/lib/types/client/TeamWorkspaceRow.d.ts +11 -0
  89. package/packages/client-agent-team/lib/types/client/TeamWorkspaceRow.d.ts.map +1 -0
  90. package/packages/client-agent-team/lib/types/client/TeamWorkspaceRow.js +6 -0
  91. package/packages/client-agent-team/lib/types/client/index.d.ts +19 -0
  92. package/packages/client-agent-team/lib/types/client/index.d.ts.map +1 -0
  93. package/packages/client-agent-team/lib/types/client/index.js +113 -0
  94. package/packages/client-agent-team/lib/types/client/locales.d.ts +224 -0
  95. package/packages/client-agent-team/lib/types/client/locales.d.ts.map +1 -0
  96. package/packages/client-agent-team/lib/types/client/locales.js +222 -0
  97. package/packages/client-agent-team/lib/types/client/navigation.d.ts +39 -0
  98. package/packages/client-agent-team/lib/types/client/navigation.d.ts.map +1 -0
  99. package/packages/client-agent-team/lib/types/client/navigation.js +96 -0
  100. package/packages/client-agent-team/lib/types/client/slots.d.ts +74 -0
  101. package/packages/client-agent-team/lib/types/client/slots.d.ts.map +1 -0
  102. package/packages/client-agent-team/lib/types/client/slots.js +1 -0
  103. package/packages/client-agent-team/lib/types/client/team-changes.d.ts +28 -0
  104. package/packages/client-agent-team/lib/types/client/team-changes.d.ts.map +1 -0
  105. package/packages/client-agent-team/lib/types/client/team-changes.js +70 -0
  106. package/packages/client-agent-team/lib/types/client/team-formatters.d.ts +53 -0
  107. package/packages/client-agent-team/lib/types/client/team-formatters.d.ts.map +1 -0
  108. package/packages/client-agent-team/lib/types/client/team-formatters.js +128 -0
  109. package/packages/client-agent-team/lib/types/client/team-membership.d.ts +25 -0
  110. package/packages/client-agent-team/lib/types/client/team-membership.d.ts.map +1 -0
  111. package/packages/client-agent-team/lib/types/client/team-membership.js +39 -0
  112. package/packages/client-agent-team/lib/types/client/team-separators.d.ts +23 -0
  113. package/packages/client-agent-team/lib/types/client/team-separators.d.ts.map +1 -0
  114. package/packages/client-agent-team/lib/types/client/team-separators.js +52 -0
  115. package/packages/client-agent-team/lib/types/client/timeline-scroll.d.ts +18 -0
  116. package/packages/client-agent-team/lib/types/client/timeline-scroll.d.ts.map +1 -0
  117. package/packages/client-agent-team/lib/types/client/timeline-scroll.js +54 -0
  118. package/packages/client-agent-team/lib/types/index.d.ts +3 -0
  119. package/packages/client-agent-team/lib/types/index.d.ts.map +1 -0
  120. package/packages/client-agent-team/lib/types/index.js +2 -0
  121. package/packages/tool-agent-team/README.md +23 -0
  122. package/packages/tool-agent-team/README.zh.md +23 -0
  123. package/packages/tool-agent-team/lib/index.js +294 -0
  124. package/packages/tool-agent-team/lib/types/index.d.ts +5 -0
  125. package/packages/tool-agent-team/lib/types/index.d.ts.map +1 -0
@@ -0,0 +1,464 @@
1
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
+ import { Fragment, useEffect, useMemo, useRef, useState } from 'react';
3
+ import { Button, DisclosureRow, IconChevronLeftOutline14, IconChecklistOutline14, Pill } from '@deepseek-ai/dsh-client-ui-primitives';
4
+ import { TeamComposer } from "./TeamComposer.js";
5
+ import { TeamPresenceDot } from "./TeamPresenceDot.js";
6
+ import { TeamMessage } from "./TeamMessage.js";
7
+ import { formatActivity, formatClaimState, formatTaskStatus, formatTaskTitle, mentionNamesOf } from "./team-formatters.js";
8
+ import { daySeparatorLabel, timelineDayKey } from "./team-separators.js";
9
+ import { useTimelineScroll } from "./timeline-scroll.js";
10
+ import css from './conversation.module.css';
11
+ import threadCss from './thread.module.css';
12
+ function factKey(fact) {
13
+ return fact.kind === 'message' ? `message:${fact.message.messageRef}` : `activity:${fact.activity.activityRef}`;
14
+ }
15
+ function messageFact(message, mentions = []) {
16
+ return { kind: 'message', sequence: message.sequence, message, mentions };
17
+ }
18
+ function mergeFacts(...groups) {
19
+ const byKey = new Map();
20
+ for (const group of groups)
21
+ for (const fact of group)
22
+ byKey.set(factKey(fact), fact);
23
+ return [...byKey.values()].sort((left, right) => left.sequence - right.sequence);
24
+ }
25
+ function minSequence(facts) {
26
+ return facts.reduce((minimum, fact) => minimum === undefined ? fact.sequence : Math.min(minimum, fact.sequence), undefined);
27
+ }
28
+ function readMeta(facts) {
29
+ return new Map(facts.map(fact => [factKey(fact.fact), fact]));
30
+ }
31
+ export function TeamThreadPage(props) {
32
+ const { workspaceId, channelRef, taskRef, threadRef, taskNumber, backToWorkspace, loadChannels, readThread, loadThreadHistory, subscribeChanges, loadMembers, reply, changeTask, t, } = props;
33
+ const [projection, setProjection] = useState();
34
+ const [channelView, setChannelView] = useState();
35
+ const [members, setMembers] = useState([]);
36
+ const [currentFacts, setCurrentFacts] = useState([]);
37
+ const [olderFacts, setOlderFacts] = useState([]);
38
+ const [readFacts, setReadFacts] = useState([]);
39
+ const [historyCursor, setHistoryCursor] = useState();
40
+ const [historyHasMore, setHistoryHasMore] = useState(false);
41
+ const [remainingUnreadCount, setRemainingUnreadCount] = useState(0);
42
+ const [newFactsCount, setNewFactsCount] = useState(0);
43
+ const [draft, setDraft] = useState('');
44
+ const [recipients, setRecipients] = useState(new Set());
45
+ const [claimsOpen, setClaimsOpen] = useState(false);
46
+ const [replyRequestId, setReplyRequestId] = useState();
47
+ const [confirmation, setConfirmation] = useState();
48
+ const [statusMessage, setStatusMessage] = useState();
49
+ const [pending, setPending] = useState(false);
50
+ const [loading, setLoading] = useState(true);
51
+ const [error, setError] = useState();
52
+ const mountedRef = useRef(false);
53
+ const currentFactsRef = useRef([]);
54
+ const sequenceRef = useRef(0);
55
+ const readRequestIdRef = useRef(crypto.randomUUID());
56
+ const mutationRequests = useRef(new Map());
57
+ const threadLastFact = currentFacts[currentFacts.length - 1];
58
+ const timeline = useTimelineScroll(`${currentFacts.length}:${olderFacts.length}:${threadLastFact === undefined ? '' : factKey(threadLastFact)}`);
59
+ const updateProjection = (next) => {
60
+ setProjection(next);
61
+ setReadFacts(next.facts);
62
+ setRemainingUnreadCount(next.remainingUnreadCount);
63
+ const anchor = messageFact(next.anchor, next.anchorMentions);
64
+ const batch = [anchor, ...next.facts.map(fact => fact.fact)];
65
+ setCurrentFacts(current => {
66
+ const merged = mergeFacts(current, batch);
67
+ currentFactsRef.current = merged;
68
+ return merged;
69
+ });
70
+ setNewFactsCount(0);
71
+ };
72
+ const readCurrent = async (newRequest = false) => {
73
+ if (!mountedRef.current)
74
+ return false;
75
+ if (newRequest)
76
+ readRequestIdRef.current = crypto.randomUUID();
77
+ const sequence = sequenceRef.current + 1;
78
+ sequenceRef.current = sequence;
79
+ setLoading(true);
80
+ try {
81
+ const result = await readThread({ requestId: readRequestIdRef.current, workspaceId, taskRef });
82
+ if (!mountedRef.current || sequence !== sequenceRef.current)
83
+ return false;
84
+ if (!result.ok) {
85
+ setError(result.error.message);
86
+ return false;
87
+ }
88
+ updateProjection(result.value);
89
+ setError(undefined);
90
+ return true;
91
+ }
92
+ catch (cause) {
93
+ if (mountedRef.current && sequence === sequenceRef.current)
94
+ setError(cause instanceof Error ? cause.message : String(cause));
95
+ return false;
96
+ }
97
+ finally {
98
+ if (mountedRef.current && sequence === sequenceRef.current)
99
+ setLoading(false);
100
+ }
101
+ };
102
+ const refreshSupplemental = async () => {
103
+ try {
104
+ const [loadedMembers, loadedView] = await Promise.all([
105
+ loadMembers({ workspaceId }),
106
+ loadChannels({ workspaceId, ...(channelRef === undefined ? {} : { channelRef }), threadRef, includeActivities: false, limit: 1 }),
107
+ ]);
108
+ if (!mountedRef.current)
109
+ return;
110
+ if (loadedMembers.ok)
111
+ setMembers(loadedMembers.value);
112
+ if (loadedView.ok)
113
+ setChannelView(loadedView.value);
114
+ const failure = [loadedMembers, loadedView].find(result => !result.ok);
115
+ if (failure !== undefined && !failure.ok)
116
+ setError(failure.error.message);
117
+ }
118
+ catch (cause) {
119
+ if (mountedRef.current)
120
+ setError(cause instanceof Error ? cause.message : String(cause));
121
+ }
122
+ };
123
+ const refreshPassiveFacts = async () => {
124
+ try {
125
+ const result = await loadThreadHistory({ workspaceId, taskRef, limit: 100 });
126
+ if (!mountedRef.current || !result.ok)
127
+ return;
128
+ const incoming = result.value.facts;
129
+ const shown = currentFactsRef.current;
130
+ if (shown.length === 0)
131
+ return;
132
+ const known = new Set(shown.map(fact => factKey(fact)));
133
+ // Facts older than everything already rendered are backfill of the
134
+ // wider history window this fetch uses, not new updates; counting
135
+ // them would re-flag already-read messages after every change wake.
136
+ const newestShown = shown.reduce((maximum, fact) => Math.max(maximum, fact.sequence), 0);
137
+ const additions = incoming.filter(fact => !known.has(factKey(fact)) && fact.sequence > newestShown);
138
+ setCurrentFacts(current => {
139
+ const merged = mergeFacts(current, incoming);
140
+ currentFactsRef.current = merged;
141
+ return merged;
142
+ });
143
+ setProjection(current => current === undefined ? current : { ...current, task: result.value.task, thread: result.value.thread, claims: result.value.claims });
144
+ if (additions.length === 0)
145
+ return;
146
+ // A reader scrolled away from the tail must be offered the explicit
147
+ // new-updates action; a reader pinned to the bottom is watching these
148
+ // facts arrive, so they are already seen and the batch is acknowledged
149
+ // durably instead of being counted for an explicit read.
150
+ if (!timeline.isPinned()) {
151
+ setNewFactsCount(current => current + additions.length);
152
+ return;
153
+ }
154
+ const priorSequence = sequenceRef.current;
155
+ if (await readCurrent(true))
156
+ return;
157
+ // The durable acknowledgment did not happen (it failed, a newer read
158
+ // superseded it, or the page unmounted); fall back to the explicit
159
+ // action unless that newer read now owns the tail.
160
+ if (!mountedRef.current || sequenceRef.current !== priorSequence + 1)
161
+ return;
162
+ setNewFactsCount(current => current + additions.length);
163
+ }
164
+ catch {
165
+ // A passive refresh is an invalidation convenience; the next explicit action rereads Host state.
166
+ }
167
+ };
168
+ useEffect(() => {
169
+ mountedRef.current = true;
170
+ setProjection(undefined);
171
+ setChannelView(undefined);
172
+ setMembers([]);
173
+ setCurrentFacts([]);
174
+ currentFactsRef.current = [];
175
+ setOlderFacts([]);
176
+ setReadFacts([]);
177
+ setHistoryCursor(undefined);
178
+ setHistoryHasMore(false);
179
+ setRemainingUnreadCount(0);
180
+ setNewFactsCount(0);
181
+ setError(undefined);
182
+ setStatusMessage(undefined);
183
+ const sequence = sequenceRef.current + 1;
184
+ sequenceRef.current = sequence;
185
+ setLoading(true);
186
+ void (async () => {
187
+ // One parallel round covers the whole first paint. The durable read no
188
+ // longer wakes any change scope, so no second wave follows it.
189
+ const [read, history] = await Promise.all([
190
+ readThread({ requestId: readRequestIdRef.current, workspaceId, taskRef }),
191
+ loadThreadHistory({ workspaceId, taskRef, limit: 20 }).catch(() => undefined),
192
+ ]);
193
+ if (!mountedRef.current || sequence !== sequenceRef.current)
194
+ return;
195
+ if (!read.ok) {
196
+ setError(read.error.message);
197
+ setLoading(false);
198
+ return;
199
+ }
200
+ updateProjection(read.value);
201
+ // Opened onto unread updates: land on the boundary instead of the floor.
202
+ if (read.value.facts.some(fact => fact.unread))
203
+ timeline.jumpToBoundary();
204
+ if (history !== undefined && history.ok) {
205
+ setCurrentFacts(current => {
206
+ const merged = mergeFacts(current, history.value.facts);
207
+ currentFactsRef.current = merged;
208
+ return merged;
209
+ });
210
+ setHistoryCursor(history.value.cursor);
211
+ setHistoryHasMore(history.value.hasMore);
212
+ }
213
+ setError(undefined);
214
+ setLoading(false);
215
+ })();
216
+ void refreshSupplemental();
217
+ const disposers = [
218
+ subscribeChanges({ kind: 'thread', threadRef }, update => {
219
+ if (!mountedRef.current)
220
+ return;
221
+ if (update.type === 'failed') {
222
+ setError(update.message);
223
+ return;
224
+ }
225
+ void refreshPassiveFacts();
226
+ }),
227
+ subscribeChanges({ kind: 'workspace', workspaceId }, update => {
228
+ if (!mountedRef.current)
229
+ return;
230
+ if (update.type === 'failed') {
231
+ setError(update.message);
232
+ return;
233
+ }
234
+ void refreshSupplemental();
235
+ }),
236
+ ];
237
+ return () => {
238
+ mountedRef.current = false;
239
+ sequenceRef.current += 1;
240
+ for (const dispose of disposers)
241
+ dispose();
242
+ };
243
+ }, [workspaceId, taskRef, threadRef]);
244
+ const loadOlder = async () => {
245
+ if (historyHasMore === false && historyCursor === undefined)
246
+ return;
247
+ const beforeSequence = historyCursor ?? minSequence(currentFactsRef.current);
248
+ if (beforeSequence === undefined)
249
+ return;
250
+ setLoading(true);
251
+ try {
252
+ const result = await loadThreadHistory({ workspaceId, taskRef, beforeSequence, limit: 20 });
253
+ if (!mountedRef.current)
254
+ return;
255
+ if (!result.ok) {
256
+ setError(result.error.message);
257
+ return;
258
+ }
259
+ setOlderFacts(current => mergeFacts(current, result.value.facts));
260
+ setHistoryCursor(result.value.cursor);
261
+ setHistoryHasMore(result.value.hasMore);
262
+ setError(undefined);
263
+ }
264
+ catch (cause) {
265
+ if (mountedRef.current)
266
+ setError(cause instanceof Error ? cause.message : String(cause));
267
+ }
268
+ finally {
269
+ if (mountedRef.current)
270
+ setLoading(false);
271
+ }
272
+ };
273
+ const activeProjection = projection;
274
+ const task = activeProjection?.task;
275
+ const thread = activeProjection?.thread;
276
+ const taskTitle = activeProjection === undefined ? undefined : formatTaskTitle(activeProjection.anchor.body);
277
+ const taskClaims = activeProjection?.claims ?? [];
278
+ const effectiveChannelRef = task?.channelRef ?? channelRef;
279
+ const channelMemberIds = useMemo(() => new Set(channelView?.members.filter(item => item.channelRef === effectiveChannelRef).map(item => item.memberId) ?? []), [channelView, effectiveChannelRef]);
280
+ const channelMembers = members.filter(status => channelMemberIds.size === 0 || channelMemberIds.has(status.member.memberId));
281
+ const mentionHandlesMap = useMemo(() => new Map(members.map(status => [status.member.memberId, status.member.handle.replace(/^@/, '')])), [members]);
282
+ const metadata = useMemo(() => readMeta(readFacts), [readFacts]);
283
+ const unreadIndex = useMemo(() => {
284
+ const all = mergeFacts([messageFact(activeProjection?.anchor ?? { messageRef: 'missing', sequence: 0 }, activeProjection?.anchorMentions), ...readFacts.map(fact => fact.fact), ...currentFacts]);
285
+ return all.findIndex(fact => metadata.get(factKey(fact))?.unread === true);
286
+ }, [activeProjection?.anchor, readFacts, currentFacts, metadata]);
287
+ const memberName = (memberId) => {
288
+ if (memberId === channelView?.humanMemberId)
289
+ return t('human');
290
+ const status = members.find(candidate => candidate.member.memberId === memberId);
291
+ return status === undefined ? t('memberUnknown') : `@${status.member.handle}`;
292
+ };
293
+ const messageSender = (fact) => fact.kind === 'message' ? fact.message.sender : undefined;
294
+ const renderFact = (fact, grouped = false) => {
295
+ if (fact.kind === 'message') {
296
+ const sender = memberName(fact.message.sender);
297
+ const senderStatus = members.find(candidate => candidate.member.memberId === fact.message.sender);
298
+ return _jsx(TeamMessage, { senderName: sender, memberId: fact.message.sender, human: fact.message.sender === channelView?.humanMemberId, body: fact.message.body, occurredAt: fact.message.occurredAt, mentionNames: mentionNamesOf(fact.mentions, mentionHandlesMap), grouped: grouped, ...(senderStatus === undefined ? {} : { senderTitle: senderStatus.member.description }) }, factKey(fact));
299
+ }
300
+ return _jsxs("p", { className: threadCss.activityRow, children: [_jsx("span", { className: threadCss.activityMark, "aria-hidden": "true" }), _jsx("span", { className: threadCss.activityText, children: formatActivity(fact.activity, { t, actorName: memberName, claims: taskClaims }) })] }, factKey(fact));
301
+ };
302
+ /** One run = one same-sender reply turn; activities, the unread boundary, and day changes break runs. */
303
+ const renderFactBlocks = (facts, boundaryIndex) => {
304
+ const nodes = [];
305
+ let run = [];
306
+ let lastDay;
307
+ const flushRun = () => {
308
+ if (run.length > 0)
309
+ nodes.push(_jsx("div", { className: css.messageRun, children: run.map((entry, entryIndex) => renderFact(entry, entryIndex > 0)) }, `run-${factKey(run[0])}`));
310
+ run = [];
311
+ };
312
+ facts.forEach((fact, index) => {
313
+ const occurredAt = fact.kind === 'message' ? fact.message.occurredAt : undefined;
314
+ if (occurredAt !== undefined) {
315
+ const day = timelineDayKey(occurredAt);
316
+ if (lastDay !== undefined && day !== lastDay) {
317
+ flushRun();
318
+ nodes.push(_jsx("p", { className: threadCss.daySeparator, children: _jsx("span", { children: daySeparatorLabel(occurredAt) }) }, `day-${index}`));
319
+ }
320
+ lastDay = day;
321
+ }
322
+ const sender = messageSender(fact);
323
+ if (sender !== undefined && run.length > 0 && sender === messageSender(run[run.length - 1])) {
324
+ run.push(fact);
325
+ return;
326
+ }
327
+ flushRun();
328
+ if (boundaryIndex === index)
329
+ nodes.push(_jsx("p", { className: threadCss.unreadBoundary, role: "separator", "data-thread-boundary": true, children: _jsx("span", { children: t('unreadBoundary') }) }, `boundary-${index}`));
330
+ if (sender !== undefined)
331
+ run.push(fact);
332
+ else
333
+ nodes.push(_jsx(Fragment, { children: renderFact(fact) }, factKey(fact)));
334
+ });
335
+ flushRun();
336
+ return nodes;
337
+ };
338
+ const refreshAfterFence = async () => {
339
+ timeline.jumpToLatest();
340
+ await readCurrent(true);
341
+ await refreshSupplemental();
342
+ };
343
+ const mutateTask = async (action) => {
344
+ if (pending || task === undefined || thread === undefined)
345
+ return;
346
+ setPending(true);
347
+ setError(undefined);
348
+ const key = `task:${action}`;
349
+ const requestId = mutationRequests.current.get(key) ?? crypto.randomUUID();
350
+ mutationRequests.current.set(key, requestId);
351
+ try {
352
+ const result = await changeTask({ requestId, workspaceId, taskRef: task.taskRef, action, baseRevision: thread.revision });
353
+ if (!result.ok) {
354
+ setError(result.error.message);
355
+ return;
356
+ }
357
+ if (result.value.kind === 'committed') {
358
+ mutationRequests.current.delete(key);
359
+ const committed = result.value;
360
+ setProjection(current => current === undefined ? current : { ...current, task: committed.task, thread: committed.thread, claims: committed.claims });
361
+ setCurrentFacts(current => {
362
+ const merged = mergeFacts(current, [{ kind: 'activity', sequence: committed.activity.sequence, activity: committed.activity }]);
363
+ currentFactsRef.current = merged;
364
+ return merged;
365
+ });
366
+ await readCurrent(true);
367
+ await refreshSupplemental();
368
+ }
369
+ else if (result.value.kind === 'unread_required') {
370
+ setError(t('unreadRequired', { count: result.value.unreadCount }));
371
+ mutationRequests.current.delete(key);
372
+ await refreshAfterFence();
373
+ }
374
+ else {
375
+ setError(t('staleRevision'));
376
+ mutationRequests.current.delete(key);
377
+ await refreshPassiveFacts();
378
+ }
379
+ }
380
+ catch (cause) {
381
+ setError(cause instanceof Error ? cause.message : String(cause));
382
+ }
383
+ finally {
384
+ setPending(false);
385
+ }
386
+ };
387
+ const sendReply = async () => {
388
+ if (pending || task === undefined || thread === undefined || draft.trim() === '')
389
+ return;
390
+ const id = replyRequestId ?? crypto.randomUUID();
391
+ setReplyRequestId(id);
392
+ setPending(true);
393
+ setError(undefined);
394
+ try {
395
+ const result = await reply({ requestId: id, workspaceId, taskRef: task.taskRef, body: draft.trim(), baseRevision: thread.revision, recipients: [...recipients].sort(), ...(confirmation === undefined ? {} : { confirmationToken: confirmation }) });
396
+ if (!result.ok) {
397
+ setError(result.error.message);
398
+ return;
399
+ }
400
+ if (result.value.kind === 'committed') {
401
+ const committed = result.value;
402
+ setCurrentFacts(current => {
403
+ const merged = mergeFacts(current, [{ kind: 'message', sequence: committed.message.sequence, message: committed.message, mentions: [...recipients].sort() }]);
404
+ currentFactsRef.current = merged;
405
+ return merged;
406
+ });
407
+ setProjection(current => current === undefined ? current : { ...current, task: committed.task, thread: committed.thread });
408
+ setDraft('');
409
+ setRecipients(new Set());
410
+ setReplyRequestId(undefined);
411
+ setConfirmation(undefined);
412
+ setStatusMessage(undefined);
413
+ await refreshSupplemental();
414
+ }
415
+ else if (result.value.kind === 'confirmation_required') {
416
+ setConfirmation(result.value.confirmationToken);
417
+ setStatusMessage(t('mentionConfirmation'));
418
+ }
419
+ else if (result.value.kind === 'unread_required') {
420
+ setError(t('unreadRequired', { count: result.value.unreadCount }));
421
+ setConfirmation(undefined);
422
+ setStatusMessage(undefined);
423
+ setReplyRequestId(undefined);
424
+ await refreshAfterFence();
425
+ }
426
+ else if (result.value.kind === 'stale_revision') {
427
+ setError(t('staleRevision'));
428
+ setConfirmation(undefined);
429
+ setStatusMessage(undefined);
430
+ setReplyRequestId(undefined);
431
+ await refreshPassiveFacts();
432
+ }
433
+ else {
434
+ setError(t('memberNotFollowing', { ids: result.value.memberIds.map(memberId => `@${members.find(candidate => candidate.member.memberId === memberId)?.member.handle ?? memberId}`).join(', ') }));
435
+ setConfirmation(undefined);
436
+ setStatusMessage(undefined);
437
+ setReplyRequestId(undefined);
438
+ }
439
+ }
440
+ catch (cause) {
441
+ setError(cause instanceof Error ? cause.message : String(cause));
442
+ }
443
+ finally {
444
+ setPending(false);
445
+ }
446
+ };
447
+ const currentFactsWithAnchor = mergeFacts(activeProjection === undefined ? [] : [messageFact(activeProjection.anchor, activeProjection.anchorMentions)], currentFacts);
448
+ const unreadBoundary = unreadIndex >= 0 ? unreadIndex : undefined;
449
+ const risks = taskClaims.filter(claim => claim.state === 'active').flatMap(claim => {
450
+ const status = members.find(candidate => candidate.member.memberId === claim.owner);
451
+ return status?.presence === 'error' ? [{ claim, status }] : [];
452
+ });
453
+ // Threads are always entered through a Channel page, so a Channel origin
454
+ // returns to its timeline; a Thread restored without one returns further.
455
+ const backLabel = channelRef === undefined ? t('backToWorkspace') : t('backToChannel');
456
+ return _jsxs("main", { className: css.surface, "data-team-thread": threadRef, children: [_jsxs("div", { className: css.surfaceHeader, children: [_jsx("div", { className: css.backRow, children: _jsx(Button, { size: "sm", icon: _jsx(IconChevronLeftOutline14, {}), onClick: backToWorkspace, children: backLabel }) }), _jsxs("header", { className: css.headerRow, children: [_jsxs("div", { className: css.headerCopy, children: [_jsxs("div", { className: threadCss.titleLine, children: [_jsx("h1", { children: task === undefined ? t('taskPending') : t('taskLabel', { number: taskNumber ?? '…' }) }), task !== undefined && _jsx(Pill, { children: formatTaskStatus(task.status, t) })] }), taskTitle !== undefined && taskTitle !== '' && _jsx("p", { className: threadCss.taskTitle, children: taskTitle })] }), task !== undefined && thread !== undefined && task.resolution !== 'closed' && _jsxs("div", { className: css.headerActions, children: [task.status === 'in_review' && task.resolution === 'open' && _jsx(Button, { size: "sm", variant: "primary", disabled: pending, onClick: () => { void mutateTask('accept'); }, children: t('acceptTask') }), task.resolution === 'open'
457
+ ? _jsx(Button, { size: "sm", variant: "outline", disabled: pending, onClick: () => { void mutateTask('close'); }, children: t('closeTask') })
458
+ : _jsx(Button, { size: "sm", variant: "primary", disabled: pending, onClick: () => { void mutateTask('reopen'); }, children: t('reopenTask') })] })] }), risks.length > 0 && _jsxs("section", { className: threadCss.riskSection, "aria-label": t('runtimeRisk'), children: [_jsx("h2", { children: t('runtimeRisk') }), risks.map(({ claim, status }) => _jsxs("p", { className: threadCss.riskRow, children: [_jsx(TeamPresenceDot, { status: status, t: t }), _jsxs("span", { children: [t('runtimeRiskDetail', { member: status.member.handle, diagnostic: status.diagnostic ?? t('statusError') }), " \u00B7 ", claim.direction] })] }, claim.claimRef))] }), task !== undefined && thread !== undefined && _jsx("section", { className: threadCss.workSection, "aria-label": t('claims'), children: _jsx(DisclosureRow, { expandOnRowClick: true, expandable: true, open: claimsOpen, onToggle: () => { setClaimsOpen(current => !current); }, icon: _jsx(IconChecklistOutline14, { size: 14 }), title: `${t('claims')} · ${taskClaims.length}`, children: _jsxs("div", { className: threadCss.claimList, children: [taskClaims.length === 0 && _jsx("p", { className: threadCss.emptyClaims, children: t('noClaims') }), taskClaims.map(claim => {
459
+ const ownerStatus = members.find(status => status.member.memberId === claim.owner);
460
+ return _jsxs("article", { className: threadCss.claimRow, children: [ownerStatus === undefined ? _jsx("span", {}) : _jsx(TeamPresenceDot, { status: ownerStatus, t: t }), _jsx("strong", { className: threadCss.claimOwner, children: memberName(claim.owner) }), _jsx("span", { className: threadCss.claimDirection, children: claim.direction }), _jsx("small", { className: threadCss.claimState, children: formatClaimState(claim.state, t) })] }, claim.claimRef);
461
+ })] }) }) })] }), _jsx("section", { ref: timeline.ref, onScroll: timeline.onScroll, className: css.timeline, "aria-label": t('timelineLabel'), children: _jsxs("div", { className: css.timelineContent, children: [loading && projection === undefined && error === undefined && _jsx("div", { className: css.emptySurface, children: _jsxs("p", { className: css.loadingState, children: [_jsx("span", { className: css.loadingMark, "aria-hidden": "true" }), t('loadingThread')] }) }), projection === undefined && error !== undefined && _jsxs("div", { className: css.errorState, role: "alert", children: [_jsx("span", { children: error }), _jsx(Button, { size: "sm", variant: "outline", onClick: () => { void readCurrent(); }, children: t('retry') })] }), olderFacts.length > 0 && _jsxs("section", { className: threadCss.historySection, "aria-label": t('olderHistory'), children: [_jsx("h2", { children: t('olderHistory') }), renderFactBlocks(olderFacts, undefined)] }), historyHasMore && _jsx("div", { className: css.timelineAction, children: _jsx(Button, { size: "sm", onClick: () => { void loadOlder(); }, children: t('loadOlder') }) }), currentFactsWithAnchor.length > 0 && _jsx("section", { className: threadCss.publicSection, children: renderFactBlocks(currentFactsWithAnchor, unreadBoundary) }), newFactsCount > 0 && _jsxs("div", { className: threadCss.newUpdates, role: "status", children: [_jsx("span", { children: t('readNewUpdates', { count: newFactsCount }) }), _jsx(Button, { size: "sm", variant: "outline", disabled: loading, onClick: () => { timeline.jumpToLatest(); void readCurrent(true); }, children: t('markRead') })] }), remainingUnreadCount > 0 && _jsxs("div", { className: css.timelineAction, role: "status", children: [_jsx("span", { children: t('remainingUnread', { count: remainingUnreadCount }) }), _jsx(Button, { size: "sm", onClick: () => { timeline.jumpToBoundary(); void readCurrent(true); }, disabled: loading, children: t('continueReading') })] })] }) }), projection !== undefined && task !== undefined && thread !== undefined ? (task.resolution === 'closed'
462
+ ? _jsxs("div", { className: threadCss.closedBar, "data-team-closed": true, children: [error !== undefined && _jsx("p", { className: css.error, role: "alert", children: error }), _jsxs("div", { className: threadCss.closedNotice, children: [_jsx("span", { children: t('taskClosedNotice') }), _jsx(Button, { size: "sm", variant: "outline", disabled: pending, onClick: () => { void mutateTask('reopen'); }, children: t('reopenTask') })] })] })
463
+ : _jsx(TeamComposer, { members: channelMembers, recipients: recipients, draft: draft, pending: pending, ...(statusMessage === undefined ? {} : { confirmation: statusMessage }), ...(error === undefined ? {} : { error }), onDraftChange: next => { setDraft(next); setConfirmation(undefined); setReplyRequestId(undefined); setStatusMessage(undefined); }, onRecipientsChange: next => { setRecipients(next); setConfirmation(undefined); setReplyRequestId(undefined); setStatusMessage(undefined); }, onSubmit: () => { void sendReply(); }, t: t })) : _jsx("div", {})] });
464
+ }
@@ -0,0 +1,3 @@
1
+ import type { TeamSidebarProps } from './slots.ts';
2
+ export declare function TeamWorkspaceBrowser({ wide, expandSidebar, navigation, selectWorkspace, selectChannel, t, useWorkspaces, loadMembers, subscribeChanges, addMember, loadChannels, createChannel, updateChannel, updateMember, joinChannel, removeChannelMember, loadModels, openMemberSession }: TeamSidebarProps): import("react").JSX.Element;
3
+ //# sourceMappingURL=TeamWorkspaceBrowser.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"TeamWorkspaceBrowser.d.ts","sourceRoot":"","sources":["../../../src/client/TeamWorkspaceBrowser.tsx"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,YAAY,CAAA;AAQlD,wBAAgB,oBAAoB,CAAC,EAAE,IAAI,EAAE,aAAa,EAAE,UAAU,EAAE,eAAe,EAAE,aAAa,EAAE,CAAC,EAAE,aAAa,EAAE,WAAW,EAAE,gBAAgB,EAAE,SAAS,EAAE,YAAY,EAAE,aAAa,EAAE,aAAa,EAAE,YAAY,EAAE,WAAW,EAAE,mBAAmB,EAAE,UAAU,EAAE,iBAAiB,EAAE,EAAE,gBAAgB,+BA2DhT"}
@@ -0,0 +1,39 @@
1
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
+ import { useEffect, useRef, useState, useSyncExternalStore } from 'react';
3
+ import { IconAgentPresetOutline16, IconListPenOutline16, Tooltip } from '@deepseek-ai/dsh-client-ui-primitives';
4
+ import { TeamWorkspaceRow } from "./TeamWorkspaceRow.js";
5
+ import { TeamAgentsPanel } from "./TeamAgentsPanel.js";
6
+ import { TeamChannelsPanel } from "./TeamChannelsPanel.js";
7
+ import css from './sidebar.module.css';
8
+ export function TeamWorkspaceBrowser({ wide, expandSidebar, navigation, selectWorkspace, selectChannel, t, useWorkspaces, loadMembers, subscribeChanges, addMember, loadChannels, createChannel, updateChannel, updateMember, joinChannel, removeChannelMember, loadModels, openMemberSession }) {
9
+ const navigationState = useSyncExternalStore(navigation.subscribe, navigation.getSnapshot, navigation.getSnapshot);
10
+ const workspaces = useWorkspaces(state => state.items);
11
+ const selected = navigationState.workspaceId;
12
+ const selectedExists = selected !== undefined && workspaces.some(workspace => workspace.workspaceId === selected);
13
+ const selectedId = selectedExists ? selected : workspaces[0]?.workspaceId;
14
+ // Exactly one sidebar row carries aria-current='page': the open Channel while
15
+ // one is set, otherwise the browsed Workspace's overview. The selected row
16
+ // keeps its quiet folder tint (data-selected) in both cases.
17
+ const overviewIsCurrent = navigationState.channelRef === undefined;
18
+ const [creatingAgents, setCreatingAgents] = useState([]);
19
+ // Rail icons request expansion and name the section to reveal once wide.
20
+ const [pendingSection, setPendingSection] = useState();
21
+ const channelsRef = useRef(null);
22
+ const agentsRef = useRef(null);
23
+ useEffect(() => {
24
+ if (navigationState.mode === 'team' && selectedId !== undefined && selectedId !== selected) {
25
+ selectWorkspace(selectedId);
26
+ }
27
+ }, [navigationState.mode, selected, selectedId, selectWorkspace]);
28
+ useEffect(() => {
29
+ if (!wide || pendingSection === undefined)
30
+ return;
31
+ const node = pendingSection === 'agents' ? agentsRef.current : channelsRef.current;
32
+ setPendingSection(undefined);
33
+ queueMicrotask(() => { node?.querySelector('button')?.focus(); });
34
+ }, [wide, pendingSection]);
35
+ if (!wide) {
36
+ return _jsxs("nav", { className: css.railWorkspace, "aria-label": t('workspaceSections'), children: [_jsx(Tooltip, { label: t('channels'), side: "right", children: _jsx("button", { type: "button", className: css.railButton, "aria-label": t('channels'), onClick: () => { setPendingSection('channels'); expandSidebar(); }, children: _jsx(IconListPenOutline16, { size: 16 }) }) }), _jsx(Tooltip, { label: t('agents'), side: "right", children: _jsx("button", { type: "button", className: css.railButton, "aria-label": t('agents'), onClick: () => { setPendingSection('agents'); expandSidebar(); }, children: _jsx(IconAgentPresetOutline16, { size: 16 }) }) })] });
37
+ }
38
+ return _jsxs("section", { className: css.workspaceBrowser, "aria-label": t('workspaces'), children: [_jsx("div", { className: css.workspaceHeader, children: t('workspaces') }), _jsxs("div", { className: css.workspaceList, children: [workspaces.map(workspace => _jsx(TeamWorkspaceRow, { workspaceId: workspace.workspaceId, title: workspace.title, path: workspace.path, selected: workspace.workspaceId === selectedId, current: workspace.workspaceId === selectedId && overviewIsCurrent, onSelect: selectWorkspace }, workspace.workspaceId)), workspaces.length === 0 && _jsx("p", { className: css.emptyState, children: t('empty') })] }), selectedId !== undefined && _jsxs("div", { className: css.workspaceSection, children: [_jsx("div", { ref: channelsRef, children: _jsx(TeamChannelsPanel, { workspaceId: selectedId, loadMembers: loadMembers, loadChannels: loadChannels, subscribeChanges: subscribeChanges, createChannel: createChannel, updateChannel: updateChannel, joinChannel: joinChannel, removeChannelMember: removeChannelMember, creatingAgents: creatingAgents.filter(request => request.workspaceId === selectedId), ...(navigationState.channelRef === undefined ? {} : { selectedChannelRef: navigationState.channelRef }), selectChannel: selectChannel, t: t }, selectedId) }), _jsx("div", { ref: agentsRef, children: _jsx(TeamAgentsPanel, { workspaceId: selectedId, loadMembers: loadMembers, subscribeChanges: subscribeChanges, loadChannels: loadChannels, addMember: addMember, updateMember: updateMember, joinChannel: joinChannel, removeChannelMember: removeChannelMember, loadModels: loadModels, openMemberSession: openMemberSession, onCreatingChange: (request, creating) => { setCreatingAgents(current => creating ? [...current.filter(item => item.requestId !== request.requestId), request] : current.filter(item => item.requestId !== request.requestId)); }, t: t }, selectedId) })] })] });
39
+ }
@@ -0,0 +1,11 @@
1
+ import type { WorkspaceId } from '@deepseek-ai/dsh-client-runtime/client';
2
+ export declare function TeamWorkspaceRow({ workspaceId, title, path, selected, current, onSelect }: {
3
+ workspaceId: WorkspaceId;
4
+ title: string;
5
+ path: string;
6
+ selected: boolean;
7
+ /** The Team center shows this Workspace's overview (no Channel is open). */
8
+ current: boolean;
9
+ onSelect: (workspaceId: WorkspaceId) => void;
10
+ }): import("react").JSX.Element;
11
+ //# sourceMappingURL=TeamWorkspaceRow.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"TeamWorkspaceRow.d.ts","sourceRoot":"","sources":["../../../src/client/TeamWorkspaceRow.tsx"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,wCAAwC,CAAA;AAGzE,wBAAgB,gBAAgB,CAAC,EAAE,WAAW,EAAE,KAAK,EAAE,IAAI,EAAE,QAAQ,EAAE,OAAO,EAAE,QAAQ,EAAE,EAAE;IAC1F,WAAW,EAAE,WAAW,CAAA;IACxB,KAAK,EAAE,MAAM,CAAA;IACb,IAAI,EAAE,MAAM,CAAA;IACZ,QAAQ,EAAE,OAAO,CAAA;IACjB,4EAA4E;IAC5E,OAAO,EAAE,OAAO,CAAA;IAChB,QAAQ,EAAE,CAAC,WAAW,EAAE,WAAW,KAAK,IAAI,CAAA;CAC7C,+BAgBA"}
@@ -0,0 +1,6 @@
1
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
+ import { IconFolderClose16, IconFolderOpen16 } from '@deepseek-ai/dsh-client-ui-primitives';
3
+ import css from './sidebar.module.css';
4
+ export function TeamWorkspaceRow({ workspaceId, title, path, selected, current, onSelect }) {
5
+ return (_jsxs("button", { type: "button", className: css.workspaceRow, "data-selected": selected || undefined, "aria-current": current ? 'page' : undefined, onClick: () => { onSelect(workspaceId); }, title: `${title} · ${path}`, children: [_jsx("span", { className: css.workspaceIcon, "aria-hidden": "true", children: selected ? _jsx(IconFolderOpen16, { size: 16 }) : _jsx(IconFolderClose16, { size: 16 }) }), _jsx("span", { className: css.workspaceCopy, children: _jsx("strong", { children: title }) })] }));
6
+ }
@@ -0,0 +1,19 @@
1
+ import type { ClientContext } from '@deepseek-ai/dsh-client-runtime/client';
2
+ import { TeamNavigation } from './navigation.ts';
3
+ import { type TeamKey } from './locales.ts';
4
+ export type { TeamMode, TeamNavigationActions, TeamNavigationSnapshot } from './navigation.ts';
5
+ export type { TeamKey } from './locales.ts';
6
+ export { TeamNavigation } from './navigation.ts';
7
+ export declare const inject: string[];
8
+ declare module '@deepseek-ai/dsh-client-ui-slots' {
9
+ interface LocaleNamespaceMap {
10
+ team: TeamKey;
11
+ }
12
+ }
13
+ declare module '@deepseek-ai/cordis' {
14
+ interface Context {
15
+ teamNavigation: TeamNavigation;
16
+ }
17
+ }
18
+ export declare function apply(ctx: ClientContext): Promise<void>;
19
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/client/index.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,aAAa,EAAa,MAAM,wCAAwC,CAAA;AA0BtF,OAAO,EAAE,cAAc,EAAE,MAAM,iBAAiB,CAAA;AAMhD,OAAO,EAAU,KAAK,OAAO,EAAE,MAAM,cAAc,CAAA;AAEnD,YAAY,EAAE,QAAQ,EAAE,qBAAqB,EAAE,sBAAsB,EAAE,MAAM,iBAAiB,CAAA;AAC9F,YAAY,EAAE,OAAO,EAAE,MAAM,cAAc,CAAA;AAC3C,OAAO,EAAE,cAAc,EAAE,MAAM,iBAAiB,CAAA;AAIhD,eAAO,MAAM,MAAM,UAElB,CAAA;AAED,OAAO,QAAQ,kCAAkC,CAAC;IAChD,UAAU,kBAAkB;QAC1B,IAAI,EAAE,OAAO,CAAA;KACd;CACF;AAED,OAAO,QAAQ,qBAAqB,CAAC;IACnC,UAAU,OAAO;QACf,cAAc,EAAE,cAAc,CAAA;KAC/B;CACF;AA+GD,wBAAsB,KAAK,CAAC,GAAG,EAAE,aAAa,GAAG,OAAO,CAAC,IAAI,CAAC,CAI7D"}