Skip to content

Commit 7ca872e

Browse files
authored
Add option to skip showing recommended interpreter in quick pick API (#20604)
Closes #20260
1 parent 184617e commit 7ca872e

File tree

4 files changed

+51
-31
lines changed

4 files changed

+51
-31
lines changed

src/client/interpreter/configuration/interpreterSelector/commands/setInterpreter.ts

Lines changed: 29 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,7 @@ import {
3232
IInterpreterQuickPick,
3333
IInterpreterQuickPickItem,
3434
IInterpreterSelector,
35+
InterpreterQuickPickParams,
3536
IPythonPathUpdaterServiceManager,
3637
ISpecialQuickPickItem,
3738
} from '../../types';
@@ -127,12 +128,12 @@ export class SetInterpreterCommand extends BaseInterpreterSelectorCommand implem
127128
input: IMultiStepInput<InterpreterStateArgs>,
128129
state: InterpreterStateArgs,
129130
filter?: (i: PythonEnvironment) => boolean,
130-
params?: { placeholder?: string | null; title?: string | null },
131+
params?: InterpreterQuickPickParams,
131132
): Promise<void | InputStep<InterpreterStateArgs>> {
132133
// If the list is refreshing, it's crucial to maintain sorting order at all
133134
// times so that the visible items do not change.
134135
const preserveOrderWhenFiltering = !!this.interpreterService.refreshPromise;
135-
const suggestions = this._getItems(state.workspace, filter);
136+
const suggestions = this._getItems(state.workspace, filter, params);
136137
state.path = undefined;
137138
const currentInterpreterPathDisplay = this.pathUtils.getDisplayName(
138139
this.configurationService.getSettings(state.workspace).pythonPath,
@@ -183,10 +184,10 @@ export class SetInterpreterCommand extends BaseInterpreterSelectorCommand implem
183184
// Items are in the final state as all previous callbacks have finished executing.
184185
quickPick.busy = false;
185186
// Ensure we set a recommended item after refresh has finished.
186-
this.updateQuickPickItems(quickPick, {}, state.workspace, filter);
187+
this.updateQuickPickItems(quickPick, {}, state.workspace, filter, params);
187188
});
188189
}
189-
this.updateQuickPickItems(quickPick, event, state.workspace, filter);
190+
this.updateQuickPickItems(quickPick, event, state.workspace, filter, params);
190191
},
191192
},
192193
});
@@ -208,21 +209,26 @@ export class SetInterpreterCommand extends BaseInterpreterSelectorCommand implem
208209
return undefined;
209210
}
210211

