@wowyuarm/dsh-agent-team 0.1.14-alpha.2 → 0.1.14

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 (127) hide show
  1. package/README.md +5 -3
  2. package/README.zh.md +5 -3
  3. package/cordis.patch.yml +2 -185
  4. package/package.json +52 -46
  5. package/packages/agent-team/README.md +1 -1
  6. package/packages/agent-team/README.zh.md +1 -1
  7. package/packages/agent-team/core-skills/member-memory-manager/SKILL.md +30 -0
  8. package/packages/agent-team/lib/context-continuity-host.js +91 -0
  9. package/packages/agent-team/lib/context-projection.js +266 -489
  10. package/packages/agent-team/lib/context-source.js +17 -106
  11. package/packages/agent-team/lib/human-avatar.js +61 -0
  12. package/packages/agent-team/lib/human-profile.js +46 -0
  13. package/packages/agent-team/lib/human-update-check.js +119 -0
  14. package/packages/agent-team/lib/index.js +408 -264
  15. package/packages/agent-team/lib/ledger.js +120 -15
  16. package/packages/agent-team/lib/member-context.js +9 -8
  17. package/packages/agent-team/lib/member-runtime.js +1 -1
  18. package/packages/agent-team/lib/member-time-context.js +2 -5
  19. package/packages/agent-team/lib/preset-roster.js +15 -0
  20. package/packages/agent-team/lib/pressure-policy.js +9 -6
  21. package/packages/agent-team/lib/session-remediation.js +493 -0
  22. package/packages/agent-team/lib/stored-session-reader.js +2 -1
  23. package/packages/agent-team/lib/typert.host.js +605 -291
  24. package/packages/agent-team/lib/typert.remote-client.d.ts +15 -6
  25. package/packages/agent-team/lib/typert.remote-client.d.ts.map +1 -1
  26. package/packages/agent-team/lib/typert.remote-client.js +367 -244
  27. package/packages/agent-team/lib/types/context-continuity-host.d.ts +84 -0
  28. package/packages/agent-team/lib/types/context-continuity-host.d.ts.map +1 -0
  29. package/packages/agent-team/lib/types/context-projection.d.ts +130 -185
  30. package/packages/agent-team/lib/types/context-projection.d.ts.map +1 -1
  31. package/packages/agent-team/lib/types/context-source.d.ts +17 -81
  32. package/packages/agent-team/lib/types/context-source.d.ts.map +1 -1
  33. package/packages/agent-team/lib/types/human-avatar.d.ts +29 -0
  34. package/packages/agent-team/lib/types/human-avatar.d.ts.map +1 -0
  35. package/packages/agent-team/lib/types/human-profile.d.ts +44 -0
  36. package/packages/agent-team/lib/types/human-profile.d.ts.map +1 -0
  37. package/packages/agent-team/lib/types/human-update-check.d.ts +73 -0
  38. package/packages/agent-team/lib/types/human-update-check.d.ts.map +1 -0
  39. package/packages/agent-team/lib/types/index.d.ts +112 -38
  40. package/packages/agent-team/lib/types/index.d.ts.map +1 -1
  41. package/packages/agent-team/lib/types/ledger.d.ts +31 -2
  42. package/packages/agent-team/lib/types/ledger.d.ts.map +1 -1
  43. package/packages/agent-team/lib/types/member-context.d.ts +0 -14
  44. package/packages/agent-team/lib/types/member-context.d.ts.map +1 -1
  45. package/packages/agent-team/lib/types/member-time-context.d.ts +0 -15
  46. package/packages/agent-team/lib/types/member-time-context.d.ts.map +1 -1
  47. package/packages/agent-team/lib/types/preset-roster.d.ts +5 -0
  48. package/packages/agent-team/lib/types/preset-roster.d.ts.map +1 -0
  49. package/packages/agent-team/lib/types/pressure-policy.d.ts +6 -0
  50. package/packages/agent-team/lib/types/pressure-policy.d.ts.map +1 -1
  51. package/packages/agent-team/lib/types/session-remediation.d.ts +172 -0
  52. package/packages/agent-team/lib/types/session-remediation.d.ts.map +1 -0
  53. package/packages/agent-team/lib/types/stored-session-reader.d.ts +2 -1
  54. package/packages/agent-team/lib/types/stored-session-reader.d.ts.map +1 -1
  55. package/packages/agent-team/lib/types/types/entities.d.ts +20 -3
  56. package/packages/agent-team/lib/types/types/entities.d.ts.map +1 -1
  57. package/packages/agent-team/lib/types/types/requests-results.d.ts +63 -0
  58. package/packages/agent-team/lib/types/types/requests-results.d.ts.map +1 -1
  59. package/packages/agent-team/preset/team-member/agent.cordis.yml +166 -0
  60. package/packages/client-agent-team/lib/client.js +1667 -516
  61. package/packages/client-agent-team/lib/client.js.map +1 -1
  62. package/packages/client-agent-team/lib/types/client/HumanSettingsSection.d.ts +15 -0
  63. package/packages/client-agent-team/lib/types/client/HumanSettingsSection.d.ts.map +1 -0
  64. package/packages/client-agent-team/lib/types/client/HumanSettingsSection.js +115 -0
  65. package/packages/client-agent-team/lib/types/client/TeamAgentsPanel.d.ts.map +1 -1
  66. package/packages/client-agent-team/lib/types/client/TeamAgentsPanel.js +12 -8
  67. package/packages/client-agent-team/lib/types/client/TeamAvatarStack.d.ts +22 -1
  68. package/packages/client-agent-team/lib/types/client/TeamAvatarStack.d.ts.map +1 -1
  69. package/packages/client-agent-team/lib/types/client/TeamAvatarStack.js +25 -2
  70. package/packages/client-agent-team/lib/types/client/TeamChannelPage.d.ts +6 -1
  71. package/packages/client-agent-team/lib/types/client/TeamChannelPage.d.ts.map +1 -1
  72. package/packages/client-agent-team/lib/types/client/TeamChannelPage.js +69 -31
  73. package/packages/client-agent-team/lib/types/client/TeamChannelsPanel.js +4 -4
  74. package/packages/client-agent-team/lib/types/client/TeamComposer.js +3 -3
  75. package/packages/client-agent-team/lib/types/client/TeamConversation.d.ts +1 -1
  76. package/packages/client-agent-team/lib/types/client/TeamConversation.d.ts.map +1 -1
  77. package/packages/client-agent-team/lib/types/client/TeamConversation.js +12 -5
  78. package/packages/client-agent-team/lib/types/client/TeamFooterAction.js +2 -2
  79. package/packages/client-agent-team/lib/types/client/TeamInboxPage.d.ts +4 -1
  80. package/packages/client-agent-team/lib/types/client/TeamInboxPage.d.ts.map +1 -1
  81. package/packages/client-agent-team/lib/types/client/TeamInboxPage.js +22 -7
  82. package/packages/client-agent-team/lib/types/client/TeamMemberEditor.d.ts +11 -1
  83. package/packages/client-agent-team/lib/types/client/TeamMemberEditor.d.ts.map +1 -1
  84. package/packages/client-agent-team/lib/types/client/TeamMemberEditor.js +69 -8
  85. package/packages/client-agent-team/lib/types/client/TeamMembersAction.js +2 -2
  86. package/packages/client-agent-team/lib/types/client/TeamMessage.d.ts +18 -3
  87. package/packages/client-agent-team/lib/types/client/TeamMessage.d.ts.map +1 -1
  88. package/packages/client-agent-team/lib/types/client/TeamMessage.js +213 -67
  89. package/packages/client-agent-team/lib/types/client/TeamRowMenu.d.ts.map +1 -1
  90. package/packages/client-agent-team/lib/types/client/TeamRowMenu.js +2 -2
  91. package/packages/client-agent-team/lib/types/client/TeamSidebarSection.js +2 -2
  92. package/packages/client-agent-team/lib/types/client/TeamThreadPage.d.ts +5 -0
  93. package/packages/client-agent-team/lib/types/client/TeamThreadPage.d.ts.map +1 -1
  94. package/packages/client-agent-team/lib/types/client/TeamThreadPage.js +55 -29
  95. package/packages/client-agent-team/lib/types/client/TeamWorkspaceBrowser.js +3 -3
  96. package/packages/client-agent-team/lib/types/client/TeamWorkspaceSelector.js +2 -2
  97. package/packages/client-agent-team/lib/types/client/avatar-image.d.ts +21 -0
  98. package/packages/client-agent-team/lib/types/client/avatar-image.d.ts.map +1 -0
  99. package/packages/client-agent-team/lib/types/client/avatar-image.js +9 -0
  100. package/packages/client-agent-team/lib/types/client/human-identity.d.ts +94 -0
  101. package/packages/client-agent-team/lib/types/client/human-identity.d.ts.map +1 -0
  102. package/packages/client-agent-team/lib/types/client/human-identity.js +117 -0
  103. package/packages/client-agent-team/lib/types/client/index.d.ts.map +1 -1
  104. package/packages/client-agent-team/lib/types/client/index.js +112 -41
  105. package/packages/client-agent-team/lib/types/client/locales.d.ts +72 -2
  106. package/packages/client-agent-team/lib/types/client/locales.d.ts.map +1 -1
  107. package/packages/client-agent-team/lib/types/client/locales.js +78 -2
  108. package/packages/client-agent-team/lib/types/client/multi-menu-field.js +2 -2
  109. package/packages/client-agent-team/lib/types/client/refs.d.ts +71 -0
  110. package/packages/client-agent-team/lib/types/client/refs.d.ts.map +1 -0
  111. package/packages/client-agent-team/lib/types/client/refs.js +181 -0
  112. package/packages/client-agent-team/lib/types/client/slots.d.ts +8 -2
  113. package/packages/client-agent-team/lib/types/client/slots.d.ts.map +1 -1
  114. package/packages/client-agent-team/lib/types/client/team-formatters.d.ts +57 -9
  115. package/packages/client-agent-team/lib/types/client/team-formatters.d.ts.map +1 -1
  116. package/packages/client-agent-team/lib/types/client/team-formatters.js +85 -17
  117. package/packages/tool-agent-team/README.md +1 -1
  118. package/packages/tool-agent-team/README.zh.md +1 -1
  119. package/packages/tool-agent-team/lib/context-tools.js +20 -6
  120. package/packages/tool-agent-team/lib/index.js +2 -2
  121. package/packages/tool-agent-team/lib/types/context-tools.d.ts.map +1 -1
  122. package/packages/agent-team/lib/context-management.js +0 -371
  123. package/packages/agent-team/lib/types/context-management.d.ts +0 -154
  124. package/packages/agent-team/lib/types/context-management.d.ts.map +0 -1
  125. package/packages/client-agent-team/lib/types/client/task-refs.d.ts +0 -31
  126. package/packages/client-agent-team/lib/types/client/task-refs.d.ts.map +0 -1
  127. package/packages/client-agent-team/lib/types/client/task-refs.js +0 -99
