@codingame/monaco-vscode-chat-service-override 5.3.0 → 6.0.1

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 (30) hide show
  1. package/chat.js +5 -7
  2. package/package.json +2 -2
  3. package/vscode/src/vs/workbench/contrib/chat/browser/actions/chatAccessibilityHelp.js +160 -0
  4. package/vscode/src/vs/workbench/contrib/chat/browser/actions/chatClearActions.js +17 -11
  5. package/vscode/src/vs/workbench/contrib/chat/browser/actions/chatCodeblockActions.js +15 -13
  6. package/vscode/src/vs/workbench/contrib/chat/browser/actions/chatContextActions.js +215 -0
  7. package/vscode/src/vs/workbench/contrib/chat/browser/actions/chatCopyActions.js +1 -9
  8. package/vscode/src/vs/workbench/contrib/chat/browser/actions/chatFileTreeActions.js +6 -4
  9. package/vscode/src/vs/workbench/contrib/chat/browser/actions/chatTitleActions.js +15 -93
  10. package/vscode/src/vs/workbench/contrib/chat/browser/chat.contribution.js +27 -106
  11. package/vscode/src/vs/workbench/contrib/chat/browser/chatAccessibilityService.js +5 -2
  12. package/vscode/src/vs/workbench/contrib/chat/browser/chatEditor.js +6 -1
  13. package/vscode/src/vs/workbench/contrib/chat/browser/chatParticipantContributions.js +95 -51
  14. package/vscode/src/vs/workbench/contrib/chat/browser/chatQuick.js +4 -4
  15. package/vscode/src/vs/workbench/contrib/chat/browser/chatResponseAccessibleView.js +94 -0
  16. package/vscode/src/vs/workbench/contrib/chat/browser/chatVariables.js +64 -8
  17. package/vscode/src/vs/workbench/contrib/chat/browser/chatViewPane.js +2 -1
  18. package/vscode/src/vs/workbench/contrib/chat/browser/contrib/chatContextAttachments.js +50 -0
  19. package/vscode/src/vs/workbench/contrib/chat/browser/contrib/chatInputCompletions.js +370 -0
  20. package/vscode/src/vs/workbench/contrib/chat/browser/contrib/chatInputEditorContrib.js +19 -366
  21. package/vscode/src/vs/workbench/contrib/chat/common/chatServiceImpl.js +122 -63
  22. package/vscode/src/vs/workbench/contrib/chat/common/chatWidgetHistoryService.js +12 -5
  23. package/vscode/src/vs/workbench/contrib/chat/common/languageModelStats.js +6 -5
  24. package/vscode/src/vs/workbench/contrib/chat/common/{voiceChat.js → voiceChatService.js} +58 -21
  25. package/vscode/src/vs/workbench/contrib/inlineChat/browser/inlineChat.contribution.js +15 -14
  26. package/vscode/src/vs/workbench/contrib/inlineChat/browser/inlineChatAccessibleView.js +33 -32
  27. package/vscode/src/vs/workbench/contrib/inlineChat/browser/inlineChatSavingServiceImpl.js +6 -3
  28. package/vscode/src/vs/workbench/contrib/chat/browser/contrib/chatHistoryVariables.js +0 -26
  29. package/vscode/src/vs/workbench/contrib/chat/common/languageModels.js +0 -50
  30. package/vscode/src/vs/workbench/contrib/inlineChat/common/inlineChatServiceImpl.js +0 -33
@@ -1,7 +1,8 @@
1
1
  import { __decorate, __param } from 'vscode/external/tslib/tslib.es6.js';
2
2
  import { isNonEmptyArray } from 'vscode/vscode/vs/base/common/arrays';
3
+ import { AmbiguousCharacters, InvisibleCharacters } from 'vscode/vscode/vs/base/common/strings';
3
4
  import { Codicon } from 'vscode/vscode/vs/base/common/codicons';
4
- import { DisposableStore, DisposableMap, toDisposable } from 'vscode/vscode/vs/base/common/lifecycle';
5
+ import { DisposableStore, DisposableMap, Disposable, toDisposable } from 'vscode/vscode/vs/base/common/lifecycle';
5
6
  import { localizeWithPath, localize2WithPath } from 'vscode/vscode/vs/nls';
6
7
  import { ContextKeyExpr } from 'vscode/vscode/vs/platform/contextkey/common/contextkey';
7
8
  import { IContextKeyService } from 'vscode/vscode/vs/platform/contextkey/common/contextkey.service';
@@ -10,13 +11,18 @@ import { ILogService } from 'vscode/vscode/vs/platform/log/common/log.service';
10
11
  import { IProductService } from 'vscode/vscode/vs/platform/product/common/productService.service';
11
12
  import { Registry } from 'vscode/vscode/vs/platform/registry/common/platform';
