@codingame/monaco-vscode-extensions-service-override 1.83.16 → 1.85.0-next.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 (71) hide show
  1. package/extensions.js +2 -2
  2. package/localExtensionHost.d.ts +1 -0
  3. package/package.json +4 -4
  4. package/vscode/src/vs/workbench/api/browser/mainThreadAuthentication.js +4 -2
  5. package/vscode/src/vs/workbench/api/browser/mainThreadChat.js +9 -88
  6. package/vscode/src/vs/workbench/api/browser/mainThreadChatAgents2.js +216 -0
  7. package/vscode/src/vs/workbench/api/browser/mainThreadChatProvider.js +3 -0
  8. package/vscode/src/vs/workbench/api/browser/mainThreadChatVariables.js +7 -6
  9. package/vscode/src/vs/workbench/api/browser/mainThreadCommands.js +8 -4
  10. package/vscode/src/vs/workbench/api/browser/mainThreadComments.js +4 -4
  11. package/vscode/src/vs/workbench/api/browser/mainThreadDocuments.js +6 -2
  12. package/vscode/src/vs/workbench/api/browser/mainThreadEditorTabs.js +16 -9
  13. package/vscode/src/vs/workbench/api/browser/mainThreadFileSystem.js +3 -75
  14. package/vscode/src/vs/workbench/api/browser/mainThreadFileSystemEventService.js +102 -11
  15. package/vscode/src/vs/workbench/api/browser/mainThreadInlineChat.js +6 -2
  16. package/vscode/src/vs/workbench/api/browser/mainThreadIssueReporter.js +16 -0
  17. package/vscode/src/vs/workbench/api/browser/mainThreadLanguageFeatures.js +25 -0
  18. package/vscode/src/vs/workbench/api/browser/mainThreadNotebook.js +36 -0
  19. package/vscode/src/vs/workbench/api/browser/mainThreadNotebookKernels.js +34 -1
  20. package/vscode/src/vs/workbench/api/browser/mainThreadQuickDiff.js +4 -11
  21. package/vscode/src/vs/workbench/api/browser/mainThreadSCM.js +136 -28
  22. package/vscode/src/vs/workbench/api/browser/mainThreadSearch.js +2 -4
  23. package/vscode/src/vs/workbench/api/browser/mainThreadSpeech.js +67 -0
  24. package/vscode/src/vs/workbench/api/browser/mainThreadTerminalService.js +8 -10
  25. package/vscode/src/vs/workbench/api/browser/mainThreadTesting.js +25 -10
  26. package/vscode/src/vs/workbench/api/browser/mainThreadTreeViews.js +8 -13
  27. package/vscode/src/vs/workbench/api/browser/mainThreadTunnelService.js +1 -1
  28. package/vscode/src/vs/workbench/api/browser/mainThreadWorkspace.js +3 -0
  29. package/vscode/src/vs/workbench/contrib/chat/browser/actions/chatExecuteActions.js +40 -0
  30. package/vscode/src/vs/workbench/contrib/chat/browser/chatEditorInput.js +141 -0
  31. package/vscode/src/vs/workbench/contrib/chat/browser/chatFollowups.js +37 -0
  32. package/vscode/src/vs/workbench/contrib/chat/browser/chatInputPart.js +342 -0
  33. package/vscode/src/vs/workbench/contrib/chat/browser/chatListRenderer.js +1197 -0
  34. package/vscode/src/vs/workbench/contrib/chat/browser/chatMarkdownDecorationsRenderer.js +117 -0
  35. package/vscode/src/vs/workbench/contrib/chat/browser/chatOptions.js +83 -0
  36. package/vscode/src/vs/workbench/contrib/chat/browser/chatWidget.js +543 -0
  37. package/vscode/src/vs/workbench/contrib/chat/browser/codeBlockPart.css.js +6 -0
  38. package/vscode/src/vs/workbench/contrib/chat/browser/codeBlockPart.js +292 -0
  39. package/vscode/src/vs/workbench/contrib/chat/browser/contrib/chatDynamicVariables.js +169 -0
  40. package/vscode/src/vs/workbench/contrib/chat/browser/media/chat.css.js +6 -0
  41. package/vscode/src/vs/workbench/contrib/chat/common/chatModel.js +111 -73
  42. package/vscode/src/vs/workbench/contrib/chat/common/chatRequestParser.js +195 -0
  43. package/vscode/src/vs/workbench/contrib/chat/common/chatViewModel.js +260 -0
  44. package/vscode/src/vs/workbench/contrib/chat/common/chatWidgetHistoryService.js +5 -0
  45. package/vscode/src/vs/workbench/contrib/chat/common/chatWordCounter.js +26 -0
  46. package/vscode/src/vs/workbench/contrib/comments/browser/commentColors.js +6 -0
  47. package/vscode/src/vs/workbench/contrib/comments/browser/commentNode.js +6 -5
  48. package/vscode/src/vs/workbench/contrib/comments/browser/commentReply.js +8 -3
  49. package/vscode/src/vs/workbench/contrib/comments/browser/commentThreadBody.js +6 -4
  50. package/vscode/src/vs/workbench/contrib/comments/browser/commentThreadHeader.js +1 -1
  51. package/vscode/src/vs/workbench/contrib/comments/browser/commentThreadWidget.js +6 -2
  52. package/vscode/src/vs/workbench/contrib/comments/browser/commentThreadZoneWidget.js +24 -10
  53. package/vscode/src/vs/workbench/contrib/comments/browser/commentsController.js +113 -34
  54. package/vscode/src/vs/workbench/contrib/comments/browser/commentsTreeViewer.js +17 -8
  55. package/vscode/src/vs/workbench/contrib/comments/browser/commentsView.js +5 -3
  56. package/vscode/src/vs/workbench/contrib/comments/browser/media/panel.css.js +1 -1
  57. package/vscode/src/vs/workbench/contrib/comments/browser/media/review.css.js +1 -1
  58. package/vscode/src/vs/workbench/contrib/comments/common/commentModel.js +18 -8
  59. package/vscode/src/vs/workbench/contrib/interactive/browser/interactiveEditorInput.js +2 -1
  60. package/vscode/src/vs/workbench/contrib/mergeEditor/browser/model/diffComputer.js +7 -0
  61. package/vscode/src/vs/workbench/contrib/tasks/common/tasks.js +5 -5
  62. package/vscode/src/vs/workbench/services/extensions/browser/extensionService.js +2 -1
  63. package/vscode/src/vs/workbench/services/extensions/browser/webWorkerExtensionHost.js +7 -4
  64. package/vscode/src/vs/workbench/services/extensions/common/abstractExtensionService.js +17 -12
  65. package/vscode/src/vs/workbench/services/extensions/common/extensionHostManager.js +17 -148
  66. package/vscode/src/vs/workbench/services/extensions/common/lazyCreateExtensionHostManager.js +161 -0
  67. package/vscode/src/vs/workbench/services/extensions/common/remoteExtensionHost.js +2 -0
  68. package/vscode/src/vs/platform/files/common/watcher.js +0 -71
  69. package/vscode/src/vs/workbench/api/browser/mainThreadChatAgents.js +0 -52
  70. package/vscode/src/vs/workbench/api/browser/mainThreadChatSlashCommands.js +0 -49
  71. package/vscode/src/vs/workbench/contrib/testing/common/testCoverage.js +0 -25