@@ -2,8 +2,10 @@ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
2
  import { Fragment, memo, useCallback, useEffect, useLayoutEffect, useMemo, useRef, useState } from 'react';
3
3
  import { MarkdownText, Modal } from '@deepseek-ai/dsh-client-ui-primitives';
4
4
  import { cachedAttachmentDataUrl, formatByteSize, loadAttachmentDataUrl } from "./attachment-preview.js";
5
- import { cachedResolvedTaskRef, resolveUnknownTaskRefs, useResolvedTaskRefVersion } from "./task-refs.js";
5
+ import { cachedResolvedTaskRef, resolveUnknownTaskRefs, useResolvedTaskRefVersion } from "./refs.js";
6
+ import { cachedResolvedThreadRef, resolveUnknownThreadRefs, useResolvedThreadRefVersion } from "./refs.js";
6
7
  import { formatMessageTime, isSingleBrandedRef, memberHue, planMessageBody, shouldClampMessage, splitBrandedRefs, splitMentionNames } from "./team-formatters.js";
8
+ import { useAvatarImage } from "./avatar-image.js";
7
9
  import css from './conversation.module.css';
8
10
  /**
9
11
  * One chat message row with identity chrome and sender-appropriate rendering.
@@ -13,30 +15,49 @@ import css from './conversation.module.css';
13
15
  * skipping a render here never detaches it. Callers must therefore keep the
14
16
  * props they derive per render (mention names, ref callbacks) identity-stable.
15
17
  */
