Skip to content

Commit 2672593

Browse files
Copilotalexr00
andcommitted
Use avatarUrl check instead of isEnterprise flag
Check for 'githubusercontent.com' in avatar URLs to determine if fetching should be attempted, rather than relying on the remote's enterprise flag. Co-authored-by: alexr00 <38270282+alexr00@users.noreply.github.com>
1 parent e369d09 commit 2672593

7 files changed

Lines changed: 205 additions & 17 deletions

src/@types/vscode.proposed.chatContextProvider.d.ts

Lines changed: 88 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -11,16 +11,45 @@ declare module 'vscode' {
1111
export namespace chat {
1212

1313
/**
14-
* Register a chat context provider. Chat context can be provided:
15-
* - For a resource. Make sure to pass a selector that matches the resource you want to provide context for.
16-
* Providers registered without a selector will not be called for resource-based context.
17-
* - Explicitly. These context items are shown as options when the user explicitly attaches context.
14+
* Register a chat workspace context provider. Workspace context is automatically included in all chat requests.
1815
*
1916
* To ensure your extension is activated when chat context is requested, make sure to include the following activations events:
2017
* - If your extension implements `provideWorkspaceChatContext` or `provideChatContextForResource`, find an activation event which is a good signal to activate.
2118
* Ex: `onLanguage:<languageId>`, `onWebviewPanel:<viewType>`, etc.`
2219
* - If your extension implements `provideChatContextExplicit`, your extension will be automatically activated when the user requests explicit context.
2320
*
21+
* @param id Unique identifier for the provider.
22+
* @param provider The chat workspace context provider.
23+
*/
24+
export function registerChatWorkspaceContextProvider(id: string, provider: ChatWorkspaceContextProvider): Disposable;
25+
26+
/**
27+
* Register a chat explicit context provider. Explicit context items are shown as options when the user explicitly attaches context.
28+
*
29+
* To ensure your extension is activated when chat context is requested, make sure to include the `onChatContextProvider:<id>` activation event in your `package.json`.
30+
*
31+
* @param id Unique identifier for the provider.
32+
* @param provider The chat explicit context provider.
33+
*/
34+
export function registerChatExplicitContextProvider(id: string, provider: ChatExplicitContextProvider): Disposable;
35+
36+
/**
37+
* Register a chat resource context provider. Resource context is provided for a specific resource.
38+
* Make sure to pass a selector that matches the resource you want to provide context for.
39+
*
40+
* To ensure your extension is activated when chat context is requested, make sure to include the `onChatContextProvider:<id>` activation event in your `package.json`.
41+
*
42+
* @param selector Document selector to filter which resources the provider is called for.
43+
* @param id Unique identifier for the provider.
44+
* @param provider The chat resource context provider.
45+
*/
46+
export function registerChatResourceContextProvider(selector: DocumentSelector, id: string, provider: ChatResourceContextProvider): Disposable;
47+
48+
/**
49+
* Register a chat context provider.
50+
*
51+
* @deprecated Use {@link registerChatWorkspaceContextProvider}, {@link registerChatExplicitContextProvider}, or {@link registerChatResourceContextProvider} instead.
52+
*
2453
* @param selector Optional document selector to filter which resources the provider is called for. If omitted, the provider will only be called for explicit context requests.
2554
* @param id Unique identifier for the provider.
2655
* @param provider The chat context provider.
@@ -57,23 +86,24 @@ declare module 'vscode' {
5786
command?: Command;
5887
}
5988

60-
export interface ChatContextProvider<T extends ChatContextItem = ChatContextItem> {
89+
export interface ChatWorkspaceContextProvider<T extends ChatContextItem = ChatContextItem> {
6190

6291
/**
6392
* An optional event that should be fired when the workspace chat context has changed.
6493
*/
6594
onDidChangeWorkspaceChatContext?: Event<void>;
6695

6796
/**
68-
* TODO @API: should this be a separate provider interface?
69-
*
7097
* Provide a list of chat context items to be included as workspace context for all chat requests.
7198
* This should be used very sparingly to avoid providing useless context and to avoid using up the context window.
7299
* A good example use case is to provide information about which branch the user is working on in a source control context.
73100
*
74101
* @param token A cancellation token.
75102
*/
76-
provideWorkspaceChatContext?(token: CancellationToken): ProviderResult<T[]>;
103+
provideChatContext(token: CancellationToken): ProviderResult<T[]>;
104+
}
105+
106+
export interface ChatExplicitContextProvider<T extends ChatContextItem = ChatContextItem> {
77107

78108
/**
79109
* Provide a list of chat context items that a user can choose from. These context items are shown as options when the user explicitly attaches context.
@@ -82,7 +112,18 @@ declare module 'vscode' {
82112
*
83113
* @param token A cancellation token.
84114
*/
85-
provideChatContextExplicit?(token: CancellationToken): ProviderResult<T[]>;
115+
provideChatContext(token: CancellationToken): ProviderResult<T[]>;
116+
117+
/**
118+
* If a chat context item is provided without a `value`, this method is called to resolve the `value` for the item.
119+
*
120+
* @param context The context item to resolve.
121+
* @param token A cancellation token.
122+
*/
123+
resolveChatContext(context: T, token: CancellationToken): ProviderResult<ChatContextItem>;
124+
}
125+
126+
export interface ChatResourceContextProvider<T extends ChatContextItem = ChatContextItem> {
86127

87128
/**
88129
* Given a particular resource, provide a chat context item for it. This is used for implicit context (see the settings `chat.implicitContext.enabled` and `chat.implicitContext.suggestedContext`).
@@ -94,15 +135,51 @@ declare module 'vscode' {
94135
* @param options Options include the resource for which to provide context.
95136
* @param token A cancellation token.
96137
*/
97-
provideChatContextForResource?(options: { resource: Uri }, token: CancellationToken): ProviderResult<T | undefined>;
138+
provideChatContext(options: { resource: Uri }, token: CancellationToken): ProviderResult<T | undefined>;
98139

99140
/**
100-
* If a chat context item is provided without a `value`, from either of the `provide` methods, this method is called to resolve the `value` for the item.
141+
* If a chat context item is provided without a `value`, this method is called to resolve the `value` for the item.
101142
*
102143
* @param context The context item to resolve.
103144
* @param token A cancellation token.
104145
*/
105146
resolveChatContext(context: T, token: CancellationToken): ProviderResult<ChatContextItem>;
106147
}
107148

149+
/**
150+
* @deprecated Use {@link ChatWorkspaceContextProvider}, {@link ChatExplicitContextProvider}, or {@link ChatResourceContextProvider} instead.
151+
*/
152+
export interface ChatContextProvider<T extends ChatContextItem = ChatContextItem> {
153+
154+
/**
155+
* An optional event that should be fired when the workspace chat context has changed.
156+
* @deprecated Use {@link ChatWorkspaceContextProvider.onDidChangeWorkspaceChatContext} instead.
157+
*/
158+
onDidChangeWorkspaceChatContext?: Event<void>;
159+
160+
/**
161+
* Provide a list of chat context items to be included as workspace context for all chat requests.
162+
* @deprecated Use {@link ChatWorkspaceContextProvider.provideChatContext} instead.
163+
*/
164+
provideWorkspaceChatContext?(token: CancellationToken): ProviderResult<T[]>;
165+
166+
/**
167+
* Provide a list of chat context items that a user can choose from.
168+
* @deprecated Use {@link ChatExplicitContextProvider.provideChatContext} instead.
169+
*/
170+
provideChatContextExplicit?(token: CancellationToken): ProviderResult<T[]>;
171+
172+
/**
173+
* Given a particular resource, provide a chat context item for it.
174+
* @deprecated Use {@link ChatResourceContextProvider.provideChatContext} instead.
175+
*/
176+
provideChatContextForResource?(options: { resource: Uri }, token: CancellationToken): ProviderResult<T | undefined>;
177+
178+
/**
179+
* If a chat context item is provided without a `value`, this method is called to resolve the `value` for the item.
180+
* @deprecated Use the `resolveChatContext` method on the specific provider type instead.
181+
*/
182+
resolveChatContext?(context: T, token: CancellationToken): ProviderResult<ChatContextItem>;
183+
}
184+
108185
}