@@ -0,0 +1,1197 @@
1
+ import { __decorate, __param } from '../../../../../../../external/tslib/tslib.es6.js';
2
+ import * as dom from 'monaco-editor/esm/vs/base/browser/dom.js';
3
+ import { Button } from 'monaco-editor/esm/vs/base/browser/ui/button/button.js';
4
+ import { renderIcon } from 'monaco-editor/esm/vs/base/browser/ui/iconLabel/iconLabels.js';
5
+ import { distinct } from 'monaco-editor/esm/vs/base/common/arrays.js';
6
+ import { disposableTimeout } from 'monaco-editor/esm/vs/base/common/async.js';
7
+ import { Codicon } from 'monaco-editor/esm/vs/base/common/codicons.js';
8
+ import { Emitter } from 'monaco-editor/esm/vs/base/common/event.js';
9
+ import { MarkdownString } from 'monaco-editor/esm/vs/base/common/htmlContent.js';
10
+ import { Disposable, DisposableStore, toDisposable } from 'monaco-editor/esm/vs/base/common/lifecycle.js';
11
+ import { ResourceMap } from 'monaco-editor/esm/vs/base/common/map.js';
12
+ import { marked } from 'monaco-editor/esm/vs/base/common/marked/marked.js';
13
+ import { FileAccess } from 'monaco-editor/esm/vs/base/common/network.js';
14
+ import { clamp } from 'monaco-editor/esm/vs/base/common/numbers.js';
15
+ import { ThemeIcon } from 'monaco-editor/esm/vs/base/common/themables.js';
16
+ import { URI } from 'monaco-editor/esm/vs/base/common/uri.js';
17
+ import { MarkdownRenderer } from 'monaco-editor/esm/vs/editor/contrib/markdownRenderer/browser/markdownRenderer.js';
18
+ import { localizeWithPath } from 'monaco-editor/esm/vs/nls.js';
19
+ import { MenuEntryActionViewItem } from 'monaco-editor/esm/vs/platform/actions/browser/menuEntryActionViewItem.js';
20
+ import { MenuWorkbenchToolBar } from 'monaco-editor/esm/vs/platform/actions/browser/toolbar.js';
21
+ import { MenuId, MenuItemAction } from 'monaco-editor/esm/vs/platform/actions/common/actions.js';
22
+ import { ICommandService } from 'monaco-editor/esm/vs/platform/commands/common/commands.js';
23
+ import { IConfigurationService } from 'monaco-editor/esm/vs/platform/configuration/common/configuration.js';
24
+ import { IContextKeyService } from 'monaco-editor/esm/vs/platform/contextkey/common/contextkey.js';
25
+ import { FileKind } from 'monaco-editor/esm/vs/platform/files/common/files.js';
26
+ import { IInstantiationService } from 'monaco-editor/esm/vs/platform/instantiation/common/instantiation.js';
27
+ import { ServiceCollection } from 'monaco-editor/esm/vs/platform/instantiation/common/serviceCollection.js';
28
+ import { WorkbenchCompressibleAsyncDataTree, WorkbenchList } from 'monaco-editor/esm/vs/platform/list/browser/listService.js';
29
+ import { ILogService } from 'monaco-editor/esm/vs/platform/log/common/log.js';
30
+ import { IOpenerService } from 'monaco-editor/esm/vs/platform/opener/common/opener.js';
31
+ import { IProductService } from 'monaco-editor/esm/vs/platform/product/common/productService.js';
32
+ import { defaultButtonStyles } from 'monaco-editor/esm/vs/platform/theme/browser/defaultStyles.js';
33
+ import { ColorScheme } from 'monaco-editor/esm/vs/platform/theme/common/theme.js';
34
+ import { IThemeService } from 'monaco-editor/esm/vs/platform/theme/common/themeService.js';
35
+ import { ResourceLabels } from 'vscode/vscode/vs/workbench/browser/labels';
36
+ import { IAccessibleViewService } from 'vscode/vscode/vs/workbench/contrib/accessibility/browser/accessibleView';
37
+ import { ChatFollowups } from './chatFollowups.js';
38
+ import { annotateSpecialMarkdownContent, convertParsedRequestToMarkdown, extractVulnerabilitiesFromText, walkTreeAndAnnotateReferenceLinks } from './chatMarkdownDecorationsRenderer.js';
39
+ import { CodeBlockPart } from './codeBlockPart.js';
40
+ import { CONTEXT_RESPONSE, CONTEXT_REQUEST, CONTEXT_CHAT_RESPONSE_SUPPORT_ISSUE_REPORTING, CONTEXT_RESPONSE_VOTE, CONTEXT_RESPONSE_FILTERED } from 'vscode/vscode/vs/workbench/contrib/chat/common/chatContextKeys';
41
+ import { chatAgentLeader, chatSubcommandLeader } from 'vscode/vscode/vs/workbench/contrib/chat/common/chatParserTypes';
42
+ import { InteractiveSessionVoteDirection, IChatService } from 'vscode/vscode/vs/workbench/contrib/chat/common/chatService';
43
+ import { isRequestVM, isResponseVM, isWelcomeVM } from '../common/chatViewModel.js';
44
+ import { getNWords } from '../common/chatWordCounter.js';
45
+ import { createFileIconThemableTreeContainerScope } from 'vscode/vscode/vs/workbench/contrib/files/browser/views/explorerView';
46
+ import { IEditorService } from 'vscode/vscode/vs/workbench/services/editor/common/editorService';
47
+
48
+ var ChatListItemRenderer_1;
49
+ const $ = dom.$;
50
+ let ChatListItemRenderer = class ChatListItemRenderer extends Disposable {
51
+ static { ChatListItemRenderer_1 = this; }
52
+ static { this.ID = 'item'; }
53
+ constructor(editorOptions, rendererOptions, delegate, instantiationService, configService, logService, commandService, openerService, contextKeyService, chatService, editorService, productService, themeService) {
54
+ super();
55
+ this.editorOptions = editorOptions;
56
+ this.rendererOptions = rendererOptions;
57
+ this.delegate = delegate;
58
+ this.instantiationService = instantiationService;
59
+ this.logService = logService;
60
+ this.commandService = commandService;
61
+ this.openerService = openerService;
62
+ this.contextKeyService = contextKeyService;
63
+ this.chatService = chatService;
64
+ this.editorService = editorService;
65
+ this.themeService = themeService;
66
+ this.codeBlocksByResponseId = ( new Map());
67
+ this.codeBlocksByEditorUri = ( new ResourceMap());
68
+ this.fileTreesByResponseId = ( new Map());
69
+ this.focusedFileTreesByResponseId = ( new Map());
70
+ this._onDidClickFollowup = this._register(( new Emitter()));
71
+ this.onDidClickFollowup = this._onDidClickFollowup.event;
72
+ this._onDidChangeItemHeight = this._register(( new Emitter()));
73
+ this.onDidChangeItemHeight = this._onDidChangeItemHeight.event;
74
+ this._currentLayoutWidth = 0;
75
+ this._isVisible = true;
76
+ this._onDidChangeVisibility = this._register(( new Emitter()));
77
+ this._usedReferencesEnabled = false;
78
+ this.renderer = this.instantiationService.createInstance(MarkdownRenderer, {});
79
+ this._editorPool = this._register(this.instantiationService.createInstance(EditorPool, this.editorOptions));
80
+ this._treePool = this._register(this.instantiationService.createInstance(TreePool, this._onDidChangeVisibility.event));
81
+ this._contentReferencesListPool = this._register(this.instantiationService.createInstance(ContentReferencesListPool, this._onDidChangeVisibility.event));
82
+ this._usedReferencesEnabled = configService.getValue('chat.experimental.usedReferences') ?? true;
83
+ this._register(configService.onDidChangeConfiguration(e => {
84
+ if (e.affectsConfiguration('chat.experimental.usedReferences')) {
85
+ this._usedReferencesEnabled = configService.getValue('chat.experimental.usedReferences') ?? true;
86
+ }
87
+ }));
88
+ }
89
+ get templateId() {
90
+ return ChatListItemRenderer_1.ID;
91
+ }
92
+ traceLayout(method, message) {
93
+ {
94
+ this.logService.trace(`ChatListItemRenderer#${method}: ${message}`);
95
+ }
96
+ }
97
+ getProgressiveRenderRate(element) {
98
+ if (element.isComplete) {
99
+ return 80;
100
+ }
101
+ if (element.contentUpdateTimings && element.contentUpdateTimings.impliedWordLoadRate) {
102
+ const minRate = 12;
103
+ const maxRate = 80;
104
+ const rateBoost = 1.5;
105
+ const rate = element.contentUpdateTimings.impliedWordLoadRate * rateBoost;
106
+ return clamp(rate, minRate, maxRate);
107
+ }
108
+ return 8;
109
+ }
110
+ getCodeBlockInfosForResponse(response) {
111
+ const codeBlocks = this.codeBlocksByResponseId.get(response.id);
112
+ return codeBlocks ?? [];
113
+ }
114
+ getCodeBlockInfoForEditor(uri) {
115
+ return this.codeBlocksByEditorUri.get(uri);
116
+ }
117
+ getFileTreeInfosForResponse(response) {
118
+ const fileTrees = this.fileTreesByResponseId.get(response.id);
119
+ return fileTrees ?? [];
120
+ }
121
+ getLastFocusedFileTreeForResponse(response) {
122
+ const fileTrees = this.fileTreesByResponseId.get(response.id);
123
+ const lastFocusedFileTreeIndex = this.focusedFileTreesByResponseId.get(response.id);
124
+ if (fileTrees?.length && lastFocusedFileTreeIndex !== undefined && lastFocusedFileTreeIndex < fileTrees.length) {
125
+ return fileTrees[lastFocusedFileTreeIndex];
126
+ }
127
+ return undefined;
128
+ }
129
+ setVisible(visible) {
130
+ this._isVisible = visible;
131
+ this._onDidChangeVisibility.fire(visible);
132
+ }
133
+ layout(width) {
134
+ this._currentLayoutWidth = width - (this.rendererOptions.noPadding ? 0 : 40);
135
+ this._editorPool.inUse.forEach(editor => {
136
+ editor.layout(this._currentLayoutWidth);
137
+ });
138
+ }
139
+ renderTemplate(container) {
140
+ const templateDisposables = ( new DisposableStore());
141
+ const rowContainer = dom.append(container, $('.interactive-item-container'));
142
+ if (this.rendererOptions.renderStyle === 'compact') {
143
+ rowContainer.classList.add('interactive-item-compact');
144
+ }
145
+ if (this.rendererOptions.noPadding) {
146
+ rowContainer.classList.add('no-padding');
147
+ }
148
+ const header = dom.append(rowContainer, $('.header'));
149
+ const user = dom.append(header, $('.user'));
150
+ const avatarContainer = dom.append(user, $('.avatar-container'));
151
+ const agentAvatarContainer = dom.append(user, $('.agent-avatar-container'));
152
+ const username = dom.append(user, $('h3.username'));
153
+ const detailContainer = dom.append(user, $('span.detail-container'));
154
+ const detail = dom.append(detailContainer, $('span.detail'));
155
+ dom.append(detailContainer, $('span.chat-animated-ellipsis'));
156
+ const progressSteps = dom.append(rowContainer, $('.progress-steps'));
157
+ const referencesListContainer = dom.append(rowContainer, $('.referencesListContainer'));
158
+ const value = dom.append(rowContainer, $('.value'));
159
+ const elementDisposables = ( new DisposableStore());
160
+ const contextKeyService = templateDisposables.add(this.contextKeyService.createScoped(rowContainer));
161
+ const scopedInstantiationService = this.instantiationService.createChild(( new ServiceCollection([IContextKeyService, contextKeyService])));
162
+ let titleToolbar;
163
+ if (this.rendererOptions.noHeader) {
164
+ header.classList.add('hidden');
165
+ }
166
+ else {
167
+ titleToolbar = templateDisposables.add(scopedInstantiationService.createInstance(MenuWorkbenchToolBar, header, MenuId.ChatMessageTitle, {
168
+ menuOptions: {
169
+ shouldForwardArgs: true
170
+ },
171
+ actionViewItemProvider: (action, options) => {
172
+ if (action instanceof MenuItemAction && (action.item.id === 'workbench.action.chat.voteDown' || action.item.id === 'workbench.action.chat.voteUp')) {
173
+ return scopedInstantiationService.createInstance(ChatVoteButton, action, options);
174
+ }
175
+ return undefined;
176
+ }
177
+ }));
178
+ }
179
+ const template = { avatarContainer, agentAvatarContainer, username, detail, progressSteps, referencesListContainer, value, rowContainer, elementDisposables, titleToolbar, templateDisposables, contextKeyService };
180
+ return template;
181
+ }
182
+ renderElement(node, index, templateData) {
183
+ this.renderChatTreeItem(node.element, index, templateData);
184
+ }
185
+ renderChatTreeItem(element, index, templateData) {
186
+ const kind = isRequestVM(element) ? 'request' :
187
+ isResponseVM(element) ? 'response' :
188
+ 'welcome';
189
+ this.traceLayout('renderElement', `${kind}, index=${index}`);
190
+ CONTEXT_RESPONSE.bindTo(templateData.contextKeyService).set(isResponseVM(element));
191
+ CONTEXT_REQUEST.bindTo(templateData.contextKeyService).set(isRequestVM(element));
192
+ if (isResponseVM(element)) {
193
+ CONTEXT_CHAT_RESPONSE_SUPPORT_ISSUE_REPORTING.bindTo(templateData.contextKeyService).set(!!element.agent?.metadata.supportIssueReporting);
194
+ CONTEXT_RESPONSE_VOTE.bindTo(templateData.contextKeyService).set(element.vote === InteractiveSessionVoteDirection.Up ? 'up' : element.vote === InteractiveSessionVoteDirection.Down ? 'down' : '');
195
+ }
196
+ else {
197
+ CONTEXT_RESPONSE_VOTE.bindTo(templateData.contextKeyService).set('');
198
+ }
199
+ if (templateData.titleToolbar) {
200
+ templateData.titleToolbar.context = element;
201
+ }
202
+ const isFiltered = !!(isResponseVM(element) && element.errorDetails?.responseIsFiltered);
203
+ CONTEXT_RESPONSE_FILTERED.bindTo(templateData.contextKeyService).set(isFiltered);
204
+ templateData.rowContainer.classList.toggle('interactive-request', isRequestVM(element));
205
+ templateData.rowContainer.classList.toggle('interactive-response', isResponseVM(element));
206
+ templateData.rowContainer.classList.toggle('interactive-welcome', isWelcomeVM(element));
207
+ templateData.rowContainer.classList.toggle('filtered-response', isFiltered);
208
+ templateData.rowContainer.classList.toggle('show-detail-progress', isResponseVM(element) && !element.isComplete && !element.progressMessages.length);
209
+ templateData.username.textContent = element.username;
210
+ if (!this.rendererOptions.noHeader) {
211
+ this.renderAvatar(element, templateData);
212
+ }
213
+ dom.clearNode(templateData.detail);
214
+ dom.clearNode(templateData.progressSteps);
215
+ if (isResponseVM(element)) {
216
+ this.renderDetail(element, templateData);
217
+ this.renderProgressSteps(element, templateData);
218
+ }
219
+ if (isResponseVM(element) && index === this.delegate.getListLength() - 1 && (!element.isComplete || element.renderData) && element.response.value.length) {
220
+ this.traceLayout('renderElement', `start progressive render ${kind}, index=${index}`);
221
+ const progressiveRenderingDisposables = templateData.elementDisposables.add(( new DisposableStore()));
222
+ const timer = templateData.elementDisposables.add(new dom.WindowIntervalTimer());
223
+ const runProgressiveRender = (initial) => {
224
+ try {
225
+ if (this.doNextProgressiveRender(element, index, templateData, !!initial, progressiveRenderingDisposables)) {
226
+ timer.cancel();
227
+ }
228
+ }
229
+ catch (err) {
230
+ timer.cancel();
231
+ throw err;
232
+ }
233
+ };
234
+ timer.cancelAndSet(runProgressiveRender, 50, dom.getWindow(templateData.rowContainer));
235
+ runProgressiveRender(true);
236
+ }
237
+ else if (isResponseVM(element)) {
238
+ const renderableResponse = annotateSpecialMarkdownContent(element.response.value);
239
+ this.basicRenderElement(renderableResponse, element, index, templateData);
240
+ }
241
+ else if (isRequestVM(element)) {
242
+ const markdown = 'kind' in element.message ?
243
+ element.message.message :
244
+ convertParsedRequestToMarkdown(element.message);
245
+ this.basicRenderElement([{ content: ( new MarkdownString(markdown)), kind: 'markdownContent' }], element, index, templateData);
246
+ }
247
+ else {
248
+ this.renderWelcomeMessage(element, templateData);
249
+ }
250
+ }
251
+ renderDetail(element, templateData) {
252
+ let progressMsg = '';
253
+ if (element.agent && !element.agent.metadata.isDefault) {
254
+ let usingMsg = chatAgentLeader + element.agent.id;
255
+ if (element.slashCommand) {
256
+ usingMsg += ` ${chatSubcommandLeader}${element.slashCommand.name}`;
257
+ }
258
+ if (element.isComplete) {
259
+ progressMsg = ( localizeWithPath(
260
+ 'vs/workbench/contrib/chat/browser/chatListRenderer',
261
+ 'usedAgent',
262
+ "used {0}",
263
+ usingMsg
264
+ ));
265
+ }
266
+ else {
267
+ progressMsg = ( localizeWithPath(
268
+ 'vs/workbench/contrib/chat/browser/chatListRenderer',
269
+ 'usingAgent',
270
+ "using {0}",
271
+ usingMsg
272
+ ));
273
+ }
274
+ }
275
+ else if (!element.isComplete) {
276
+ progressMsg = ( localizeWithPath(
277
+ 'vs/workbench/contrib/chat/browser/chatListRenderer',
278
+ 'thinking',
279
+ "Thinking"
280
+ ));
281
+ }
282
+ templateData.detail.textContent = progressMsg;
283
+ if (element.agent) {
284
+ templateData.detail.title = progressMsg + (element.slashCommand?.description ? `\n${element.slashCommand.description}` : '');
285
+ }
286
+ else {
287
+ templateData.detail.title = '';
288
+ }
289
+ }
290
+ renderProgressSteps(element, templateData) {
291
+ if (element.response.value.length || element.isComplete) {
292
+ return;
293
+ }
294
+ element.progressMessages.forEach((msg, index) => {
295
+ const last = index === element.progressMessages.length - 1;
296
+ const icon = last ? ThemeIcon.modify(Codicon.sync, 'spin') : Codicon.check;
297
+ const step = dom.$('.progress-step', undefined, renderIcon(icon), dom.$('span.progress-step-message', undefined, msg.content));
298
+ templateData.progressSteps.appendChild(step);
299
+ });
300
+ }
301
+ renderAvatar(element, templateData) {
302
+ if (element.avatarIconUri) {
303
+ const avatarImgIcon = dom.$('img.icon');
304
+ avatarImgIcon.src = ( FileAccess.uriToBrowserUri(element.avatarIconUri).toString(true));
305
+ templateData.avatarContainer.replaceChildren(dom.$('.avatar', undefined, avatarImgIcon));
306
+ }
307
+ else {
308
+ const defaultIcon = isRequestVM(element) ? Codicon.account : Codicon.copilot;
309
+ const avatarIcon = dom.$(ThemeIcon.asCSSSelector(defaultIcon));
310
+ templateData.avatarContainer.replaceChildren(dom.$('.avatar.codicon-avatar', undefined, avatarIcon));
311
+ }
312
+ if (isResponseVM(element) && element.agent && !element.agent.metadata.isDefault) {
313
+ dom.show(templateData.agentAvatarContainer);
314
+ const icon = this.getAgentIcon(element.agent.metadata);
315
+ if (icon instanceof URI) {
316
+ const avatarIcon = dom.$('img.icon');
317
+ avatarIcon.src = ( FileAccess.uriToBrowserUri(icon).toString(true));
318
+ templateData.agentAvatarContainer.replaceChildren(dom.$('.avatar', undefined, avatarIcon));
319
+ }
320
+ else if (icon) {
321
+ const avatarIcon = dom.$(ThemeIcon.asCSSSelector(icon));
322
+ templateData.agentAvatarContainer.replaceChildren(dom.$('.avatar.codicon-avatar', undefined, avatarIcon));
323
+ }
324
+ else {
325
+ dom.hide(templateData.agentAvatarContainer);
326
+ return;
327
+ }
328
+ templateData.agentAvatarContainer.classList.toggle('complete', element.isComplete);
329
+ if (!element.agentAvatarHasBeenRendered && !element.isComplete) {
330
+ element.agentAvatarHasBeenRendered = true;
331
+ templateData.agentAvatarContainer.classList.remove('loading');
332
+ templateData.elementDisposables.add(disposableTimeout(() => {
333
+ templateData.agentAvatarContainer.classList.toggle('loading', !element.isComplete);
334
+ }, 100));
335
+ }
336
+ else {
337
+ templateData.agentAvatarContainer.classList.toggle('loading', !element.isComplete);
338
+ }
339
+ }
340
+ else {
341
+ dom.hide(templateData.agentAvatarContainer);
342
+ }
343
+ }
344
+ getAgentIcon(agent) {
345
+ if (agent.themeIcon) {
346
+ return agent.themeIcon;
347
+ }
348
+ else {
349
+ return this.themeService.getColorTheme().type === ColorScheme.DARK && agent.iconDark ? agent.iconDark :
350
+ agent.icon;
351
+ }
352
+ }
353
+ basicRenderElement(value, element, index, templateData) {
354
+ const fillInIncompleteTokens = isResponseVM(element) && (!element.isComplete || element.isCanceled || element.errorDetails?.responseIsFiltered || element.errorDetails?.responseIsIncomplete);
355
+ dom.clearNode(templateData.value);
356
+ dom.clearNode(templateData.referencesListContainer);
357
+ if (isResponseVM(element)) {
358
+ this.renderDetail(element, templateData);
359
+ }
360
+ this.renderContentReferencesIfNeeded(element, templateData, templateData.elementDisposables);
361
+ let fileTreeIndex = 0;
362
+ for (const data of value) {
363
+ const result = data.kind === 'treeData'
364
+ ? this.renderTreeData(data.treeData, element, templateData, fileTreeIndex++)
365
+ : data.kind === 'markdownContent'
366
+ ? this.renderMarkdown(data.content, element, templateData, fillInIncompleteTokens)
367
+ : this.renderPlaceholder(( new MarkdownString(data.content)), templateData);
368
+ templateData.value.appendChild(result.element);
369
+ templateData.elementDisposables.add(result);
370
+ }
371
+ if (isResponseVM(element) && element.errorDetails?.message) {
372
+ const icon = element.errorDetails.responseIsFiltered ? Codicon.info : Codicon.error;
373
+ const errorDetails = dom.append(templateData.value, $('.interactive-response-error-details', undefined, renderIcon(icon)));
374
+ const renderedError = templateData.elementDisposables.add(this.renderer.render(( new MarkdownString(element.errorDetails.message))));
375
+ errorDetails.appendChild($('span', undefined, renderedError.element));
376
+ }
377
+ if (isResponseVM(element) && element.commandFollowups?.length) {
378
+ const followupsContainer = dom.append(templateData.value, $('.interactive-response-followups'));
379
+ templateData.elementDisposables.add(( new ChatFollowups(
380
+ followupsContainer,
381
+ element.commandFollowups,
382
+ defaultButtonStyles,
383
+ followup => {
384
+ this.chatService.notifyUserAction({
385
+ providerId: element.providerId,
386
+ agentId: element.agent?.id,
387
+ sessionId: element.sessionId,
388
+ requestId: element.requestId,
389
+ action: {
390
+ kind: 'command',
391
+ command: followup,
392
+ }
393
+ });
394
+ return this.commandService.executeCommand(followup.commandId, ...(followup.args ?? []));
395
+ },
396
+ templateData.contextKeyService
397
+ )));
398
+ }
399
+ const newHeight = templateData.rowContainer.offsetHeight;
400
+ const fireEvent = !element.currentRenderedHeight || element.currentRenderedHeight !== newHeight;
401
+ element.currentRenderedHeight = newHeight;
402
+ if (fireEvent) {
403
+ const disposable = templateData.elementDisposables.add(dom.scheduleAtNextAnimationFrame(dom.getWindow(templateData.value), () => {
404
+ disposable.dispose();
405
+ this._onDidChangeItemHeight.fire({ element, height: newHeight });
406
+ }));
407
+ }
408
+ }
409
+ renderWelcomeMessage(element, templateData) {
410
+ dom.clearNode(templateData.value);
411
+ dom.clearNode(templateData.referencesListContainer);
412
+ for (const item of element.content) {
413
+ if (Array.isArray(item)) {
414
+ templateData.elementDisposables.add(( new ChatFollowups(
415
+ templateData.value,
416
+ item,
417
+ undefined,
418
+ followup => this._onDidClickFollowup.fire(followup),
419
+ templateData.contextKeyService
420
+ )));
421
+ }
422
+ else {
423
+ const result = this.renderMarkdown(item, element, templateData);
424
+ templateData.value.appendChild(result.element);
425
+ templateData.elementDisposables.add(result);
426
+ }
427
+ }
428
+ const newHeight = templateData.rowContainer.offsetHeight;
429
+ const fireEvent = !element.currentRenderedHeight || element.currentRenderedHeight !== newHeight;
430
+ element.currentRenderedHeight = newHeight;
431
+ if (fireEvent) {
432
+ const disposable = templateData.elementDisposables.add(dom.scheduleAtNextAnimationFrame(dom.getWindow(templateData.value), () => {
433
+ disposable.dispose();
434
+ this._onDidChangeItemHeight.fire({ element, height: newHeight });
435
+ }));
436
+ }
437
+ }
438
+ doNextProgressiveRender(element, index, templateData, isInRenderElement, disposables) {
439
+ if (!this._isVisible) {
440
+ return true;
441
+ }
442
+ disposables.clear();
443
+ const annotatedResult = annotateSpecialMarkdownContent(element.response.value);
444
+ const renderableResponse = annotatedResult;
445
+ let isFullyRendered = false;
446
+ if (element.isCanceled) {
447
+ this.traceLayout('runProgressiveRender', `canceled, index=${index}`);
448
+ element.renderData = undefined;
449
+ this.basicRenderElement(renderableResponse, element, index, templateData);
450
+ isFullyRendered = true;
451
+ }
452
+ else {
453
+ element.renderData ??= { renderedParts: [] };
454
+ const renderedParts = element.renderData.renderedParts;
455
+ const wordCountResults = [];
456
+ const partsToRender = [];
457
+ let somePartIsNotFullyRendered = false;
458
+ renderableResponse.forEach((part, index) => {
459
+ const renderedPart = renderedParts[index];
460
+ if (!renderedPart) {
461
+ if (part.kind === 'treeData') {
462
+ partsToRender[index] = part.treeData;
463
+ }
464
+ else {
465
+ const wordCountResult = this.getDataForProgressiveRender(element, contentToMarkdown(part.content), { renderedWordCount: 0, lastRenderTime: 0 });
466
+ if (wordCountResult !== undefined) {
467
+ this.traceLayout('doNextProgressiveRender', `Rendering new part ${index}, wordCountResult=${wordCountResult.actualWordCount}, rate=${wordCountResult.rate}`);
468
+ partsToRender[index] = {
469
+ renderedWordCount: wordCountResult.actualWordCount,
470
+ lastRenderTime: Date.now(),
471
+ isFullyRendered: wordCountResult.isFullString,
472
+ };
473
+ wordCountResults[index] = wordCountResult;
474
+ }
475
+ }
476
+ }
477
+ else if (part.kind === 'treeData' && !isInteractiveProgressTreeData(renderedPart)) {
478
+ partsToRender[index] = part.treeData;
479
+ }
480
+ else if (part.kind !== 'treeData' && !isInteractiveProgressTreeData(renderedPart)) {
481
+ const wordCountResult = this.getDataForProgressiveRender(element, contentToMarkdown(part.content), renderedPart);
482
+ if (wordCountResult !== undefined && renderedPart.renderedWordCount !== wordCountResult?.actualWordCount) {
483
+ this.traceLayout('doNextProgressiveRender', `Rendering changed part ${index}, wordCountResult=${wordCountResult.actualWordCount}, rate=${wordCountResult.rate}`);
484
+ partsToRender[index] = {
485
+ renderedWordCount: wordCountResult.actualWordCount,
486
+ lastRenderTime: Date.now(),
487
+ isFullyRendered: wordCountResult.isFullString,
488
+ };
489
+ wordCountResults[index] = wordCountResult;
490
+ }
491
+ else if (!renderedPart.isFullyRendered && !wordCountResult) {
492
+ somePartIsNotFullyRendered = true;
493
+ }
494
+ }
495
+ });
496
+ isFullyRendered = partsToRender.length === 0 && !somePartIsNotFullyRendered;
497
+ if (isFullyRendered && element.isComplete) {
498
+ this.traceLayout('runProgressiveRender', `end progressive render, index=${index} and clearing renderData, response is complete, index=${index}`);
499
+ element.renderData = undefined;
500
+ disposables.clear();
501
+ this.basicRenderElement(renderableResponse, element, index, templateData);
502
+ }
503
+ else if (!isFullyRendered) {
504
+ this.renderContentReferencesIfNeeded(element, templateData, disposables);
505
+ let hasRenderedOneMarkdownBlock = false;
506
+ partsToRender.forEach((partToRender, index) => {
507
+ if (!partToRender) {
508
+ return;
509
+ }
510
+ let result;
511
+ if (isInteractiveProgressTreeData(partToRender)) {
512
+ result = this.renderTreeData(partToRender, element, templateData, index);
513
+ }
514
+ else if (!hasRenderedOneMarkdownBlock) {
515
+ const { value } = wordCountResults[index];
516
+ result = renderableResponse[index].kind === 'asyncContent'
517
+ ? this.renderPlaceholder(( new MarkdownString(value)), templateData)
518
+ : this.renderMarkdown(( new MarkdownString(value)), element, templateData, true);
519
+ hasRenderedOneMarkdownBlock = true;
520
+ }
521
+ if (!result) {
522
+ return;
523
+ }
524
+ renderedParts[index] = partToRender;
525
+ const existingElement = templateData.value.children[index];
526
+ if (existingElement) {
527
+ templateData.value.replaceChild(result.element, existingElement);
528
+ }
529
+ else {
530
+ templateData.value.appendChild(result.element);
531
+ }
532
+ disposables.add(result);
533
+ });
534
+ }
535
+ else {
536
+ return false;
537
+ }
538
+ }
539
+ const height = templateData.rowContainer.offsetHeight;
540
+ element.currentRenderedHeight = height;
541
+ if (!isInRenderElement) {
542
+ this._onDidChangeItemHeight.fire({ element, height: templateData.rowContainer.offsetHeight });
543
+ }
544
+ return isFullyRendered;
545
+ }
546
+ renderTreeData(data, element, templateData, treeDataIndex) {
547
+ const treeDisposables = ( new DisposableStore());
548
+ const ref = treeDisposables.add(this._treePool.get());
549
+ const tree = ref.object;
550
+ treeDisposables.add(tree.onDidOpen((e) => {
551
+ if (e.element && !('children' in e.element)) {
552
+ this.openerService.open(e.element.uri);
553
+ }
554
+ }));
555
+ treeDisposables.add(tree.onDidChangeCollapseState(() => {
556
+ this._onDidChangeItemHeight.fire({ element, height: templateData.rowContainer.offsetHeight });
557
+ }));
558
+ treeDisposables.add(tree.onContextMenu((e) => {
559
+ e.browserEvent.preventDefault();
560
+ e.browserEvent.stopPropagation();
561
+ }));
562
+ tree.setInput(data).then(() => {
563
+ if (!ref.isStale()) {
564
+ tree.layout();
565
+ this._onDidChangeItemHeight.fire({ element, height: templateData.rowContainer.offsetHeight });
566
+ }
567
+ });
568
+ if (isResponseVM(element)) {
569
+ const fileTreeFocusInfo = {
570
+ treeDataId: ( data.uri.toString()),
571
+ treeIndex: treeDataIndex,
572
+ focus() {
573
+ tree.domFocus();
574
+ }
575
+ };
576
+ treeDisposables.add(tree.onDidFocus(() => {
577
+ this.focusedFileTreesByResponseId.set(element.id, fileTreeFocusInfo.treeIndex);
578
+ }));
579
+ const fileTrees = this.fileTreesByResponseId.get(element.id) ?? [];
580
+ fileTrees.push(fileTreeFocusInfo);
581
+ this.fileTreesByResponseId.set(element.id, distinct(fileTrees, (v) => v.treeDataId));
582
+ treeDisposables.add(toDisposable(() => this.fileTreesByResponseId.set(element.id, fileTrees.filter(v => v.treeDataId !== ( data.uri.toString())))));
583
+ }
584
+ return {
585
+ element: tree.getHTMLElement().parentElement,
586
+ dispose: () => {
587
+ treeDisposables.dispose();
588
+ }
589
+ };
590
+ }
591
+ renderContentReferencesIfNeeded(element, templateData, disposables) {
592
+ dom.clearNode(templateData.referencesListContainer);
593
+ if (isResponseVM(element) && this._usedReferencesEnabled && element.contentReferences.length) {
594
+ dom.show(templateData.referencesListContainer);
595
+ const contentReferencesListResult = this.renderContentReferencesListData(element.contentReferences, element, templateData);
596
+ templateData.referencesListContainer.appendChild(contentReferencesListResult.element);
597
+ disposables.add(contentReferencesListResult);
598
+ }
599
+ else {
600
+ dom.hide(templateData.referencesListContainer);
601
+ }
602
+ }
603
+ renderContentReferencesListData(data, element, templateData) {
604
+ const listDisposables = ( new DisposableStore());
605
+ const referencesLabel = data.length > 1 ?
606
+ ( localizeWithPath(
607
+ 'vs/workbench/contrib/chat/browser/chatListRenderer',
608
+ 'usedReferencesPlural',
609
+ "Used {0} references",
610
+ data.length
611
+ )) :
612
+ ( localizeWithPath(
613
+ 'vs/workbench/contrib/chat/browser/chatListRenderer',
614
+ 'usedReferencesSingular',
615
+ "Used {0} reference",
616
+ 1
617
+ ));
618
+ const iconElement = $('.chat-used-context-icon');
619
+ const icon = (element) => element.usedReferencesExpanded ? Codicon.chevronDown : Codicon.chevronRight;
620
+ iconElement.classList.add(...ThemeIcon.asClassNameArray(icon(element)));
621
+ const buttonElement = $('.chat-used-context-label', undefined);
622
+ const collapseButton = ( new Button(buttonElement, {
623
+ buttonBackground: undefined,
624
+ buttonBorder: undefined,
625
+ buttonForeground: undefined,
626
+ buttonHoverBackground: undefined,
627
+ buttonSecondaryBackground: undefined,
628
+ buttonSecondaryForeground: undefined,
629
+ buttonSecondaryHoverBackground: undefined,
630
+ buttonSeparator: undefined
631
+ }));
632
+ const container = $('.chat-used-context', undefined, buttonElement);
633
+ collapseButton.label = referencesLabel;
634
+ collapseButton.element.append(iconElement);
635
+ this.updateAriaLabel(collapseButton.element, referencesLabel, element.usedReferencesExpanded);
636
+ container.classList.toggle('chat-used-context-collapsed', !element.usedReferencesExpanded);
637
+ listDisposables.add(collapseButton.onDidClick(() => {
638
+ iconElement.classList.remove(...ThemeIcon.asClassNameArray(icon(element)));
639
+ element.usedReferencesExpanded = !element.usedReferencesExpanded;
640
+ iconElement.classList.add(...ThemeIcon.asClassNameArray(icon(element)));
641
+ container.classList.toggle('chat-used-context-collapsed', !element.usedReferencesExpanded);
642
+ this._onDidChangeItemHeight.fire({ element, height: templateData.rowContainer.offsetHeight });
643
+ this.updateAriaLabel(collapseButton.element, referencesLabel, element.usedReferencesExpanded);
644
+ }));
645
+ const ref = listDisposables.add(this._contentReferencesListPool.get());
646
+ const list = ref.object;
647
+ container.appendChild(list.getHTMLElement().parentElement);
648
+ listDisposables.add(list.onDidOpen((e) => {
649
+ if (e.element) {
650
+ this.editorService.openEditor({
651
+ resource: 'uri' in e.element.reference ? e.element.reference.uri : e.element.reference,
652
+ options: {
653
+ ...e.editorOptions,
654
+ ...{
655
+ selection: 'range' in e.element.reference ? e.element.reference.range : undefined
656
+ }
657
+ }
658
+ });
659
+ }
660
+ }));
661
+ listDisposables.add(list.onContextMenu((e) => {
662
+ e.browserEvent.preventDefault();
663
+ e.browserEvent.stopPropagation();
664
+ }));
665
+ const maxItemsShown = 6;
666
+ const itemsShown = Math.min(data.length, maxItemsShown);
667
+ const height = itemsShown * 22;
668
+ list.layout(height);
669
+ list.getHTMLElement().style.height = `${height}px`;
670
+ list.splice(0, list.length, data);
671
+ return {
672
+ element: container,
673
+ dispose: () => {
674
+ listDisposables.dispose();
675
+ }
676
+ };
677
+ }
678
+ updateAriaLabel(element, label, expanded) {
679
+ element.ariaLabel = expanded ? ( localizeWithPath(
680
+ 'vs/workbench/contrib/chat/browser/chatListRenderer',
681
+ 'usedReferencesExpanded',
682
+ "{0}, expanded",
683
+ label
684
+ )) : ( localizeWithPath(
685
+ 'vs/workbench/contrib/chat/browser/chatListRenderer',
686
+ 'usedReferencesCollapsed',
687
+ "{0}, collapsed",
688
+ label
689
+ ));
690
+ }
691
+ renderPlaceholder(markdown, templateData) {
692
+ const codicon = $('.interactive-response-codicon-details', undefined, renderIcon({ id: 'sync~spin' }));
693
+ codicon.classList.add('interactive-response-placeholder-codicon');
694
+ const result = dom.append(templateData.value, codicon);
695
+ const content = this.renderer.render(markdown);
696
+ content.element.className = 'interactive-response-placeholder-content';
697
+ result.appendChild(content.element);
698
+ return { element: result, dispose: () => content.dispose() };
699
+ }
700
+ renderMarkdown(markdown, element, templateData, fillInIncompleteTokens = false) {
701
+ const disposables = ( new DisposableStore());
702
+ let codeBlockIndex = 0;
703
+ markdown = ( new MarkdownString(markdown.value, {
704
+ isTrusted: {
705
+ enabledCommands: typeof markdown.isTrusted === 'object' ? markdown.isTrusted?.enabledCommands : [] ?? []
706
+ }
707
+ }));
708
+ const orderedDisposablesList = [];
709
+ const codeblocks = [];
710
+ const result = this.renderer.render(markdown, {
711
+ fillInIncompleteTokens,
712
+ codeBlockRendererSync: (languageId, text) => {
713
+ const vulns = extractVulnerabilitiesFromText(text);
714
+ const hideToolbar = isResponseVM(element) && element.errorDetails?.responseIsFiltered;
715
+ const data = { languageId, text: vulns.newText, codeBlockIndex: codeBlockIndex++, element, hideToolbar, parentContextKeyService: templateData.contextKeyService, vulns: vulns.vulnerabilities };
716
+ const ref = this.renderCodeBlock(data, disposables);
717
+ disposables.add(ref.object.onDidChangeContentHeight(() => {
718
+ ref.object.layout(this._currentLayoutWidth);
719
+ this._onDidChangeItemHeight.fire({ element, height: templateData.rowContainer.offsetHeight });
720
+ }));
721
+ if (isResponseVM(element)) {
722
+ const info = {
723
+ codeBlockIndex: data.codeBlockIndex,
724
+ element,
725
+ focus() {
726
+ ref.object.focus();
727
+ }
728
+ };
729
+ codeblocks.push(info);
730
+ this.codeBlocksByEditorUri.set(ref.object.textModel.uri, info);
731
+ disposables.add(toDisposable(() => this.codeBlocksByEditorUri.delete(ref.object.textModel.uri)));
732
+ }
733
+ orderedDisposablesList.push(ref);
734
+ return ref.object.element;
735
+ },
736
+ asyncRenderCallback: () => this._onDidChangeItemHeight.fire({ element, height: templateData.rowContainer.offsetHeight }),
737
+ });
738
+ if (isResponseVM(element)) {
739
+ this.codeBlocksByResponseId.set(element.id, codeblocks);
740
+ disposables.add(toDisposable(() => this.codeBlocksByResponseId.delete(element.id)));
741
+ }
742
+ walkTreeAndAnnotateReferenceLinks(result.element);
743
+ orderedDisposablesList.reverse().forEach(d => disposables.add(d));
744
+ return {
745
+ element: result.element,
746
+ dispose() {
747
+ result.dispose();
748
+ disposables.dispose();
749
+ }
750
+ };
751
+ }
752
+ renderCodeBlock(data, disposables) {
753
+ const ref = this._editorPool.get();
754
+ const editorInfo = ref.object;
755
+ editorInfo.render(data, this._currentLayoutWidth);
756
+ return ref;
757
+ }
758
+ getDataForProgressiveRender(element, data, renderData) {
759
+ const rate = this.getProgressiveRenderRate(element);
760
+ const numWordsToRender = renderData.lastRenderTime === 0 ?
761
+ 1 :
762
+ renderData.renderedWordCount +
763
+ Math.floor((Date.now() - renderData.lastRenderTime) / 1000 * rate);
764
+ if (numWordsToRender === renderData.renderedWordCount) {
765
+ return undefined;
766
+ }
767
+ return {
768
+ ...getNWords(data.value, numWordsToRender),
769
+ rate
770
+ };
771
+ }
772
+ disposeElement(node, index, templateData) {
773
+ templateData.elementDisposables.clear();
774
+ }
775
+ disposeTemplate(templateData) {
776
+ templateData.templateDisposables.dispose();
777
+ }
778
+ };
779
+ ChatListItemRenderer = ChatListItemRenderer_1 = ( __decorate([
780
+ ( __param(3, IInstantiationService)),
781
+ ( __param(4, IConfigurationService)),
782
+ ( __param(5, ILogService)),
783
+ ( __param(6, ICommandService)),
784
+ ( __param(7, IOpenerService)),
785
+ ( __param(8, IContextKeyService)),
786
+ ( __param(9, IChatService)),
787
+ ( __param(10, IEditorService)),
788
+ ( __param(11, IProductService)),
789
+ ( __param(12, IThemeService))
790
+ ], ChatListItemRenderer));
791
+ let ChatListDelegate = class ChatListDelegate {
792
+ constructor(logService) {
793
+ this.logService = logService;
794
+ }
795
+ _traceLayout(method, message) {
796
+ {
797
+ this.logService.trace(`ChatListDelegate#${method}: ${message}`);
798
+ }
799
+ }
800
+ getHeight(element) {
801
+ const kind = isRequestVM(element) ? 'request' : 'response';
802
+ const height = ('currentRenderedHeight' in element ? element.currentRenderedHeight : undefined) ?? 200;
803
+ this._traceLayout('getHeight', `${kind}, height=${height}`);
804
+ return height;
805
+ }
806
+ getTemplateId(element) {
807
+ return ChatListItemRenderer.ID;
808
+ }
809
+ hasDynamicHeight(element) {
810
+ return true;
811
+ }
812
+ };
813
+ ChatListDelegate = ( __decorate([
814
+ ( __param(0, ILogService))
815
+ ], ChatListDelegate));
816
+ let ChatAccessibilityProvider = class ChatAccessibilityProvider {
817
+ constructor(_accessibleViewService) {
818
+ this._accessibleViewService = _accessibleViewService;
819
+ }
820
+ getWidgetRole() {
821
+ return 'list';
822
+ }
823
+ getRole(element) {
824
+ return 'listitem';
825
+ }
826
+ getWidgetAriaLabel() {
827
+ return ( localizeWithPath('vs/workbench/contrib/chat/browser/chatListRenderer', 'chat', "Chat"));
828
+ }
829
+ getAriaLabel(element) {
830
+ if (isRequestVM(element)) {
831
+ return element.messageText;
832
+ }
833
+ if (isResponseVM(element)) {
834
+ return this._getLabelWithCodeBlockCount(element);
835
+ }
836
+ if (isWelcomeVM(element)) {
837
+ return ( element.content.map(c => 'value' in c ? c.value : ( c.map(followup => followup.message)).join('\n'))).join('\n');
838
+ }
839
+ return '';
840
+ }
841
+ _getLabelWithCodeBlockCount(element) {
842
+ const accessibleViewHint = this._accessibleViewService.getOpenAriaHint("accessibility.verbosity.panelChat" );
843
+ let label = '';
844
+ let commandFollowUpInfo;
845
+ const commandFollowupLength = element.commandFollowups?.length ?? 0;
846
+ switch (commandFollowupLength) {
847
+ case 0:
848
+ break;
849
+ case 1:
850
+ commandFollowUpInfo = ( localizeWithPath(
851
+ 'vs/workbench/contrib/chat/browser/chatListRenderer',
852
+ 'commandFollowUpInfo',
853
+ "Command: {0}",
854
+ element.commandFollowups[0].title
855
+ ));
856
+ break;
857
+ default:
858
+ commandFollowUpInfo = ( localizeWithPath(
859
+ 'vs/workbench/contrib/chat/browser/chatListRenderer',
860
+ 'commandFollowUpInfoMany',
861
+ "Commands: {0}",
862
+ ( element.commandFollowups.map(followup => followup.title)).join(', ')
863
+ ));
864
+ }
865
+ const fileTreeCount = element.response.value.filter((v) => !('value' in v))?.length ?? 0;
866
+ let fileTreeCountHint = '';
867
+ switch (fileTreeCount) {
868
+ case 0:
869
+ break;
870
+ case 1:
871
+ fileTreeCountHint = ( localizeWithPath(
872
+ 'vs/workbench/contrib/chat/browser/chatListRenderer',
873
+ 'singleFileTreeHint',
874
+ "1 file tree"
875
+ ));
876
+ break;
877
+ default:
878
+ fileTreeCountHint = ( localizeWithPath(
879
+ 'vs/workbench/contrib/chat/browser/chatListRenderer',
880
+ 'multiFileTreeHint',
881
+ "{0} file trees",
882
+ fileTreeCount
883
+ ));
884
+ break;
885
+ }
886
+ const codeBlockCount = marked.lexer(element.response.asString()).filter(token => token.type === 'code')?.length ?? 0;
887
+ switch (codeBlockCount) {
888
+ case 0:
889
+ label = accessibleViewHint ? ( localizeWithPath(
890
+ 'vs/workbench/contrib/chat/browser/chatListRenderer',
891
+ 'noCodeBlocksHint',
892
+ "{0} {1} {2}",
893
+ fileTreeCountHint,
894
+ element.response.asString(),
895
+ accessibleViewHint
896
+ )) : ( localizeWithPath(
897
+ 'vs/workbench/contrib/chat/browser/chatListRenderer',
898
+ 'noCodeBlocks',
899
+ "{0} {1}",
900
+ fileTreeCountHint,
901
+ element.response.asString()
902
+ ));
903
+ break;
904
+ case 1:
905
+ label = accessibleViewHint ? ( localizeWithPath(
906
+ 'vs/workbench/contrib/chat/browser/chatListRenderer',
907
+ 'singleCodeBlockHint',
908
+ "{0} 1 code block: {1} {2}",
909
+ fileTreeCountHint,
910
+ element.response.asString(),
911
+ accessibleViewHint
912
+ )) : ( localizeWithPath(
913
+ 'vs/workbench/contrib/chat/browser/chatListRenderer',
914
+ 'singleCodeBlock',
915
+ "{0} 1 code block: {1}",
916
+ fileTreeCountHint,
917
+ element.response.asString()
918
+ ));
919
+ break;
920
+ default:
921
+ label = accessibleViewHint ? ( localizeWithPath(
922
+ 'vs/workbench/contrib/chat/browser/chatListRenderer',
923
+ 'multiCodeBlockHint',
924
+ "{0} {1} code blocks: {2}",
925
+ fileTreeCountHint,
926
+ codeBlockCount,
927
+ element.response.asString(),
928
+ accessibleViewHint
929
+ )) : ( localizeWithPath(
930
+ 'vs/workbench/contrib/chat/browser/chatListRenderer',
931
+ 'multiCodeBlock',
932
+ "{0} {1} code blocks",
933
+ fileTreeCountHint,
934
+ codeBlockCount,
935
+ element.response.asString()
936
+ ));
937
+ break;
938
+ }
939
+ return commandFollowUpInfo ? commandFollowUpInfo + ', ' + label : label;
940
+ }
941
+ };
942
+ ChatAccessibilityProvider = ( __decorate([
943
+ ( __param(0, IAccessibleViewService))
944
+ ], ChatAccessibilityProvider));
945
+ let EditorPool = class EditorPool extends Disposable {
946
+ get inUse() {
947
+ return this._pool.inUse;
948
+ }
949
+ constructor(options, instantiationService) {
950
+ super();
951
+ this.options = options;
952
+ this.instantiationService = instantiationService;
953
+ this._pool = this._register(( new ResourcePool(() => this.editorFactory())));
954
+ }
955
+ editorFactory() {
956
+ return this.instantiationService.createInstance(CodeBlockPart, this.options, MenuId.ChatCodeBlock);
957
+ }
958
+ get() {
959
+ const object = this._pool.get();
960
+ let stale = false;
961
+ return {
962
+ object,
963
+ isStale: () => stale,
964
+ dispose: () => {
965
+ stale = true;
966
+ this._pool.release(object);
967
+ }
968
+ };
969
+ }
970
+ };
971
+ EditorPool = ( __decorate([
972
+ ( __param(1, IInstantiationService))
973
+ ], EditorPool));
974
+ let TreePool = class TreePool extends Disposable {
975
+ get inUse() {
976
+ return this._pool.inUse;
977
+ }
978
+ constructor(_onDidChangeVisibility, instantiationService, configService, themeService) {
979
+ super();
980
+ this._onDidChangeVisibility = _onDidChangeVisibility;
981
+ this.instantiationService = instantiationService;
982
+ this.configService = configService;
983
+ this.themeService = themeService;
984
+ this._pool = this._register(( new ResourcePool(() => this.treeFactory())));
985
+ }
986
+ treeFactory() {
987
+ const resourceLabels = this.instantiationService.createInstance(ResourceLabels, { onDidChangeVisibility: this._onDidChangeVisibility });
988
+ const container = $('.interactive-response-progress-tree');
989
+ createFileIconThemableTreeContainerScope(container, this.themeService);
990
+ const tree = this.instantiationService.createInstance(WorkbenchCompressibleAsyncDataTree, 'ChatListRenderer', container, ( new ChatListTreeDelegate()), ( new ChatListTreeCompressionDelegate()), [( new ChatListTreeRenderer(resourceLabels, this.configService.getValue('explorer.decorations')))], ( new ChatListTreeDataSource()), {
991
+ collapseByDefault: () => false,
992
+ expandOnlyOnTwistieClick: () => false,
993
+ identityProvider: {
994
+ getId: (e) => ( e.uri.toString())
995
+ },
996
+ accessibilityProvider: {
997
+ getAriaLabel: (element) => element.label,
998
+ getWidgetAriaLabel: () => ( localizeWithPath(
999
+ 'vs/workbench/contrib/chat/browser/chatListRenderer',
1000
+ 'treeAriaLabel',
1001
+ "File Tree"
1002
+ ))
1003
+ },
1004
+ alwaysConsumeMouseWheel: false
1005
+ });
1006
+ return tree;
1007
+ }
1008
+ get() {
1009
+ const object = this._pool.get();
1010
+ let stale = false;
1011
+ return {
1012
+ object,
1013
+ isStale: () => stale,
1014
+ dispose: () => {
1015
+ stale = true;
1016
+ this._pool.release(object);
1017
+ }
1018
+ };
1019
+ }
1020
+ };
1021
+ TreePool = ( __decorate([
1022
+ ( __param(1, IInstantiationService)),
1023
+ ( __param(2, IConfigurationService)),
1024
+ ( __param(3, IThemeService))
1025
+ ], TreePool));
1026
+ let ContentReferencesListPool = class ContentReferencesListPool extends Disposable {
1027
+ get inUse() {
1028
+ return this._pool.inUse;
1029
+ }
1030
+ constructor(_onDidChangeVisibility, instantiationService, themeService) {
1031
+ super();
1032
+ this._onDidChangeVisibility = _onDidChangeVisibility;
1033
+ this.instantiationService = instantiationService;
1034
+ this.themeService = themeService;
1035
+ this._pool = this._register(( new ResourcePool(() => this.listFactory())));
1036
+ }
1037
+ listFactory() {
1038
+ const resourceLabels = this.instantiationService.createInstance(ResourceLabels, { onDidChangeVisibility: this._onDidChangeVisibility });
1039
+ const container = $('.chat-used-context-list');
1040
+ createFileIconThemableTreeContainerScope(container, this.themeService);
1041
+ const list = this.instantiationService.createInstance(WorkbenchList, 'ChatListRenderer', container, ( new ContentReferencesListDelegate()), [( new ContentReferencesListRenderer(resourceLabels))], {
1042
+ alwaysConsumeMouseWheel: false,
1043
+ });
1044
+ return list;
1045
+ }
1046
+ get() {
1047
+ const object = this._pool.get();
1048
+ let stale = false;
1049
+ return {
1050
+ object,
1051
+ isStale: () => stale,
1052
+ dispose: () => {
1053
+ stale = true;
1054
+ this._pool.release(object);
1055
+ }
1056
+ };
1057
+ }
1058
+ };
1059
+ ContentReferencesListPool = ( __decorate([
1060
+ ( __param(1, IInstantiationService)),
1061
+ ( __param(2, IThemeService))
1062
+ ], ContentReferencesListPool));
1063
+ class ContentReferencesListDelegate {
1064
+ getHeight(element) {
1065
+ return 22;
1066
+ }
1067
+ getTemplateId(element) {
1068
+ return ContentReferencesListRenderer.TEMPLATE_ID;
1069
+ }
1070
+ }
1071
+ class ContentReferencesListRenderer {
1072
+ static { this.TEMPLATE_ID = 'contentReferencesListRenderer'; }
1073
+ constructor(labels) {
1074
+ this.labels = labels;
1075
+ this.templateId = ContentReferencesListRenderer.TEMPLATE_ID;
1076
+ }
1077
+ renderTemplate(container) {
1078
+ const templateDisposables = ( new DisposableStore());
1079
+ const label = templateDisposables.add(this.labels.create(container, { supportHighlights: true }));
1080
+ return { templateDisposables, label };
1081
+ }
1082
+ renderElement(element, index, templateData, height) {
1083
+ templateData.label.element.style.display = 'flex';
1084
+ templateData.label.setFile('uri' in element.reference ? element.reference.uri : element.reference, {
1085
+ fileKind: FileKind.FILE,
1086
+ fileDecorations: { badges: false, colors: false },
1087
+ range: 'range' in element.reference ? element.reference.range : undefined
1088
+ });
1089
+ }
1090
+ disposeTemplate(templateData) {
1091
+ templateData.templateDisposables.dispose();
1092
+ }
1093
+ }
1094
+ class ResourcePool extends Disposable {
1095
+ get inUse() {
1096
+ return this._inUse;
1097
+ }
1098
+ constructor(_itemFactory) {
1099
+ super();
1100
+ this._itemFactory = _itemFactory;
1101
+ this.pool = [];
1102
+ this._inUse = ( new Set());
1103
+ }
1104
+ get() {
1105
+ if (this.pool.length > 0) {
1106
+ const item = this.pool.pop();
1107
+ this._inUse.add(item);
1108
+ return item;
1109
+ }
1110
+ const item = this._register(this._itemFactory());
1111
+ this._inUse.add(item);
1112
+ return item;
1113
+ }
1114
+ release(item) {
1115
+ this._inUse.delete(item);
1116
+ this.pool.push(item);
1117
+ }
1118
+ }
1119
+ class ChatVoteButton extends MenuEntryActionViewItem {
1120
+ render(container) {
1121
+ super.render(container);
1122
+ container.classList.toggle('checked', this.action.checked);
1123
+ }
1124
+ }
1125
+ class ChatListTreeDelegate {
1126
+ static { this.ITEM_HEIGHT = 22; }
1127
+ getHeight(element) {
1128
+ return ChatListTreeDelegate.ITEM_HEIGHT;
1129
+ }
1130
+ getTemplateId(element) {
1131
+ return 'chatListTreeTemplate';
1132
+ }
1133
+ }
1134
+ class ChatListTreeCompressionDelegate {
1135
+ isIncompressible(element) {
1136
+ return !element.children;
1137
+ }
1138
+ }
1139
+ class ChatListTreeRenderer {
1140
+ constructor(labels, decorations) {
1141
+ this.labels = labels;
1142
+ this.decorations = decorations;
1143
+ this.templateId = 'chatListTreeTemplate';
1144
+ }
1145
+ renderCompressedElements(element, index, templateData, height) {
1146
+ templateData.label.element.style.display = 'flex';
1147
+ const label = ( element.element.elements.map((e) => e.label));
1148
+ templateData.label.setResource({ resource: element.element.elements[0].uri, name: label }, {
1149
+ title: element.element.elements[0].label,
1150
+ fileKind: element.children ? FileKind.FOLDER : FileKind.FILE,
1151
+ extraClasses: ['explorer-item'],
1152
+ fileDecorations: this.decorations
1153
+ });
1154
+ }
1155
+ renderTemplate(container) {
1156
+ const templateDisposables = ( new DisposableStore());
1157
+ const label = templateDisposables.add(this.labels.create(container, { supportHighlights: true }));
1158
+ return { templateDisposables, label };
1159
+ }
1160
+ renderElement(element, index, templateData, height) {
1161
+ templateData.label.element.style.display = 'flex';
1162
+ const hasExtension = /\.[^/.]+$/.test(element.element.label);
1163
+ if (!element.children.length && hasExtension) {
1164
+ templateData.label.setFile(element.element.uri, {
1165
+ fileKind: FileKind.FILE,
1166
+ hidePath: true,
1167
+ fileDecorations: this.decorations,
1168
+ });
1169
+ }
1170
+ else {
1171
+ templateData.label.setResource({ resource: element.element.uri, name: element.element.label }, {
1172
+ title: element.element.label,
1173
+ fileKind: FileKind.FOLDER,
1174
+ fileDecorations: this.decorations
1175
+ });
1176
+ }
1177
+ }
1178
+ disposeTemplate(templateData) {
1179
+ templateData.templateDisposables.dispose();
1180
+ }
1181
+ }
1182
+ class ChatListTreeDataSource {
1183
+ hasChildren(element) {
1184
+ return !!element.children;
1185
+ }
1186
+ async getChildren(element) {
1187
+ return element.children ?? [];
1188
+ }
1189
+ }
1190
+ function isInteractiveProgressTreeData(item) {
1191
+ return 'label' in item;
1192
+ }
1193
+ function contentToMarkdown(str) {
1194
+ return typeof str === 'string' ? { value: str } : str;
1195
+ }
1196
+
1197
+ export { ChatAccessibilityProvider, ChatListDelegate, ChatListItemRenderer };