12
13
  import { ViewPaneContainer } from 'vscode/vscode/vs/workbench/browser/parts/views/viewPaneContainer';
13
- import { Extensions } from 'vscode/vscode/vs/workbench/common/views';
14
+ import { Extensions, ViewContainerLocation } from 'vscode/vscode/vs/workbench/common/views';
14
15
  import { CHAT_VIEW_ID } from 'vscode/vscode/vs/workbench/contrib/chat/browser/chat';
15
16
  import { ChatViewPane, CHAT_SIDEBAR_PANEL_ID } from './chatViewPane.js';
16
17
  import { ChatAgentLocation } from 'vscode/vscode/vs/workbench/contrib/chat/common/chatAgents';
17
18
  import { IChatAgentService } from 'vscode/vscode/vs/workbench/contrib/chat/common/chatAgents.service';
18
19
  import { isProposedApiEnabled } from 'vscode/vscode/vs/workbench/services/extensions/common/extensions';
19
20
  import { ExtensionsRegistry } from 'vscode/vscode/vs/workbench/services/extensions/common/extensionsRegistry';
21
+ import 'vscode/vscode/vs/platform/notification/common/notification';
22
+ import { INotificationService } from 'vscode/vscode/vs/platform/notification/common/notification.service';
23
+ import { Action } from 'vscode/vscode/vs/base/common/actions';
24
+ import { ICommandService } from 'vscode/vscode/vs/platform/commands/common/commands.service';
25
+ import Severity$1 from 'vscode/vscode/vs/base/common/severity';
20
26
 
21
27
  const _moduleId = "vs/workbench/contrib/chat/browser/chatParticipantContributions";
22
28
  const chatParticipantExtensionPoint = ExtensionsRegistry.registerExtensionPoint({
@@ -38,21 +44,23 @@ const chatParticipantExtensionPoint = ExtensionsRegistry.registerExtensionPoint(
38
44
  description: ( localizeWithPath(
39
45
  _moduleId,
40
46
  2,
41
- "User-facing display name for this chat participant. The user will use '@' with this name to invoke the participant."
47
+ "User-facing name for this chat participant. The user will use '@' with this name to invoke the participant. Name must not contain whitespace."
42
48
  )),
43
- type: 'string'
49
+ type: 'string',
50
+ pattern: '^[\\w0-9_-]+$'
44
51
  },
45
- description: {
46
- description: ( localizeWithPath(_moduleId, 3, "A description of this chat participant, shown in the UI.")),
47
- type: 'string'
48
- },
49
- isDefault: {
52
+ fullName: {
50
53
  markdownDescription: ( localizeWithPath(
51
54
  _moduleId,
52
- 4,
53
- "**Only** allowed for extensions that have the `defaultChatParticipant` proposal."
55
+ 3,
56
+ "The full name of this chat participant, which is shown as the label for responses coming from this participant. If not provided, {0} is used.",
57
+ '`name`'
54
58
  )),
55
- type: 'boolean',
59
+ type: 'string'
60
+ },
61
+ description: {
62
+ description: ( localizeWithPath(_moduleId, 4, "A description of this chat participant, shown in the UI.")),
63
+ type: 'string'
56
64
  },
57
65
  isSticky: {
58
66
  description: ( localizeWithPath(
@@ -62,17 +70,18 @@ const chatParticipantExtensionPoint = ExtensionsRegistry.registerExtensionPoint(
62
70
  )),
63
71
  type: 'boolean'
64
72
  },
65
- defaultImplicitVariables: {
66
- markdownDescription: '**Only** allowed for extensions that have the `chatParticipantAdditions` proposal. The names of the variables that are invoked by default',
67
- type: 'array',
68
- items: {
69
- type: 'string'
70
- }
73
+ sampleRequest: {
74
+ description: ( localizeWithPath(
75
+ _moduleId,
76
+ 6,
77
+ "When the user clicks this participant in `/help`, this text will be submitted to the participant."
78
+ )),
79
+ type: 'string'
71
80
  },
72
81
  commands: {
73
82
  markdownDescription: ( localizeWithPath(
74
83
  _moduleId,
75
- 6,
84
+ 7,
76
85
  "Commands available for this chat participant, which the user can invoke with a `/`."
77
86
  )),
78
87
  type: 'array',
@@ -85,24 +94,24 @@ const chatParticipantExtensionPoint = ExtensionsRegistry.registerExtensionPoint(
85
94
  name: {
86
95
  description: ( localizeWithPath(
87
96
  _moduleId,
88
- 7,
97
+ 8,
89
98
  "A short name by which this command is referred to in the UI, e.g. `fix` or * `explain` for commands that fix an issue or explain code. The name should be unique among the commands provided by this participant."
90
99
  )),
91
100
  type: 'string'
92
101
  },
93
102
  description: {
94
- description: ( localizeWithPath(_moduleId, 8, "A description of this command.")),
103
+ description: ( localizeWithPath(_moduleId, 9, "A description of this command.")),
95
104
  type: 'string'
96
105
  },
97
106
  when: {
98
- description: ( localizeWithPath(_moduleId, 9, "A condition which must be true to enable this command.")),
107
+ description: ( localizeWithPath(_moduleId, 10, "A condition which must be true to enable this command.")),
99
108
  type: 'string'
100
109
  },
101
110
  sampleRequest: {
102
111
  description: ( localizeWithPath(
103
112
  _moduleId,
104
- 10,
105
- "When the user clicks this command in `/help`, this text will be submitted to this participant."
113
+ 11,
114
+ "When the user clicks this command in `/help`, this text will be submitted to the participant."
106
115
  )),
107
116
  type: 'string'
108
117
  },
@@ -114,29 +123,9 @@ const chatParticipantExtensionPoint = ExtensionsRegistry.registerExtensionPoint(
114
123
  )),
115
124
  type: 'boolean'
116
125
  },
117
- defaultImplicitVariables: {
118
- markdownDescription: ( localizeWithPath(
119
- _moduleId,
120
- 11,
121
- "**Only** allowed for extensions that have the `chatParticipantAdditions` proposal. The names of the variables that are invoked by default"
122
- )),
123
- type: 'array',
124
- items: {
125
- type: 'string'
126
- }
127
- },
128
126
  }
129
127
  }
130
128
  },
131
- locations: {
132
- markdownDescription: ( localizeWithPath(_moduleId, 12, "Locations in which this chat participant is available.")),
133
- type: 'array',
134
- default: ['panel'],
135
- items: {
136
- type: 'string',
137
- enum: ['panel', 'terminal', 'notebook']
138
- }
139
- }
140
129
  }
141
130
  }