16
- export const TeamMessage = memo(function TeamMessage({ senderName, memberId, human, body, occurredAt, mentionNames, senderTitle, grouped, showGroupedTime, attachments, loadAttachment, t, onOpenRef, onResolveTaskRefs, children }) {
18
+ export const TeamMessage = memo(function TeamMessage({ senderName, memberId, human, avatarUrl, body, occurredAt, mentionNames, senderTitle, grouped, showGroupedTime, attachments, loadAttachment, t, onOpenRef, onResolveTaskRefs, onResolveThreadRefs, channelNameOf, memberOf, onOpenMemberSession, children }) {
17
19
  const avatarStyle = human ? undefined : { '--team-avatar-hue': memberHue(memberId) };
20
+ // Only the Human's own row may draw a picture: the profile owns those bytes,
21
+ // and one seat painting the reader's face for another author would name two
22
+ // people alike. A seat draws it while those bytes decode; anything else keeps
23
+ // the initial, which is what the fallback promises.
24
+ const identityImage = useAvatarImage(human ? avatarUrl : undefined);
18
25
  // Literal bodies carry mention chips inline — Human input always, and
19
26
  // plain-prose Agent bodies where literal rendering loses nothing. Rich
20
27
  // Markdown keeps unmatched structured mentions in the trailing row.
21
28
  // The stored body carries machine-facing `[attachment] <path>` prompt lines;
22
29
  // humans see the attachment strip rendered from the message metadata instead.
23
30
  // One pure plan resolves the stored body into the rendering branch, the
24
- // trailing fallback rows, and the literal Task refs that resolve in place.
31
+ // trailing fallback rows, and the literal Task/Thread refs that resolve in place.
25
32
  const plan = planMessageBody(body, { human, ...(mentionNames === undefined ? {} : { mentionNames }), canOpenRefs: onOpenRef !== undefined });
26
33
  const displayBody = plan.displayBody;
27
34
  const { richAgentBody } = plan;
28
- // Resolved refs re-label once the Host lookup lands; the version token
29
- // refreshes literal links and rendered Markdown prose.
30
- const refVersion = useResolvedTaskRefVersion();
35
+ // Resolved refs re-label once the Host lookup lands; the version tokens
36
+ // refresh literal links and rendered Markdown prose.
37
+ const taskRefVersion = useResolvedTaskRefVersion();
38
+ const threadRefVersion = useResolvedThreadRefVersion();
31
39
  const bodyTaskRefs = plan.taskRefs;
32
40
  const bodyTaskRefKey = bodyTaskRefs.join(',');
41
+ const bodyThreadRefs = plan.threadRefs;
42
+ const bodyThreadRefKey = bodyThreadRefs.join(',');
33
43
  useEffect(() => {
34
- if (onResolveTaskRefs === undefined || bodyTaskRefKey === '')
35
- return;
36
- void resolveUnknownTaskRefs(bodyTaskRefs, onResolveTaskRefs);
37
- }, [onResolveTaskRefs, bodyTaskRefKey, refVersion]);
44
+ if (onResolveTaskRefs !== undefined && bodyTaskRefKey !== '')
45
+ void resolveUnknownTaskRefs(bodyTaskRefs, onResolveTaskRefs);
46
+ if (onResolveThreadRefs !== undefined && bodyThreadRefKey !== '')
47
+ void resolveUnknownThreadRefs(bodyThreadRefs, onResolveThreadRefs);
48
+ }, [onResolveTaskRefs, onResolveThreadRefs, bodyTaskRefKey, bodyThreadRefKey, taskRefVersion, threadRefVersion]);
38
49
  const taskLabel = useCallback((taskNumber) => t?.('taskLabel', { number: taskNumber }) ?? `Task #${taskNumber}`, [t]);
39
- const refLabel = useCallback((ref) => ref.startsWith('thread:') ? (t?.('threadLabel') ?? 'Thread') : ref.startsWith('channel:') ? (t?.('channels') ?? 'Channels') : ref, [t]);
50
+ // Thread chips carry the cited Thread's opening-line gist, so one taskless
51
+ // Thread no longer reads exactly like the next. Unresolvable refs never
52
+ // reach this label — they stay plain text (see renderRefs).
53
+ const threadChipLabel = useCallback((title) => {
54
+ const base = t?.('threadLabel') ?? 'Thread';
55
+ return title === '' ? base : `${base} · ${title}`;
56
+ }, [t]);
57
+ // Channel chips name the cited Channel; member chips name the cited Member
58
+ // with a handle — deliberately distinct from `@mention` chips, which notify.
59
+ const channelChipLabel = useCallback((name) => t?.('channelLabel', { name }) ?? `Channel · ${name}`, [t]);
60
+ const memberChipLabel = useCallback((name) => t?.('memberLabel', { name }) ?? `Member · @${name}`, [t]);
40
61
  // Markdown chrome (code-copy buttons, footnotes heading) is locale copy the
41
62
  // cordis-free primitive receives via props. Stable per locale revision — a
42
63
  // fresh object per render would rebuild the component table every chunk.
@@ -61,19 +82,31 @@ export const TeamMessage = memo(function TeamMessage({ senderName, memberId, hum
61
82
  .flatMap(text => splitBrandedRefs(text)
62
83
  .filter(segment => segment.ref?.startsWith('task:') === true)
63
84
  .map(segment => segment.ref)))];
85
+ const threadRefs = [...new Set([...textNodes.map(node => node.data), ...styledRefCodes.map(code => code.textContent ?? '')]
86
+ .flatMap(text => splitBrandedRefs(text)
87
+ .filter(segment => segment.ref?.startsWith('thread:') === true)
88
+ .map(segment => segment.ref)))];
64
89
  if (onResolveTaskRefs !== undefined && taskRefs.length > 0)
65
90
  void resolveUnknownTaskRefs(taskRefs, onResolveTaskRefs);
91
+ if (onResolveThreadRefs !== undefined && threadRefs.length > 0)
92
+ void resolveUnknownThreadRefs(threadRefs, onResolveThreadRefs);
66
93
  for (const code of styledRefCodes)
67
- renderResolvedMarkdownCodeRef(code, taskLabel, refLabel);
94
+ renderResolvedMarkdownCodeRef(code, taskLabel, threadChipLabel, channelChipLabel, memberChipLabel, channelNameOf, memberOf);
68
95
  for (const node of textNodes)
69
- renderResolvedMarkdownText(node, mentionNames ?? [], taskLabel, refLabel);
96
+ renderResolvedMarkdownText(node, mentionNames ?? [], taskLabel, threadChipLabel, channelChipLabel, memberChipLabel, channelNameOf, memberOf);
70
97
  for (const button of root.querySelectorAll('button[data-task-ref]')) {
71
98
  const taskRef = button.dataset.taskRef;
72
99
  const hit = taskRef === undefined ? undefined : cachedResolvedTaskRef(taskRef);
73
100
  if (taskRef !== undefined && hit !== undefined)
74
101
  button.textContent = taskLabel(hit.taskNumber);
75
102
  }
76
- }, [richAgentBody, onOpenRef, onResolveTaskRefs, refVersion, taskLabel, refLabel, mentionNames]);
103
+ for (const button of root.querySelectorAll('button[data-thread-ref]')) {
104
+ const threadRef = button.dataset.threadRef;
105
+ const hit = threadRef === undefined ? undefined : cachedResolvedThreadRef(threadRef);
106
+ if (threadRef !== undefined && hit !== undefined)
107
+ button.textContent = threadChipLabel(hit.title);
108
+ }
109
+ }, [richAgentBody, onOpenRef, onResolveTaskRefs, onResolveThreadRefs, taskRefVersion, threadRefVersion, taskLabel, threadChipLabel, channelChipLabel, memberChipLabel, channelNameOf, memberOf, mentionNames]);
77
110
  useEffect(() => {
78
111
  const root = markdownRef.current;
79
112
  if (!richAgentBody || root === null || onOpenRef === undefined)
@@ -82,24 +115,35 @@ export const TeamMessage = memo(function TeamMessage({ senderName, memberId, hum
82
115
  const target = event.target;
83
116
  if (!(target instanceof Element))
84
117
  return;
85
- const button = target.closest('button[data-ref], button[data-task-ref]');
118
+ const button = target.closest('button[data-ref], button[data-task-ref], button[data-thread-ref], button[data-member-session]');
86
119
  if (button === null || !root.contains(button))
87
120
  return;
88
- const ref = button instanceof HTMLElement ? button.dataset.ref ?? button.dataset.taskRef : undefined;
89
- if (ref !== undefined)
90
- onOpenRef(ref);
121
+ if (button instanceof HTMLElement) {
122
+ // Member chips carry their session, not a Team ref: the same jump
123
+ // the agent card performs. Every other chip resolves to onOpenRef.
124
+ const sessionId = button.dataset.memberSession;
125
+ if (sessionId !== undefined) {
126
+ onOpenMemberSession?.(sessionId);
127
+ return;
128
+ }
129
+ const ref = button.dataset.ref ?? button.dataset.taskRef ?? button.dataset.threadRef;
130
+ if (ref !== undefined)
131
+ onOpenRef(ref);
132
+ }
91
133
  };
92
134
  root.addEventListener('click', openTask);
93
135
  return () => { root.removeEventListener('click', openTask); };
94
- }, [richAgentBody, onOpenRef]);
136
+ }, [richAgentBody, onOpenRef, onOpenMemberSession]);
95
137
  const bodyNode = plan.render === 'inline' && plan.inline !== undefined