211-
public _getItems(resource: Resource, filter: ((i: PythonEnvironment) => boolean) | undefined): QuickPickType[] {
212+
public _getItems(
213+
resource: Resource,
214+
filter: ((i: PythonEnvironment) => boolean) | undefined,
215+
params?: InterpreterQuickPickParams,
216+
): QuickPickType[] {
212217
const suggestions: QuickPickType[] = [this.manualEntrySuggestion];
213218
const defaultInterpreterPathSuggestion = this.getDefaultInterpreterPathSuggestion(resource);
214219
if (defaultInterpreterPathSuggestion) {
215220
suggestions.push(defaultInterpreterPathSuggestion);
216221
}
217-
const interpreterSuggestions = this.getSuggestions(resource, filter);
218-
this.finalizeItems(interpreterSuggestions, resource);
222+
const interpreterSuggestions = this.getSuggestions(resource, filter, params);
223+
this.finalizeItems(interpreterSuggestions, resource, params);
219224
suggestions.push(...interpreterSuggestions);
220225
return suggestions;
221226
}
222227

223228
private getSuggestions(
224229
resource: Resource,
225230
filter: ((i: PythonEnvironment) => boolean) | undefined,
231+
params?: InterpreterQuickPickParams,
226232
): QuickPickType[] {
227233
const workspaceFolder = this.workspaceService.getWorkspaceFolder(resource);
228234
const items = this.interpreterSelector
@@ -235,10 +241,13 @@ export class SetInterpreterCommand extends BaseInterpreterSelectorCommand implem
235241
const itemsWithFullName = this.interpreterSelector
236242
.getSuggestions(resource, true)
237243
.filter((i) => !filter || filter(i.interpreter));
238-
const recommended = this.interpreterSelector.getRecommendedSuggestion(
239-
itemsWithFullName,
240-
this.workspaceService.getWorkspaceFolder(resource)?.uri,
241-
);
244+
let recommended: IInterpreterQuickPickItem | undefined;
245+
if (!params?.skipRecommended) {
246+
recommended = this.interpreterSelector.getRecommendedSuggestion(
247+
itemsWithFullName,
248+
this.workspaceService.getWorkspaceFolder(resource)?.uri,
249+
);
250+
}
242251
if (recommended && items[0].interpreter.id === recommended.interpreter.id) {
243252
items.shift();
244253
}
@@ -289,10 +298,11 @@ export class SetInterpreterCommand extends BaseInterpreterSelectorCommand implem
289298
event: PythonEnvironmentsChangedEvent,
290299
resource: Resource,
291300
filter: ((i: PythonEnvironment) => boolean) | undefined,
301+
params?: InterpreterQuickPickParams,
292302
) {
293303
// Active items are reset once we replace the current list with updated items, so save it.
294304
const activeItemBeforeUpdate = quickPick.activeItems.length > 0 ? quickPick.activeItems[0] : undefined;
295-
quickPick.items = this.getUpdatedItems(quickPick.items, event, resource, filter);
305+
quickPick.items = this.getUpdatedItems(quickPick.items, event, resource, filter, params);
296306
// Ensure we maintain the same active item as before.
297307
const activeItem = activeItemBeforeUpdate
298308
? quickPick.items.find((item) => {
@@ -317,6 +327,7 @@ export class SetInterpreterCommand extends BaseInterpreterSelectorCommand implem
317327
event: PythonEnvironmentsChangedEvent,
318328
resource: Resource,
319329
filter: ((i: PythonEnvironment) => boolean) | undefined,
330+
params?: InterpreterQuickPickParams,
320331
): QuickPickType[] {
321332
const updatedItems = [...items.values()];
322333
const areItemsGrouped = items.find((item) => isSeparatorItem(item));
@@ -364,16 +375,18 @@ export class SetInterpreterCommand extends BaseInterpreterSelectorCommand implem
364375
if (envIndex !== -1 && event.new === undefined) {
365376
updatedItems.splice(envIndex, 1);
366377
}
367-
this.finalizeItems(updatedItems, resource);
378+
this.finalizeItems(updatedItems, resource, params);
368379
return updatedItems;
369380
}
370381

371-
private finalizeItems(items: QuickPickType[], resource: Resource) {
382+
private finalizeItems(items: QuickPickType[], resource: Resource, params?: InterpreterQuickPickParams) {
372383
const interpreterSuggestions = this.interpreterSelector.getSuggestions(resource, true);
373384
const r = this.interpreterService.refreshPromise;
374385
if (!r) {
375386
if (interpreterSuggestions.length) {
376-
this.setRecommendedItem(interpreterSuggestions, items, resource);
387+
if (!params?.skipRecommended) {
388+
this.setRecommendedItem(interpreterSuggestions, items, resource);
389+
}
377390
// Add warning label to certain environments
378391
items.forEach((item, i) => {
379392
if (isInterpreterQuickPickItem(item) && isProblematicCondaEnvironment(item.interpreter)) {
@@ -513,7 +526,7 @@ export class SetInterpreterCommand extends BaseInterpreterSelectorCommand implem
513526
public async getInterpreterViaQuickPick(
514527
workspace: Resource,
515528
filter: ((i: PythonEnvironment) => boolean) | undefined,
516-
params?: { placeholder?: string | null; title?: string | null },
529+
params?: InterpreterQuickPickParams,
517530
): Promise<string | undefined> {
518531
const interpreterState: InterpreterStateArgs = { path: undefined, workspace };
519532
const multiStep = this.multiStepFactory.create<InterpreterStateArgs>();

src/client/interpreter/configuration/types.ts

Lines changed: 16 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -66,20 +66,26 @@ export interface IInterpreterComparer {
6666
getRecommended(interpreters: PythonEnvironment[], resource: Resource): PythonEnvironment | undefined;
6767
}
6868

69+
export interface InterpreterQuickPickParams {
70+
/**
71+
* Specify `null` if a placeholder is not required.
72+
*/
73+
placeholder?: string | null;
74+
/**
75+
* Specify `null` if a title is not required.
76+
*/
77+
title?: string | null;
78+
/**
79+
* Specify `true` to skip showing recommended python interpreter.
80+
*/
81+
skipRecommended?: boolean;
82+
}
83+
6984
export const IInterpreterQuickPick = Symbol('IInterpreterQuickPick');
7085
export interface IInterpreterQuickPick {
7186
getInterpreterViaQuickPick(
7287
workspace: Resource,
7388
filter?: (i: PythonEnvironment) => boolean,
74-
params?: {
75-
/**
76-
* Specify `null` if a placeholder is not required.
77-
*/
78-
placeholder?: string | null;
79-
/**
80-
* Specify `null` if a title is not required.
81-
*/
82-
title?: string | null;
83-
},
89+
params?: InterpreterQuickPickParams,
8490
): Promise<string | undefined>;
8591
}

src/client/pythonEnvironments/creation/provider/venvCreationProvider.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -125,6 +125,7 @@ export class VenvCreationProvider implements CreateEnvironmentProvider {
125125
workspace.uri,
126126
(i: PythonEnvironment) =>
127127
[EnvironmentType.System, EnvironmentType.MicrosoftStore, EnvironmentType.Global].includes(i.envType),
128+
{ skipRecommended: true },
128129
);
129130

130131
if (!interpreter) {

src/test/pythonEnvironments/creation/provider/venvCreationProvider.unit.test.ts

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -76,7 +76,7 @@ suite('venv Creation provider tests', () => {
7676
pickWorkspaceFolderStub.resolves(workspace1);
7777

7878
interpreterQuickPick
79-
.setup((i) => i.getInterpreterViaQuickPick(typemoq.It.isAny(), typemoq.It.isAny()))
79+
.setup((i) => i.getInterpreterViaQuickPick(typemoq.It.isAny(), typemoq.It.isAny(), typemoq.It.isAny()))
8080
.returns(() => Promise.resolve(undefined))
8181
.verifiable(typemoq.Times.once());
8282

@@ -91,7 +91,7 @@ suite('venv Creation provider tests', () => {
9191
pickWorkspaceFolderStub.resolves(workspace1);
9292

9393
interpreterQuickPick
94-
.setup((i) => i.getInterpreterViaQuickPick(typemoq.It.isAny(), typemoq.It.isAny()))
94+
.setup((i) => i.getInterpreterViaQuickPick(typemoq.It.isAny(), typemoq.It.isAny(), typemoq.It.isAny()))
9595
.returns(() => Promise.resolve('/usr/bin/python'))
9696
.verifiable(typemoq.Times.once());
9797

@@ -105,7 +105,7 @@ suite('venv Creation provider tests', () => {
105105
pickWorkspaceFolderStub.resolves(workspace1);
106106

107107
interpreterQuickPick
108-
.setup((i) => i.getInterpreterViaQuickPick(typemoq.It.isAny(), typemoq.It.isAny()))
108+
.setup((i) => i.getInterpreterViaQuickPick(typemoq.It.isAny(), typemoq.It.isAny(), typemoq.It.isAny()))
109109
.returns(() => Promise.resolve('/usr/bin/python'))
110110
.verifiable(typemoq.Times.once());
111111

@@ -168,7 +168,7 @@ suite('venv Creation provider tests', () => {
168168
pickWorkspaceFolderStub.resolves(workspace1);
169169

170170
interpreterQuickPick
171-
.setup((i) => i.getInterpreterViaQuickPick(typemoq.It.isAny(), typemoq.It.isAny()))
171+
.setup((i) => i.getInterpreterViaQuickPick(typemoq.It.isAny(), typemoq.It.isAny(), typemoq.It.isAny()))
172172
.returns(() => Promise.resolve('/usr/bin/python'))
173173
.verifiable(typemoq.Times.once());
174174

@@ -225,7 +225,7 @@ suite('venv Creation provider tests', () => {
225225
pickWorkspaceFolderStub.resolves(workspace1);
226226

227227
interpreterQuickPick
228-
.setup((i) => i.getInterpreterViaQuickPick(typemoq.It.isAny(), typemoq.It.isAny()))
228+
.setup((i) => i.getInterpreterViaQuickPick(typemoq.It.isAny(), typemoq.It.isAny(), typemoq.It.isAny()))
229229
.returns(() => Promise.resolve('/usr/bin/python'))
230230
.verifiable(typemoq.Times.once());
231231

0 commit comments

Comments
 (0)