142
131
  },
@@ -148,13 +137,16 @@ const chatParticipantExtensionPoint = ExtensionsRegistry.registerExtensionPoint(
148
137
  });
149
138
  let ChatExtensionPointHandler = class ChatExtensionPointHandler {
150
139
  static { this.ID = 'workbench.contrib.chatExtensionPointHandler'; }
151
- constructor(_chatAgentService, productService, contextService, logService) {
140
+ constructor(_chatAgentService, productService, contextService, logService, notificationService, commandService) {
152
141
  this._chatAgentService = _chatAgentService;
153
142
  this.productService = productService;
154
143
  this.contextService = contextService;
155
144
  this.logService = logService;
145
+ this.notificationService = notificationService;
146
+ this.commandService = commandService;
156
147
  this.disposables = ( (new DisposableStore()));
157
148
  this._participantRegistrationDisposables = ( (new DisposableMap()));
149
+ this.hasRegisteredDefaultParticipantView = false;
158
150
  this._viewContainer = this.registerViewContainer();
159
151
  this.registerListeners();
160
152
  this.handleAndRegisterChatExtensions();
@@ -193,12 +185,48 @@ let ChatExtensionPointHandler = class ChatExtensionPointHandler {
193
185
  handleAndRegisterChatExtensions() {
194
186
  chatParticipantExtensionPoint.setHandler((extensions, delta) => {
195
187
  for (const extension of delta.added) {
188
+ if (( (extension.value.some(
189
+ participant => participant.id === 'github.copilot.default' && !participant.fullName
190
+ )))) {
191
+ this.notificationService.notify({
192
+ severity: Severity$1.Error,
193
+ message: ( localizeWithPath(
194
+ _moduleId,
195
+ 12,
196
+ "Chat failed to load. Please ensure that the GitHub Copilot Chat extension is up to date."
197
+ )),
198
+ actions: {
199
+ primary: [
200
+ ( (new Action('showExtension', ( localizeWithPath(_moduleId, 13, "Show Extension")), undefined, true, () => {
201
+ return this.commandService.executeCommand('workbench.extensions.action.showExtensionsWithIds', ['GitHub.copilot-chat']);
202
+ })))
203
+ ]
204
+ }
205
+ });
206
+ continue;
207
+ }
208
+ if (this.productService.quality === 'stable' && !isProposedApiEnabled(extension.description, 'chatParticipantPrivate')) {
209
+ this.logService.warn(`Chat participants are not yet enabled in VS Code Stable (${extension.description.identifier.value})`);
210
+ continue;
211
+ }
196
212
  for (const providerDescriptor of extension.value) {
213
+ if (!providerDescriptor.name.match(/^[\w0-9_-]+$/)) {
214
+ this.logService.error(`Extension '${extension.description.identifier.value}' CANNOT register participant with invalid name: ${providerDescriptor.name}. Name must match /^[\\w0-9_-]+$/.`);
215
+ continue;
216
+ }
217
+ if (providerDescriptor.fullName && AmbiguousCharacters.getInstance(( (new Set()))).containsAmbiguousCharacter(providerDescriptor.fullName)) {
218
+ this.logService.error(`Extension '${extension.description.identifier.value}' CANNOT register participant with fullName that contains ambiguous characters: ${providerDescriptor.fullName}.`);
219
+ continue;
220
+ }
221
+ if (providerDescriptor.fullName && InvisibleCharacters.containsInvisibleCharacter(providerDescriptor.fullName.replace(/ /g, ''))) {
222
+ this.logService.error(`Extension '${extension.description.identifier.value}' CANNOT register participant with fullName that contains invisible characters: ${providerDescriptor.fullName}.`);
223
+ continue;
224
+ }
197
225
  if (providerDescriptor.isDefault && !isProposedApiEnabled(extension.description, 'defaultChatParticipant')) {
198
226
  this.logService.error(`Extension '${extension.description.identifier.value}' CANNOT use API proposal: defaultChatParticipant.`);
199
227
  continue;
200
228
  }
201
- if (providerDescriptor.defaultImplicitVariables && !isProposedApiEnabled(extension.description, 'chatParticipantAdditions')) {
229
+ if ((providerDescriptor.defaultImplicitVariables || providerDescriptor.locations) && !isProposedApiEnabled(extension.description, 'chatParticipantAdditions')) {
202
230
  this.logService.error(`Extension '${extension.description.identifier.value}' CANNOT use API proposal: chatParticipantAdditions.`);
203
231
  continue;
204
232
  }
@@ -210,17 +238,24 @@ let ChatExtensionPointHandler = class ChatExtensionPointHandler {
210
238
  if (providerDescriptor.isDefault && (!providerDescriptor.locations || providerDescriptor.locations?.includes(ChatAgentLocation.Panel))) {
211
239
  store.add(this.registerDefaultParticipantView(providerDescriptor));
212
240
  }
241
+ if (providerDescriptor.when && !isProposedApiEnabled(extension.description, 'chatParticipantAdditions')) {
242
+ this.logService.error(`Extension '${extension.description.identifier.value}' CANNOT use API proposal: chatParticipantAdditions.`);
243
+ continue;
244
+ }
213
245
  store.add(this._chatAgentService.registerAgent(providerDescriptor.id, {
214
246
  extensionId: extension.description.identifier,
215
- extensionPublisherDisplayName: extension.description.publisherDisplayName ?? extension.description.publisher,
247
+ publisherDisplayName: extension.description.publisherDisplayName ?? extension.description.publisher,
216
248
  extensionPublisherId: extension.description.publisher,
217
249
  extensionDisplayName: extension.description.displayName ?? extension.description.name,
218
250
  id: providerDescriptor.id,
219
251
  description: providerDescriptor.description,
252
+ when: providerDescriptor.when,
220
253
  metadata: {
221
254
  isSticky: providerDescriptor.isSticky,
255
+ sampleRequest: providerDescriptor.sampleRequest,
222
256
  },
223
257
  name: providerDescriptor.name,
258
+ fullName: providerDescriptor.fullName,
224
259
  isDefault: providerDescriptor.isDefault,
225
260
  defaultImplicitVariables: providerDescriptor.defaultImplicitVariables,
226
261
  locations: isNonEmptyArray(providerDescriptor.locations) ?
@@ -239,7 +274,7 @@ let ChatExtensionPointHandler = class ChatExtensionPointHandler {
239
274
  });
240
275
  }
241
276
  registerViewContainer() {
242
- const title = ( localize2WithPath(_moduleId, 13, "Chat"));
277
+ const title = ( localize2WithPath(_moduleId, 14, "Chat"));
243
278
  const icon = Codicon.commentDiscussion;
244
279
  const viewContainerId = CHAT_SIDEBAR_PANEL_ID;
245
280
  const viewContainer = ( (Registry.as(Extensions.ViewContainersRegistry))).registerViewContainer({
@@ -253,22 +288,29 @@ let ChatExtensionPointHandler = class ChatExtensionPointHandler {
253
288
  storageId: viewContainerId,
254
289
  hideIfEmpty: true,
255
290
  order: 100,
256
- }, 0 );
291
+ }, ViewContainerLocation.Sidebar);
257
292
  return viewContainer;
258
293
  }
259
294
  registerDefaultParticipantView(defaultParticipantDescriptor) {
295
+ if (this.hasRegisteredDefaultParticipantView) {
296
+ this.logService.warn(`Tried to register a second default chat participant view for "${defaultParticipantDescriptor.id}"`);
297
+ return Disposable.None;
298
+ }
299
+ const name = defaultParticipantDescriptor.fullName ?? defaultParticipantDescriptor.name;
260
300
  const viewDescriptor = [{
261
301
  id: CHAT_VIEW_ID,
262
302
  containerIcon: this._viewContainer.icon,
263
303
  containerTitle: this._viewContainer.title.value,
264
304
  singleViewPaneContainerTitle: this._viewContainer.title.value,
265
- name: { value: defaultParticipantDescriptor.name, original: defaultParticipantDescriptor.name },
305
+ name: { value: name, original: name },
266
306
  canToggleVisibility: false,
267
307
  canMoveView: true,
268
308
  ctorDescriptor: ( (new SyncDescriptor(ChatViewPane))),
269
309
  }];
310
+ this.hasRegisteredDefaultParticipantView = true;
270
311
  ( (Registry.as(Extensions.ViewsRegistry))).registerViews(viewDescriptor, this._viewContainer);
271
312
  return toDisposable(() => {
313
+ this.hasRegisteredDefaultParticipantView = false;
272
314
  ( (Registry.as(Extensions.ViewsRegistry))).deregisterViews(viewDescriptor, this._viewContainer);
273
315
  });
274
316
  }
@@ -277,7 +319,9 @@ ChatExtensionPointHandler = ( (__decorate([
277
319
  ( (__param(0, IChatAgentService))),
278
320
  ( (__param(1, IProductService))),
279
321
  ( (__param(2, IContextKeyService))),
280
- ( (__param(3, ILogService)))
322
+ ( (__param(3, ILogService))),
323
+ ( (__param(4, INotificationService))),
324
+ ( (__param(5, ICommandService)))
281
325
  ], ChatExtensionPointHandler)));
282
326
  function getParticipantKey(extensionId, participantName) {
283
327
  return `${extensionId.value}_${participantName}`;
@@ -1,6 +1,6 @@
1
1
  import { __decorate, __param } from 'vscode/external/tslib/tslib.es6.js';
2
2
  import { isAncestorOfActiveElement, $ } from 'vscode/vscode/vs/base/browser/dom';
3
- import { Sash } from 'vscode/vscode/vs/base/browser/ui/sash/sash';
3
+ import { Sash, Orientation } from 'vscode/vscode/vs/base/browser/ui/sash/sash';
4
4
  import { disposableTimeout } from 'vscode/vscode/vs/base/common/async';
5
5
  import { CancellationToken } from 'vscode/vscode/vs/base/common/cancellation';
6
6
  import { Emitter, Event } from 'vscode/vscode/vs/base/common/event';
@@ -174,10 +174,10 @@ let QuickChat = class QuickChat extends Disposable {
174
174
  if (this.widget) {
175
175
  throw ( new Error('Cannot render quick chat twice'));
176
176
  }
177
- const scopedInstantiationService = this.instantiationService.createChild(( new ServiceCollection([
177
+ const scopedInstantiationService = this._register(this.instantiationService.createChild(( new ServiceCollection([
178
178
  IContextKeyService,
179
179
  this._register(this.contextKeyService.createScoped(parent))
180
- ])));
180
+ ]))));
181
181
  this.widget = this._register(scopedInstantiationService.createInstance(ChatWidget, ChatAgentLocation.Panel, { resource: true }, { renderInputOnTop: true, renderStyle: 'compact', menus: { inputSideToolbar: MenuId.ChatInputSide } }, {
182
182
  listForeground: quickInputForeground,
183
183
  listBackground: quickInputBackground,
@@ -191,7 +191,7 @@ let QuickChat = class QuickChat extends Disposable {
191
191
  this.sash = this._register(( new Sash(
192
192
  parent,
193
193
  { getHorizontalSashTop: () => parent.offsetHeight },
194
- { orientation: 1 }
194
+ { orientation: Orientation.HORIZONTAL }
195
195
  )));
196
196
  this.registerListeners(parent);
197
197
  }
@@ -0,0 +1,94 @@
1
+ import { renderMarkdownAsPlaintext } from 'vscode/vscode/vs/base/browser/markdownRenderer';
2
+ import { MarkdownString } from 'vscode/vscode/vs/base/common/htmlContent';
3
+ import { ICodeEditorService } from 'vscode/vscode/vs/editor/browser/services/codeEditorService';
4
+ import { AccessibleViewType, AccessibleViewProviderId } from 'vscode/vscode/vs/platform/accessibility/browser/accessibleView';
5
+ import { alertAccessibleViewFocusChange } from 'vscode/vscode/vs/platform/accessibility/browser/accessibleViewRegistry';
6
+ import { AccessibilityVerbositySettingId } from 'vscode/vscode/vs/workbench/contrib/accessibility/browser/accessibilityConfiguration';
7
+ import { IChatWidgetService } from 'vscode/vscode/vs/workbench/contrib/chat/browser/chat.service';
8
+ import { CONTEXT_IN_CHAT_SESSION } from 'vscode/vscode/vs/workbench/contrib/chat/common/chatContextKeys';
9
+ import { ChatWelcomeMessageModel } from 'vscode/vscode/vs/workbench/contrib/chat/common/chatModel';
10
+ import { isResponseVM } from 'vscode/vscode/vs/workbench/contrib/chat/common/chatViewModel';
11
+
12
+ class ChatResponseAccessibleView {
13
+ constructor() {
14
+ this.priority = 100;
15
+ this.name = 'panelChat';
16
+ this.type = AccessibleViewType.View;
17
+ this.when = CONTEXT_IN_CHAT_SESSION;
18
+ }
19
+ getProvider(accessor) {
20
+ const widgetService = accessor.get(IChatWidgetService);
21
+ const codeEditorService = accessor.get(ICodeEditorService);
22
+ return resolveProvider(widgetService, codeEditorService, true);
23
+ function resolveProvider(widgetService, codeEditorService, initialRender) {
24
+ const widget = widgetService.lastFocusedWidget;
25
+ if (!widget) {
26
+ return;
27
+ }
28
+ const chatInputFocused = initialRender && !!codeEditorService.getFocusedCodeEditor();
29
+ if (initialRender && chatInputFocused) {
30
+ widget.focusLastMessage();
31
+ }
32
+ if (!widget) {
33
+ return;
34
+ }
35
+ const verifiedWidget = widget;
36
+ const focusedItem = verifiedWidget.getFocus();
37
+ if (!focusedItem) {
38
+ return;
39
+ }
40
+ widget.focus(focusedItem);
41
+ const isWelcome = focusedItem instanceof ChatWelcomeMessageModel;
42
+ let responseContent = isResponseVM(focusedItem) ? focusedItem.response.asString() : undefined;
43
+ if (isWelcome) {
44
+ const welcomeReplyContents = [];
45
+ for (const content of focusedItem.content) {
46
+ if (Array.isArray(content)) {
47
+ welcomeReplyContents.push(...( content.map(m => m.message)));
48
+ }
49
+ else {
50
+ welcomeReplyContents.push(content.value);
51
+ }
52
+ }
53
+ responseContent = welcomeReplyContents.join('\n');
54
+ }
55
+ if (!responseContent && 'errorDetails' in focusedItem && focusedItem.errorDetails) {
56
+ responseContent = focusedItem.errorDetails.message;
57
+ }
58
+ if (!responseContent) {
59
+ return;
60
+ }
61
+ const responses = verifiedWidget.viewModel?.getItems().filter(i => isResponseVM(i));
62
+ const length = responses?.length;
63
+ const responseIndex = responses?.findIndex(i => i === focusedItem);
64
+ return {
65
+ id: AccessibleViewProviderId.Chat,
66
+ verbositySettingKey: AccessibilityVerbositySettingId.Chat,
67
+ provideContent() { return renderMarkdownAsPlaintext(( new MarkdownString(responseContent)), true); },
68
+ onClose() {
69
+ verifiedWidget.reveal(focusedItem);
70
+ if (chatInputFocused) {
71
+ verifiedWidget.focusInput();
72
+ }
73
+ else {
74
+ verifiedWidget.focus(focusedItem);
75
+ }
76
+ },
77
+ next() {
78
+ verifiedWidget.moveFocus(focusedItem, 'next');
79
+ alertAccessibleViewFocusChange(responseIndex, length, 'next');
80
+ resolveProvider(widgetService, codeEditorService);
81
+ },
82
+ previous() {
83
+ verifiedWidget.moveFocus(focusedItem, 'previous');
84
+ alertAccessibleViewFocusChange(responseIndex, length, 'previous');
85
+ resolveProvider(widgetService, codeEditorService);
86
+ },
87
+ options: { type: AccessibleViewType.View }
88
+ };
89
+ }
90
+ }
91
+ dispose() { }
92
+ }
93
+
94
+ export { ChatResponseAccessibleView };
@@ -1,18 +1,25 @@
1
1
  import { __decorate, __param } from 'vscode/external/tslib/tslib.es6.js';
2
+ import { basename } from 'vscode/vscode/vs/base/common/path';
2
3
  import { coalesce } from 'vscode/vscode/vs/base/common/arrays';
3
4
  import { onUnexpectedExternalError } from 'vscode/vscode/vs/base/common/errors';
4
5
  import { Iterable } from 'vscode/vscode/vs/base/common/iterator';
5
6
  import { toDisposable } from 'vscode/vscode/vs/base/common/lifecycle';
7
+ import { URI } from 'vscode/vscode/vs/base/common/uri';
8
+ import { showChatView } from 'vscode/vscode/vs/workbench/contrib/chat/browser/chat';
6
9
  import { IChatWidgetService } from 'vscode/vscode/vs/workbench/contrib/chat/browser/chat.service';
7
10
  import { ChatDynamicVariableModel } from 'vscode/vscode/vs/workbench/contrib/chat/browser/contrib/chatDynamicVariables';
11
+ import { ChatAgentLocation } from 'vscode/vscode/vs/workbench/contrib/chat/common/chatAgents';
8
12
  import { ChatRequestVariablePart, ChatRequestDynamicVariablePart } from 'vscode/vscode/vs/workbench/contrib/chat/common/chatParserTypes';
13
+ import { ChatContextAttachments } from './contrib/chatContextAttachments.js';
14
+ import { IViewsService } from 'vscode/vscode/vs/workbench/services/views/common/viewsService.service';
9
15
 
10
16
  let ChatVariablesService = class ChatVariablesService {
11
- constructor(chatWidgetService) {
17
+ constructor(chatWidgetService, viewsService) {
12
18
  this.chatWidgetService = chatWidgetService;
19
+ this.viewsService = viewsService;
13
20
  this._resolver = ( new Map());
14
21
  }
15
- async resolveVariables(prompt, model, progress, token) {
22
+ async resolveVariables(prompt, attachedContextVariables, model, progress, token) {
16
23
  let resolvedVariables = [];
17
24
  const jobs = [];
18
25
  prompt.parts
@@ -28,18 +35,44 @@ let ChatVariablesService = class ChatVariablesService {
28
35
  }
29
36
  progress(item);
30
37
  };
31
- jobs.push(data.resolver(prompt.text, part.variableArg, model, variableProgressCallback, token).then(values => {
32
- resolvedVariables[i] = { name: part.variableName, range: part.range, values: values ?? [], references };
38
+ jobs.push(data.resolver(prompt.text, part.variableArg, model, variableProgressCallback, token).then(value => {
39
+ if (value) {
40
+ resolvedVariables[i] = { id: data.data.id, modelDescription: data.data.modelDescription, name: part.variableName, range: part.range, value, references };
41
+ }
33
42
  }).catch(onUnexpectedExternalError));
34
43
  }
35
44
  }
36
45
  else if (part instanceof ChatRequestDynamicVariablePart) {
37
- resolvedVariables[i] = { name: part.referenceText, range: part.range, values: part.data };
46
+ resolvedVariables[i] = { id: part.id, name: part.referenceText, range: part.range, value: part.data };
47
+ }
48
+ });
49
+ const resolvedAttachedContext = [];
50
+ attachedContextVariables
51
+ ?.forEach((attachment, i) => {
52
+ const data = this._resolver.get(attachment.name?.toLowerCase());
53
+ if (data) {
54
+ const references = [];
55
+ const variableProgressCallback = (item) => {
56
+ if (item.kind === 'reference') {
57
+ references.push(item);
58
+ return;
59
+ }
60
+ progress(item);
61
+ };
62
+ jobs.push(data.resolver(prompt.text, '', model, variableProgressCallback, token).then(value => {
63
+ if (value) {
64
+ resolvedAttachedContext[i] = { id: data.data.id, modelDescription: data.data.modelDescription, name: attachment.name, range: attachment.range, value, references };
65
+ }
66
+ }).catch(onUnexpectedExternalError));
67
+ }
68
+ else if (attachment.isDynamic) {
69
+ resolvedAttachedContext[i] = { id: attachment.id, name: attachment.name, value: attachment.value };
38
70
  }
39
71
  });
40
72
  await Promise.allSettled(jobs);
41
73
  resolvedVariables = coalesce(resolvedVariables);
42
74
  resolvedVariables.sort((a, b) => b.range.start - a.range.start);
75
+ resolvedVariables.push(...resolvedAttachedContext);
43
76
  return {
44
77
  variables: resolvedVariables,
45
78
  };
@@ -47,9 +80,9 @@ let ChatVariablesService = class ChatVariablesService {
47
80
  async resolveVariable(variableName, promptText, model, progress, token) {
48
81
  const data = this._resolver.get(variableName.toLowerCase());
49
82
  if (!data) {
50
- return Promise.resolve([]);
83
+ return undefined;
51
84
  }
52
- return (await data.resolver(promptText, undefined, model, progress, token)) ?? [];
85
+ return (await data.resolver(promptText, undefined, model, progress, token));
53
86
  }
54
87
  hasVariable(name) {
55
88
  return ( this._resolver.has(name.toLowerCase()));
@@ -82,9 +115,32 @@ let ChatVariablesService = class ChatVariablesService {
82
115
  this._resolver.delete(key);
83
116
  });
84
117
  }
118
+ async attachContext(name, value, location) {
119
+ if (location !== ChatAgentLocation.Panel) {
120
+ return;
121
+ }
122
+ await showChatView(this.viewsService);
123
+ const widget = this.chatWidgetService.lastFocusedWidget;
124
+ if (!widget || !widget.viewModel) {
125
+ return;
126
+ }
127
+ const key = name.toLowerCase();
128
+ if (key === 'file' && typeof value !== 'string') {
129
+ const uri = URI.isUri(value) ? value : value.uri;
130
+ const range = 'range' in value ? value.range : undefined;
131
+ widget.getContrib(ChatContextAttachments.ID)?.setContext(false, { value, id: ( uri.toString()) + (range?.toString() ?? ''), name: basename(uri.path), isFile: true, isDynamic: true });
132
+ return;
133
+ }
134
+ const resolved = this._resolver.get(key);
135
+ if (!resolved) {
136
+ return;
137
+ }
138
+ widget.getContrib(ChatContextAttachments.ID)?.setContext(false, { ...resolved.data, value });
139
+ }
85
140
  };
86
141
  ChatVariablesService = ( __decorate([
87
- ( __param(0, IChatWidgetService))
142
+ ( __param(0, IChatWidgetService)),
143
+ ( __param(1, IViewsService))
88
144
  ], ChatVariablesService));
89
145
 
90
146
  export { ChatVariablesService };
@@ -10,6 +10,7 @@ import { ServiceCollection } from 'vscode/vscode/vs/platform/instantiation/commo
10
10
  import { IKeybindingService } from 'vscode/vscode/vs/platform/keybinding/common/keybinding.service';
11
11
  import { ILogService } from 'vscode/vscode/vs/platform/log/common/log.service';
12
12
  import { IOpenerService } from 'vscode/vscode/vs/platform/opener/common/opener.service';
13
+ import { StorageScope, StorageTarget } from 'vscode/vscode/vs/platform/storage/common/storage';
13
14
  import { IStorageService } from 'vscode/vscode/vs/platform/storage/common/storage.service';
14
15
  import { ITelemetryService } from 'vscode/vscode/vs/platform/telemetry/common/telemetry.service';
15
16
  import 'vscode/vscode/vs/platform/theme/common/colorUtils';
@@ -48,7 +49,7 @@ let ChatViewPane = class ChatViewPane extends ViewPane {
48
49
  this.didProviderRegistrationFail = false;
49
50
  this.didUnregisterProvider = false;
50
51
  this.memento = ( new Memento('interactive-session-view-' + CHAT_PROVIDER_ID, this.storageService));
51
- this.viewState = this.memento.getMemento(1 , 1 );
52
+ this.viewState = this.memento.getMemento(StorageScope.WORKSPACE, StorageTarget.MACHINE);
52
53
  this._register(this.chatAgentService.onDidChangeAgents(() => {
53
54
  if (this.chatAgentService.getDefaultAgent(ChatAgentLocation.Panel)) {
54
55
  if (!this._widget?.viewModel) {
@@ -0,0 +1,50 @@
1
+ import { Disposable } from 'vscode/vscode/vs/base/common/lifecycle';
2
+ import { ChatWidget } from 'vscode/vscode/vs/workbench/contrib/chat/browser/chatWidget';
3
+
4
+ class ChatContextAttachments extends Disposable {
5
+ static { this.ID = 'chatContextAttachments'; }
6
+ get id() {
7
+ return ChatContextAttachments.ID;
8
+ }
9
+ constructor(widget) {
10
+ super();
11
+ this.widget = widget;
12
+ this._attachedContext = ( new Set());
13
+ this._register(this.widget.onDidDeleteContext((e) => {
14
+ this._removeContext(e);
15
+ }));
16
+ this._register(this.widget.onDidSubmitAgent(() => {
17
+ this._clearAttachedContext();
18
+ }));
19
+ }
20
+ getInputState() {
21
+ return [...( this._attachedContext.values())];
22
+ }
23
+ setInputState(s) {
24
+ if (!Array.isArray(s)) {
25
+ return;
26
+ }
27
+ this.widget.setContext(true, ...s);
28
+ }
29
+ getContext() {
30
+ return ( new Set(( [...( this._attachedContext.values())].map((v) => v.id))));
31
+ }
32
+ setContext(overwrite, ...attachments) {
33
+ if (overwrite) {
34
+ this._attachedContext.clear();
35
+ }
36
+ for (const attachment of attachments) {
37
+ this._attachedContext.add(attachment);
38
+ }
39
+ this.widget.setContext(overwrite, ...attachments);
40
+ }
41
+ _removeContext(attachment) {
42
+ this._attachedContext.delete(attachment);
43
+ }
44
+ _clearAttachedContext() {
45
+ this._attachedContext.clear();
46
+ }
47
+ }
48
+ ChatWidget.CONTRIBS.push(ChatContextAttachments);
49
+
50
+ export { ChatContextAttachments };