96
138
  ? _jsx("div", { className: css.messageText, children: plan.inline.segments.map((segment, index) => segment.mention
97
139
  ? _jsx("span", { className: css.mention, children: segment.text }, index)
98
- : _jsx(Fragment, { children: renderRefs(segment.text, onOpenRef, taskLabel, refLabel) }, index)) })
140
+ : _jsx(Fragment, { children: renderRefs(segment.text, onOpenRef, onOpenMemberSession, taskLabel, threadChipLabel, channelChipLabel, memberChipLabel, channelNameOf, memberOf) }, index)) })
99
141
  : plan.render === 'literal'
100
- ? _jsx("div", { className: css.messageText, children: onOpenRef === undefined ? displayBody : renderRefs(displayBody, onOpenRef, taskLabel, refLabel) })
142
+ ? _jsx("div", { className: css.messageText, children: onOpenRef === undefined ? displayBody : renderRefs(displayBody, onOpenRef, onOpenMemberSession, taskLabel, threadChipLabel, channelChipLabel, memberChipLabel, channelNameOf, memberOf) })
101
143
  : _jsx("div", { ref: markdownRef, className: css.messageMarkdown, children: _jsx(MarkdownText, { text: displayBody, labels: markdownLabels }, `${displayBody}:${onOpenRef === undefined ? 'literal' : 'refs'}`) });