src/@types/vscode.proposed.chatParticipantAdditions.d.ts

Lines changed: 112 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -96,6 +96,108 @@ declare module 'vscode' {
9696
constructor(title: string, message: string | MarkdownString, data: any, buttons?: string[]);
9797
}
9898

99+
/**
100+
* An option for a question in a carousel.
101+
*/
102+
export interface ChatQuestionOption {
103+
/**
104+
* Unique identifier for the option.
105+
*/
106+
id: string;
107+
/**
108+
* The display label for the option.
109+
*/
110+
label: string;
111+
/**
112+
* The value returned when this option is selected.
113+
*/
114+
value: unknown;
115+
}
116+
117+
/**
118+
* The type of question for a chat question carousel.
119+
*/
120+
export enum ChatQuestionType {
121+
/**
122+
* A free-form text input question.
123+
*/
124+
Text = 1,
125+
/**
126+
* A single-select question with radio buttons.
127+
*/
128+
SingleSelect = 2,
129+
/**
130+
* A multi-select question with checkboxes.
131+
*/
132+
MultiSelect = 3
133+
}
134+
135+
/**
136+
* A question to be displayed in a question carousel.
137+
*/
138+
export class ChatQuestion {
139+
/**
140+
* Unique identifier for the question.
141+
*/
142+
id: string;
143+
/**
144+
* The type of question: Text for free-form input, SingleSelect for radio buttons, MultiSelect for checkboxes.
145+
*/
146+
type: ChatQuestionType;
147+
/**
148+
* The title/header of the question.
149+
*/
150+
title: string;
151+
/**
152+
* Optional detailed message or description for the question.
153+
*/
154+
message?: string | MarkdownString;
155+
/**
156+
* Options for singleSelect or multiSelect questions.
157+
*/
158+
options?: ChatQuestionOption[];
159+
/**
160+
* The id(s) of the default selected option(s).
161+
* For SingleSelect, this should be a single option id.
162+
* For MultiSelect, this can be an array of option ids.
163+
*/
164+
defaultValue?: string | string[];
165+
/**
166+
* Whether to allow free-form text input in addition to predefined options.
167+
* When true, users can provide their own text answer even for SingleSelect or MultiSelect questions.
168+
*/
169+
allowFreeformInput?: boolean;
170+
171+
constructor(
172+
id: string,
173+
type: ChatQuestionType,
174+
title: string,
175+
options?: {
176+
message?: string | MarkdownString;
177+
options?: ChatQuestionOption[];
178+
defaultValue?: string | string[];
179+
allowFreeformInput?: boolean;
180+
}
181+
);
182+
}
183+
184+
/**
185+
* A carousel view for presenting multiple questions inline in the chat.
186+
* The UI is displayed but does not block the chat input.
187+
*/
188+
export class ChatResponseQuestionCarouselPart {
189+
/**
190+
* The questions to display in the carousel.
191+
*/
192+
questions: ChatQuestion[];
193+
/**
194+
* Whether users can skip answering the questions.
195+
*/
196+
allowSkip: boolean;
197+
198+
constructor(questions: ChatQuestion[], allowSkip?: boolean);
199+
}
200+
99201
export class ChatResponseCodeCitationPart {
100202
value: Uri;
101203
license: string;
@@ -244,7 +346,7 @@ declare module 'vscode' {
244346
constructor(uris: Uri[], callback: () => Thenable<unknown>);
245347
}
246348

247-
export type ExtendedChatResponsePart = ChatResponsePart | ChatResponseTextEditPart | ChatResponseNotebookEditPart | ChatResponseWorkspaceEditPart | ChatResponseConfirmationPart | ChatResponseCodeCitationPart | ChatResponseReferencePart2 | ChatResponseMovePart | ChatResponseExtensionsPart | ChatResponsePullRequestPart | ChatToolInvocationPart | ChatResponseMultiDiffPart | ChatResponseThinkingProgressPart | ChatResponseExternalEditPart;
349+
export type ExtendedChatResponsePart = ChatResponsePart | ChatResponseTextEditPart | ChatResponseNotebookEditPart | ChatResponseWorkspaceEditPart | ChatResponseConfirmationPart | ChatResponseCodeCitationPart | ChatResponseReferencePart2 | ChatResponseMovePart | ChatResponseExtensionsPart | ChatResponsePullRequestPart | ChatToolInvocationPart | ChatResponseMultiDiffPart | ChatResponseThinkingProgressPart | ChatResponseExternalEditPart | ChatResponseQuestionCarouselPart;
248350
export class ChatResponseWarningPart {
249351
value: MarkdownString;
250352
constructor(value: string | MarkdownString);
@@ -408,6 +510,15 @@ declare module 'vscode' {
408510
*/
409511
confirmation(title: string, message: string | MarkdownString, data: any, buttons?: string[]): void;
410512

513+
/**
514+
* Show an inline carousel of questions to gather information from the user.
515+
* This is a blocking call that waits for the user to submit or skip the questions.
516+
* @param questions Array of questions to display to the user
517+
* @param allowSkip Whether the user can skip questions without answering
518+
* @returns A promise that resolves with the user's answers, or undefined if skipped
519+
*/
520+
questionCarousel(questions: ChatQuestion[], allowSkip?: boolean): Thenable<Record<string, unknown> | undefined>;
521+
411522
/**
412523
* Push a warning to this stream. Short-hand for
413524
* `push(new ChatResponseWarningPart(message))`.

src/@types/vscode.proposed.chatSessionsProvider.d.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -97,7 +97,7 @@ declare module 'vscode' {
9797
*
9898
* This is also called on first load to get the initial set of items.
9999
*/
100-
refreshHandler: () => Thenable<void>;
100+
refreshHandler: (token: CancellationToken) => Thenable<void>;
101101

102102
/**
103103
* Fired when an item's archived state changes.

src/issues/issuesView.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -102,7 +102,7 @@ export class IssuesTreeData
102102

103103
if (avatarUser) {
104104
// For enterprise, use placeholder icon instead of trying to fetch avatar
105-
if (element.githubRepository.remote.isEnterprise) {
105+
if (!avatarUser.avatarUrl?.includes('githubusercontent.com')) {
106106
treeItem.iconPath = new vscode.ThemeIcon('github');
107107
} else {
108108
treeItem.iconPath = (await DataUri.avatarCirclesAsImageDataUris(this.context, [avatarUser], 16, 16))[0] ??

src/view/treeNodes/commitNode.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,7 @@ export class CommitNode extends TreeNode implements vscode.TreeItem {
4141
async getTreeItem(): Promise<vscode.TreeItem> {
4242
if (this.commit.author) {
4343
// For enterprise, use placeholder icon instead of trying to fetch avatar
44-
if (this.pullRequest.githubRepository.remote.isEnterprise) {
44+
if (!this.commit.author.avatar_url?.includes('githubusercontent.com')) {
4545
this.iconPath = new vscode.ThemeIcon('github');
4646
} else {
4747
const author: IAccount = { id: this.commit.author.node_id, login: this.commit.author.login, url: this.commit.author.url, avatarUrl: this.commit.author.avatar_url, accountType: this.commit.author.type as AccountType };

src/view/treeNodes/pullRequestNode.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -272,7 +272,7 @@ export class PRNode extends TreeNode implements vscode.CommentingRangeProvider2
272272

273273
private async _getAuthorIcon(): Promise<vscode.Uri | vscode.ThemeIcon> {
274274
// For enterprise, use placeholder icon instead of trying to fetch avatar
275-
if (this.pullRequestModel.githubRepository.remote.isEnterprise) {
275+
if (!this.pullRequestModel.author.avatarUrl?.includes('githubusercontent.com')) {
276276
return new vscode.ThemeIcon('github');
277277
}
278278
return (await DataUri.avatarCirclesAsImageDataUris(this._folderReposManager.context, [this.pullRequestModel.author], 16, 16))[0]

src/view/treeNodes/repositoryChangesNode.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -112,7 +112,7 @@ export class RepositoryChangesNode extends TreeNode implements vscode.TreeItem {
112112
override async getTreeItem(): Promise<vscode.TreeItem> {
113113
this.setLabel();
114114
// For enterprise, use placeholder icon instead of trying to fetch avatar
115-
if (this.pullRequestModel.githubRepository.remote.isEnterprise) {
115+
if (!this.pullRequestModel.author.avatarUrl?.includes('githubusercontent.com')) {
116116
this.iconPath = new vscode.ThemeIcon('github');
117117
} else {
118118
this.iconPath = (await DataUri.avatarCirclesAsImageDataUris(this._pullRequestManager.context, [this.pullRequestModel.author], 16, 16))[0];

0 commit comments

Comments
 (0)