102
- return (_jsxs("article", { className: css.messageRow, "data-human": human || undefined, "data-grouped": grouped || undefined, children: [_jsx("div", { className: css.messageIdentity, style: avatarStyle, "aria-hidden": "true", children: senderName.replace('@', '').slice(0, 1).toUpperCase() }), _jsxs("div", { className: css.messageBody, children: [(!grouped || showGroupedTime === true) && (_jsxs("div", { className: css.nameRow, children: [!grouped && _jsx("strong", { ...(senderTitle === undefined ? {} : { title: senderTitle }), children: senderName }), occurredAt !== undefined && _jsx("span", { className: css.messageTime, children: formatMessageTime(occurredAt) })] })), clampable ? _jsx("div", { className: clamped ? css.messageClamp : undefined, children: bodyNode }) : bodyNode, clampable && (_jsx("button", { type: "button", className: css.messageExpand, "data-message-expand": "true", "aria-expanded": expanded, onClick: () => { setExpanded(value => !value); }, children: expanded ? (t?.('collapseMessage') ?? 'Show less') : (t?.('expandMessage') ?? 'Show more') })), (plan.fallbackNames.length > 0 || plan.fallbackRefs.length > 0) && (_jsxs("div", { className: css.mentionsRow, children: [plan.fallbackNames.map(name => _jsxs("span", { className: css.mention, children: ["@", name] }, name)), plan.fallbackRefs.map(ref => {
144
+ return (_jsxs("article", { className: css.messageRow, "data-human": human || undefined, "data-grouped": grouped || undefined, children: [identityImage.src === undefined
145
+ ? _jsx("div", { className: css.messageIdentity, "data-avatar": "initial", style: avatarStyle, "aria-hidden": "true", children: senderName.replace('@', '').slice(0, 1).toUpperCase() })
146
+ : _jsx("img", { className: css.messageIdentityImage, "data-avatar": "image", src: identityImage.src, alt: "", "aria-hidden": "true", onError: identityImage.failed }), _jsxs("div", { className: css.messageBody, children: [(!grouped || showGroupedTime === true) && (_jsxs("div", { className: css.nameRow, children: [!grouped && _jsx("strong", { ...(senderTitle === undefined ? {} : { title: senderTitle }), children: senderName }), occurredAt !== undefined && _jsx("span", { className: css.messageTime, children: formatMessageTime(occurredAt) })] })), clampable ? _jsx("div", { className: clamped ? css.messageClamp : undefined, children: bodyNode }) : bodyNode, clampable && (_jsx("button", { type: "button", className: css.messageExpand, "data-message-expand": "true", "aria-expanded": expanded, onClick: () => { setExpanded(value => !value); }, children: expanded ? (t?.('collapseMessage') ?? 'Show less') : (t?.('expandMessage') ?? 'Show more') })), (plan.fallbackNames.length > 0 || plan.fallbackRefs.length > 0) && (_jsxs("div", { className: css.mentionsRow, children: [plan.fallbackNames.map(name => _jsxs("span", { className: css.mention, children: ["@", name] }, name)), plan.fallbackRefs.map(ref => {
103
147
  const resolved = cachedResolvedTaskRef(ref);
104
148
  const label = resolved !== undefined && ref.startsWith('task:') ? taskLabel(resolved.taskNumber) : ref;
105
149
  return _jsx("button", { type: "button", className: css.refLink, title: ref, onClick: () => { onOpenRef(ref); }, children: label }, ref);
@@ -146,32 +190,89 @@ function resolvedTaskRefButton(taskRef, label) {
146
190
  button.textContent = label;
147
191
  return button;
148
192
  }
149
- /** Replace a whole-ref code span with its resolved Task chip once known. */
150
- function renderResolvedMarkdownCodeRef(code, taskLabel, refLabel) {
193
+ /** One resolved Thread-ref chip built outside React, matching the styled ref link. */
194
+ function resolvedThreadRefButton(threadRef, label) {
195
+ const button = document.createElement('button');
196
+ button.type = 'button';
197
+ if (css.refLink !== undefined)
198
+ button.className = css.refLink;
199
+ button.dataset.threadRef = threadRef;
200
+ button.title = threadRef;
201
+ button.textContent = label;
202
+ return button;
203
+ }
204
+ /** One roster-resolved Channel chip built outside React, matching the styled ref link. */
205
+ function resolvedChannelRefButton(channelRef, label) {
206
+ const button = document.createElement('button');
207
+ button.type = 'button';
208
+ if (css.refLink !== undefined)
209
+ button.className = css.refLink;
210
+ button.dataset.ref = channelRef;
211
+ button.title = channelRef;
212
+ button.textContent = label;
213
+ return button;
214
+ }
215
+ /**
216
+ * One roster-resolved Member chip built outside React. Openable Members jump
217
+ * to their session through the delegated click listener; everyone else gets
218
+ * a labelled but inert span, never a link-shaped misfire.
219
+ */
220
+ function resolvedMemberRefChip(memberRef, label, sessionId) {
221
+ if (sessionId === undefined) {
222
+ const span = document.createElement('span');
223
+ span.title = memberRef;
224
+ span.textContent = label;
225
+ return span;
226
+ }
227
+ const button = document.createElement('button');
228
+ button.type = 'button';
229
+ if (css.refLink !== undefined)
230
+ button.className = css.refLink;
231
+ button.dataset.memberSession = sessionId;
232
+ button.title = memberRef;
233
+ button.textContent = label;
234
+ return button;
235
+ }
236
+ /** Replace a whole-ref code span with its resolved chip once known. */
237
+ function renderResolvedMarkdownCodeRef(code, taskLabel, threadChipLabel, channelChipLabel, memberChipLabel, channelNameOf, memberOf) {
151
238
  const segments = splitBrandedRefs((code.textContent ?? '').trim());
152
239
  const segment = segments.length === 1 ? segments[0] : undefined;
153
240
  const ref = segment?.ref;
154
241
  if (ref === undefined)
155
242
  return;
156
- const taskRef = ref.startsWith('task:') === true ? ref : undefined;
157
- const resolved = taskRef === undefined ? undefined : cachedResolvedTaskRef(taskRef);
158
- if (taskRef !== undefined && resolved === undefined)
243
+ // Task and Thread refs need Host resolution before becoming human-readable
244
+ // links; Channel and Member refs resolve against the loaded rosters, and
245
+ // anything the roster does not know stays untouched plain text.
246
+ if (ref.startsWith('task:')) {
247
+ const resolved = cachedResolvedTaskRef(ref);
248
+ if (resolved === undefined)
249
+ return;
250
+ code.replaceWith(resolvedTaskRefButton(ref, taskLabel(resolved.taskNumber)));
159
251
  return;
160
- if (taskRef !== undefined) {
161
- code.replaceWith(resolvedTaskRefButton(taskRef, taskLabel(resolved.taskNumber)));
252
+ }
253
+ if (ref.startsWith('thread:')) {
254
+ const resolved = cachedResolvedThreadRef(ref);
255
+ if (resolved === undefined)
256
+ return;
257
+ code.replaceWith(resolvedThreadRefButton(ref, threadChipLabel(resolved.title)));
162
258
  return;
163
259
  }
164
- const button = document.createElement('button');
165
- button.type = 'button';
166
- if (css.refLink !== undefined)
167
- button.className = css.refLink;
168
- button.dataset.ref = ref;
169
- button.title = ref;
170
- button.textContent = refLabel(ref);
171
- code.replaceWith(button);
260
+ if (ref.startsWith('channel:')) {
261
+ const name = channelNameOf?.(ref);
262
+ if (name === undefined)
263
+ return;
264
+ code.replaceWith(resolvedChannelRefButton(ref, channelChipLabel(name)));
265
+ return;
266
+ }
267
+ if (ref.startsWith('member:')) {
268
+ const resolved = memberOf?.(ref);
269
+ if (resolved === undefined)
270
+ return;
271
+ code.replaceWith(resolvedMemberRefChip(ref, memberChipLabel(resolved.handle), resolved.openable ? resolved.sessionId : undefined));
272
+ }
172
273
  }
173
- /** Replace resolved Task refs and structured mention handles in one prose text node without changing Markdown structure. */
174
- function renderResolvedMarkdownText(node, mentionNames, taskLabel, refLabel) {
274
+ /** Replace resolved Task/Thread/Channel/Member refs and structured mention handles in one prose text node without changing Markdown structure. */
275
+ function renderResolvedMarkdownText(node, mentionNames, taskLabel, threadChipLabel, channelChipLabel, memberChipLabel, channelNameOf, memberOf) {
175
276
  let changed = false;
176
277
  const fragment = document.createDocumentFragment();
177
278
  for (const refSegment of splitBrandedRefs(node.data)) {
@@ -190,48 +291,93 @@ function renderResolvedMarkdownText(node, mentionNames, taskLabel, refLabel) {
190
291
  }
191
292
  continue;
192
293
  }
193
- const taskRef = refSegment.ref.startsWith('task:') === true ? refSegment.ref : undefined;
194
- const resolved = taskRef === undefined ? undefined : cachedResolvedTaskRef(taskRef);
195
- // Task refs need Host resolution before becoming human-readable links;
196
- // channel/thread refs already have their canonical display text and can be
197
- // linked immediately at the authored position.
198
- if (taskRef !== undefined && resolved === undefined) {
199
- fragment.append(refSegment.text);
200
- continue;
294
+ // Task and Thread refs need Host resolution before becoming human-readable
295
+ // links; Channel and Member refs resolve against the loaded rosters.
296
+ // Unresolvable refs stay plain text so prose never misfires as a link.
297
+ if (refSegment.ref.startsWith('task:')) {
298
+ const resolved = cachedResolvedTaskRef(refSegment.ref);
299
+ if (resolved === undefined) {
300
+ fragment.append(refSegment.text);
301
+ continue;
302
+ }
303
+ changed = true;
304
+ fragment.append(resolvedTaskRefButton(refSegment.ref, taskLabel(resolved.taskNumber)));
305
+ }
306
+ else if (refSegment.ref.startsWith('thread:')) {
307
+ const resolved = cachedResolvedThreadRef(refSegment.ref);
308
+ if (resolved === undefined) {
309
+ fragment.append(refSegment.text);
310
+ continue;
311
+ }
312
+ changed = true;
313
+ fragment.append(resolvedThreadRefButton(refSegment.ref, threadChipLabel(resolved.title)));
201
314
  }
202
- changed = true;
203
- if (taskRef !== undefined) {
204
- fragment.append(resolvedTaskRefButton(taskRef, taskLabel(resolved.taskNumber)));
315
+ else if (refSegment.ref.startsWith('channel:')) {
316
+ const name = channelNameOf?.(refSegment.ref);
317
+ if (name === undefined) {
318
+ fragment.append(refSegment.text);
319
+ continue;
320
+ }
321
+ changed = true;
322
+ fragment.append(resolvedChannelRefButton(refSegment.ref, channelChipLabel(name)));
323
+ }
324
+ else if (refSegment.ref.startsWith('member:')) {
325
+ const resolved = memberOf?.(refSegment.ref);
326
+ if (resolved === undefined) {
327
+ fragment.append(refSegment.text);
328
+ continue;
329
+ }
330
+ changed = true;
331
+ fragment.append(resolvedMemberRefChip(refSegment.ref, memberChipLabel(resolved.handle), resolved.openable ? resolved.sessionId : undefined));
205
332
  }
206
333
  else {
207
- const button = document.createElement('button');
208
- button.type = 'button';
209
- if (css.refLink !== undefined)
210
- button.className = css.refLink;
211
- button.dataset.ref = refSegment.ref;
212
- button.title = refSegment.ref;
213
- button.textContent = refLabel(refSegment.ref);
214
- fragment.append(button);
334
+ fragment.append(refSegment.text);
215
335
  }
216
336
  }
217
337
  if (changed)
218
338
  node.replaceWith(fragment);
219
339
  }
220
340
  /** Render one literal text run, linkifying branded refs when navigation is available. */
221
- function renderRefs(text, onOpenRef, taskLabel, refLabel) {
341
+ function renderRefs(text, onOpenRef, onOpenMemberSession, taskLabel, threadChipLabel, channelChipLabel, memberChipLabel, channelNameOf, memberOf) {
222
342
  if (onOpenRef === undefined)
223
343
  return text;
224
344
  return splitBrandedRefs(text).map((segment, index) => {
225
345
  if (segment.ref === undefined)
226
346
  return _jsx(Fragment, { children: segment.text }, index);
227
- const resolved = cachedResolvedTaskRef(segment.ref);
228
- // Task refs link only once the Host confirms them; abbreviated or unknown
229
- // refs stay plain text so prose never misfires as a link. Channel and
230
- // Thread refs have no resolver and link at the authored position.
231
- if (segment.ref.startsWith('task:') && resolved === undefined)
232
- return _jsx(Fragment, { children: segment.text }, index);
233
- const label = resolved !== undefined && segment.ref.startsWith('task:') ? taskLabel(resolved.taskNumber) : refLabel(segment.ref);
234
- return _jsx("button", { type: "button", className: css.refLink, title: segment.ref, onClick: () => { onOpenRef(segment.ref); }, children: label }, index);
347
+ // Task and Thread refs link only once the Host confirms them; Channel and
348
+ // Member refs link once the loaded roster knows them. Anything unknown
349
+ // stays plain text so prose never misfires as a link.
350
+ if (segment.ref.startsWith('task:')) {
351
+ const resolved = cachedResolvedTaskRef(segment.ref);
352
+ if (resolved === undefined)
353
+ return _jsx(Fragment, { children: segment.text }, index);
354
+ return _jsx("button", { type: "button", className: css.refLink, title: segment.ref, onClick: () => { onOpenRef(segment.ref); }, children: taskLabel(resolved.taskNumber) }, index);
355
+ }
356
+ if (segment.ref.startsWith('thread:')) {
357
+ const resolved = cachedResolvedThreadRef(segment.ref);
358
+ if (resolved === undefined)
359
+ return _jsx(Fragment, { children: segment.text }, index);
360
+ return _jsx("button", { type: "button", className: css.refLink, title: segment.ref, onClick: () => { onOpenRef(segment.ref); }, children: threadChipLabel(resolved.title) }, index);
361
+ }
362
+ if (segment.ref.startsWith('channel:')) {
363
+ const name = channelNameOf?.(segment.ref);
364
+ if (name === undefined)
365
+ return _jsx(Fragment, { children: segment.text }, index);
366
+ return _jsx("button", { type: "button", className: css.refLink, title: segment.ref, onClick: () => { onOpenRef(segment.ref); }, children: channelChipLabel(name) }, index);
367
+ }
368
+ if (segment.ref.startsWith('member:')) {
369
+ const resolved = memberOf?.(segment.ref);
370
+ if (resolved === undefined)
371
+ return _jsx(Fragment, { children: segment.text }, index);
372
+ // Known but not openable (suspended Members, the Human): a labelled
373
+ // span, informative without promising a jump that cannot happen.
374
+ if (!resolved.openable || resolved.sessionId === undefined || onOpenMemberSession === undefined) {
375
+ return _jsx("span", { title: segment.ref, children: memberChipLabel(resolved.handle) }, index);
376
+ }
377
+ const sessionId = resolved.sessionId;
378
+ return _jsx("button", { type: "button", className: css.refLink, title: segment.ref, onClick: () => { onOpenMemberSession(sessionId); }, children: memberChipLabel(resolved.handle) }, index);
379
+ }
380
+ return _jsx(Fragment, { children: segment.text }, index);
235
381
  });
236
382
  }
237
383
  /** One message's attachment strip: image thumbnails with a large view, or name chips when bytes are gone. */
@@ -1 +1 @@
1
- {"version":3,"file":"TeamRowMenu.d.ts","sourceRoot":"","sources":["../../../src/client/TeamRowMenu.tsx"],"names":[],"mappings":"AACA,OAAO,EAAoC,KAAK,SAAS,EAAE,MAAM,uCAAuC,CAAA;AAGxG;;;;GAIG;AACH,wBAAgB,WAAW,CAAC,EAAE,KAAK,EAAE,KAAK,EAAE,QAAQ,EAAE,YAAY,EAAE,EAAE;IACpE,iEAAiE;IACjE,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAA;IACtB,qEAAqE;IACrE,QAAQ,CAAC,KAAK,EAAE,SAAS,SAAS,EAAE,CAAA;IACpC,QAAQ,CAAC,QAAQ,EAAE,CAAC,EAAE,EAAE,MAAM,KAAK,IAAI,CAAA;IACvC,sEAAsE;IACtE,QAAQ,CAAC,YAAY,CAAC,EAAE,CAAC,IAAI,EAAE,OAAO,KAAK,IAAI,CAAA;CAChD,+BAkCA"}
1
+ {"version":3,"file":"TeamRowMenu.d.ts","sourceRoot":"","sources":["../../../src/client/TeamRowMenu.tsx"],"names":[],"mappings":"AACA,OAAO,EAA+B,KAAK,SAAS,EAAE,MAAM,uCAAuC,CAAA;AAGnG;;;;GAIG;AACH,wBAAgB,WAAW,CAAC,EAAE,KAAK,EAAE,KAAK,EAAE,QAAQ,EAAE,YAAY,EAAE,EAAE;IACpE,iEAAiE;IACjE,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAA;IACtB,qEAAqE;IACrE,QAAQ,CAAC,KAAK,EAAE,SAAS,SAAS,EAAE,CAAA;IACpC,QAAQ,CAAC,QAAQ,EAAE,CAAC,EAAE,EAAE,MAAM,KAAK,IAAI,CAAA;IACvC,sEAAsE;IACtE,QAAQ,CAAC,YAAY,CAAC,EAAE,CAAC,IAAI,EAAE,OAAO,KAAK,IAAI,CAAA;CAChD,+BAkCA"}
@@ -1,6 +1,6 @@
1
1
  import { jsx as _jsx } from "react/jsx-runtime";
2
2
  import { useState } from 'react';
3
- import { IconEllipsisOutlineRegular, Menu } from '@deepseek-ai/dsh-client-ui-primitives';
3
+ import { IconEllipsisOutline16, Menu } from '@deepseek-ai/dsh-client-ui-primitives';
4
4
  import css from './sidebar.module.css';
5
5
  /**
6
6
  * Row-level overflow menu shared by sidebar Channel and Agent rows, mirroring
@@ -19,5 +19,5 @@ export function TeamRowMenu({ label, items, onSelect, onOpenChange }) {
19
19
  setOpen(false);
20
20
  onOpenChange?.(false);
21
21
  };
22
- return (_jsx(Menu, { open: open, onClose: close, items: items, onSelect: (id) => { close(); onSelect(id); }, portal: true, closeOnPointerLeave: true, anchor: (_jsx("button", { type: "button", className: css.rowMenuButton, "aria-label": label, "aria-haspopup": "menu", "aria-expanded": open, onClick: (event) => { event.stopPropagation(); toggle(); }, children: _jsx(IconEllipsisOutlineRegular, {}) })) }));
22
+ return (_jsx(Menu, { open: open, onClose: close, items: items, onSelect: (id) => { close(); onSelect(id); }, portal: true, closeOnPointerLeave: true, anchor: (_jsx("button", { type: "button", className: css.rowMenuButton, "aria-label": label, "aria-haspopup": "menu", "aria-expanded": open, onClick: (event) => { event.stopPropagation(); toggle(); }, children: _jsx(IconEllipsisOutline16, {}) })) }));
23
23
  }
@@ -1,7 +1,7 @@
1
1
  import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
- import { IconChevronDownOutlineRegular } from '@deepseek-ai/dsh-client-ui-primitives';
2
+ import { IconChevronDownOutline14 } from '@deepseek-ai/dsh-client-ui-primitives';
3
3
  import css from './sidebar.module.css';
4
4
  /** Collapsible sidebar section header: disclosure toggle plus trailing actions. */
5
5
  export function TeamSidebarSection({ title, actions, open, onToggle, children }) {
6
- return (_jsxs("section", { className: css.section, children: [_jsxs("div", { className: css.sectionHeader, children: [_jsxs("button", { type: "button", className: css.sectionToggle, "aria-expanded": open, onClick: () => { onToggle(!open); }, children: [_jsx(IconChevronDownOutlineRegular, { className: css.sectionChevron }), _jsx("span", { className: css.sectionTitle, children: title })] }), actions !== undefined && _jsx("span", { className: css.sectionActions, children: actions })] }), open && children] }));
6
+ return (_jsxs("section", { className: css.section, children: [_jsxs("div", { className: css.sectionHeader, children: [_jsxs("button", { type: "button", className: css.sectionToggle, "aria-expanded": open, onClick: () => { onToggle(!open); }, children: [_jsx(IconChevronDownOutline14, { className: css.sectionChevron }), _jsx("span", { className: css.sectionTitle, children: title })] }), actions !== undefined && _jsx("span", { className: css.sectionActions, children: actions })] }), open && children] }));
7
7
  }
@@ -4,6 +4,9 @@ import type { TeamConversationProps } from './slots.ts';
4
4
  import type { TeamDraftStore } from './drafts.ts';
5
5
  interface TeamThreadPageProps {
6
6
  readonly workspaceId: WorkspaceId;
7
+ /** The Human's own display name and avatar, from the shared identity projection. */
8
+ readonly humanName: string;
9
+ readonly humanAvatarUrl?: string | undefined;
7
10
  readonly channelRef?: AgentTeamChannelRef;
8
11
  readonly taskRef?: AgentTeamTaskRef;
9
12
  readonly threadRef: AgentTeamThreadRef;
@@ -24,6 +27,8 @@ interface TeamThreadPageProps {
24
27
  readonly selectChannel: TeamConversationProps['selectChannel'];
25
28
  readonly selectThread: TeamConversationProps['selectThread'];
26
29
  readonly resolveTaskRefs: TeamConversationProps['resolveTaskRefs'];
30
+ readonly resolveThreadRefs: TeamConversationProps['resolveThreadRefs'];
31
+ readonly openMemberSession: TeamConversationProps['openMemberSession'];
27
32
  readonly t: TeamConversationProps['t'];
28
33
  }
29
34
  export declare function TeamThreadPage(props: TeamThreadPageProps): import("react").JSX.Element;
@@ -1 +1 @@
1
- {"version":3,"file":"TeamThreadPage.d.ts","sourceRoot":"","sources":["../../../src/client/TeamThreadPage.tsx"],"names":[],"mappings":"AACA,OAAO,KAAK,EAEV,mBAAmB,EAInB,gBAAgB,EAGhB,kBAAkB,EAEnB,MAAM,gCAAgC,CAAA;AACvC,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,kDAAkD,CAAA;AAEnF,OAAO,KAAK,EAAE,qBAAqB,EAAE,MAAM,YAAY,CAAA;AACvD,OAAO,KAAK,EAAgB,cAAc,EAAE,MAAM,aAAa,CAAA;AAc/D,UAAU,mBAAmB;IAC3B,QAAQ,CAAC,WAAW,EAAE,WAAW,CAAA;IACjC,QAAQ,CAAC,UAAU,CAAC,EAAE,mBAAmB,CAAA;IACzC,QAAQ,CAAC,OAAO,CAAC,EAAE,gBAAgB,CAAA;IACnC,QAAQ,CAAC,SAAS,EAAE,kBAAkB,CAAA;IACtC,QAAQ,CAAC,UAAU,CAAC,EAAE,MAAM,CAAA;IAC5B,QAAQ,CAAC,eAAe,EAAE,qBAAqB,CAAC,iBAAiB,CAAC,CAAA;IAClE,QAAQ,CAAC,YAAY,EAAE,qBAAqB,CAAC,cAAc,CAAC,CAAA;IAC5D,QAAQ,CAAC,UAAU,EAAE,qBAAqB,CAAC,YAAY,CAAC,CAAA;IACxD,QAAQ,CAAC,iBAAiB,EAAE,qBAAqB,CAAC,mBAAmB,CAAC,CAAA;IACtE,QAAQ,CAAC,kBAAkB,EAAE,qBAAqB,CAAC,oBAAoB,CAAC,CAAA;IACxE,QAAQ,CAAC,gBAAgB,EAAE,qBAAqB,CAAC,kBAAkB,CAAC,CAAA;IACpE,QAAQ,CAAC,WAAW,EAAE,qBAAqB,CAAC,aAAa,CAAC,CAAA;IAC1D,QAAQ,CAAC,MAAM,EAAE,cAAc,CAAA;IAC/B,QAAQ,CAAC,aAAa,EAAE,qBAAqB,CAAC,eAAe,CAAC,CAAA;IAC9D,QAAQ,CAAC,KAAK,EAAE,qBAAqB,CAAC,OAAO,CAAC,CAAA;IAC9C,QAAQ,CAAC,UAAU,EAAE,qBAAqB,CAAC,YAAY,CAAC,CAAA;IACxD,QAAQ,CAAC,aAAa,EAAE,qBAAqB,CAAC,eAAe,CAAC,CAAA;IAC9D,QAAQ,CAAC,aAAa,EAAE,qBAAqB,CAAC,eAAe,CAAC,CAAA;IAC9D,QAAQ,CAAC,aAAa,EAAE,qBAAqB,CAAC,eAAe,CAAC,CAAA;IAC9D,QAAQ,CAAC,YAAY,EAAE,qBAAqB,CAAC,cAAc,CAAC,CAAA;IAC5D,QAAQ,CAAC,eAAe,EAAE,qBAAqB,CAAC,iBAAiB,CAAC,CAAA;IAClE,QAAQ,CAAC,CAAC,EAAE,qBAAqB,CAAC,GAAG,CAAC,CAAA;CACvC;AA+CD,wBAAgB,cAAc,CAAC,KAAK,EAAE,mBAAmB,+BA2uBxD"}
1
+ {"version":3,"file":"TeamThreadPage.d.ts","sourceRoot":"","sources":["../../../src/client/TeamThreadPage.tsx"],"names":[],"mappings":"AACA,OAAO,KAAK,EAEV,mBAAmB,EAInB,gBAAgB,EAGhB,kBAAkB,EAEnB,MAAM,gCAAgC,CAAA;AACvC,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,kDAAkD,CAAA;AAEnF,OAAO,KAAK,EAAE,qBAAqB,EAAE,MAAM,YAAY,CAAA;AACvD,OAAO,KAAK,EAAgB,cAAc,EAAE,MAAM,aAAa,CAAA;AAgB/D,UAAU,mBAAmB;IAC3B,QAAQ,CAAC,WAAW,EAAE,WAAW,CAAA;IACjC,oFAAoF;IACpF,QAAQ,CAAC,SAAS,EAAE,MAAM,CAAA;IAC1B,QAAQ,CAAC,cAAc,CAAC,EAAE,MAAM,GAAG,SAAS,CAAA;IAC5C,QAAQ,CAAC,UAAU,CAAC,EAAE,mBAAmB,CAAA;IACzC,QAAQ,CAAC,OAAO,CAAC,EAAE,gBAAgB,CAAA;IACnC,QAAQ,CAAC,SAAS,EAAE,kBAAkB,CAAA;IACtC,QAAQ,CAAC,UAAU,CAAC,EAAE,MAAM,CAAA;IAC5B,QAAQ,CAAC,eAAe,EAAE,qBAAqB,CAAC,iBAAiB,CAAC,CAAA;IAClE,QAAQ,CAAC,YAAY,EAAE,qBAAqB,CAAC,cAAc,CAAC,CAAA;IAC5D,QAAQ,CAAC,UAAU,EAAE,qBAAqB,CAAC,YAAY,CAAC,CAAA;IACxD,QAAQ,CAAC,iBAAiB,EAAE,qBAAqB,CAAC,mBAAmB,CAAC,CAAA;IACtE,QAAQ,CAAC,kBAAkB,EAAE,qBAAqB,CAAC,oBAAoB,CAAC,CAAA;IACxE,QAAQ,CAAC,gBAAgB,EAAE,qBAAqB,CAAC,kBAAkB,CAAC,CAAA;IACpE,QAAQ,CAAC,WAAW,EAAE,qBAAqB,CAAC,aAAa,CAAC,CAAA;IAC1D,QAAQ,CAAC,MAAM,EAAE,cAAc,CAAA;IAC/B,QAAQ,CAAC,aAAa,EAAE,qBAAqB,CAAC,eAAe,CAAC,CAAA;IAC9D,QAAQ,CAAC,KAAK,EAAE,qBAAqB,CAAC,OAAO,CAAC,CAAA;IAC9C,QAAQ,CAAC,UAAU,EAAE,qBAAqB,CAAC,YAAY,CAAC,CAAA;IACxD,QAAQ,CAAC,aAAa,EAAE,qBAAqB,CAAC,eAAe,CAAC,CAAA;IAC9D,QAAQ,CAAC,aAAa,EAAE,qBAAqB,CAAC,eAAe,CAAC,CAAA;IAC9D,QAAQ,CAAC,aAAa,EAAE,qBAAqB,CAAC,eAAe,CAAC,CAAA;IAC9D,QAAQ,CAAC,YAAY,EAAE,qBAAqB,CAAC,cAAc,CAAC,CAAA;IAC5D,QAAQ,CAAC,eAAe,EAAE,qBAAqB,CAAC,iBAAiB,CAAC,CAAA;IAClE,QAAQ,CAAC,iBAAiB,EAAE,qBAAqB,CAAC,mBAAmB,CAAC,CAAA;IACtE,QAAQ,CAAC,iBAAiB,EAAE,qBAAqB,CAAC,mBAAmB,CAAC,CAAA;IACtE,QAAQ,CAAC,CAAC,EAAE,qBAAqB,CAAC,GAAG,CAAC,CAAA;CACvC;AA+CD,wBAAgB,cAAc,CAAC,KAAK,EAAE,mBAAmB,+BA6wBxD"}