Skip to content
This repository was archived by the owner on Jul 20, 2026. It is now read-only.

Commit 62dcfc5

Browse files
authored
Add compose service startup CodeLenses, update vscode-docker-registries (#4432)
1 parent 3303668 commit 62dcfc5

5 files changed

Lines changed: 43 additions & 27 deletions

File tree

package-lock.json

Lines changed: 8 additions & 8 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3008,13 +3008,13 @@
30083008
"@azure/arm-authorization": "^9.0.0",
30093009
"@azure/arm-containerregistry": "^10.1.0",
30103010
"@azure/storage-blob": "^12.14.0",
3011-
"@microsoft/compose-language-service": "^0.2.0",
3011+
"@microsoft/compose-language-service": "^0.3.0",
30123012
"@microsoft/vscode-azext-azureappservice": "~3.3.0",
30133013
"@microsoft/vscode-azext-azureauth": "^2.4.1",
30143014
"@microsoft/vscode-azext-azureutils": "^3.0.1",
30153015
"@microsoft/vscode-azext-utils": "^2.5.1",
30163016
"@microsoft/vscode-container-client": "^0.1.2",
3017-
"@microsoft/vscode-docker-registries": "^0.1.12",
3017+
"@microsoft/vscode-docker-registries": "^0.1.13",
30183018
"dayjs": "^1.11.7",
30193019
"dockerfile-language-server-nodejs": "^0.13.0",
30203020
"fs-extra": "^11.1.1",

src/commands/compose/compose.ts

Lines changed: 16 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -12,11 +12,15 @@ import { quickPickWorkspaceFolder } from '../../utils/quickPickWorkspaceFolder';
1212
import { selectComposeCommand } from '../selectCommandTemplate';
1313
import { getComposeProfileList, getComposeProfilesOrServices, getComposeServiceList } from './getComposeSubsetList';
1414

15-
async function compose(context: IActionContext, commands: ('up' | 'down' | 'upSubset')[], message: string, dockerComposeFileUri?: vscode.Uri, selectedComposeFileUris?: vscode.Uri[]): Promise<void> {
15+
async function compose(context: IActionContext, commands: ('up' | 'down' | 'upSubset')[], message: string, dockerComposeFileUri?: vscode.Uri | string, selectedComposeFileUris?: vscode.Uri[], preselectedServices?: string[], preselectedProfiles?: string[]): Promise<void> {
1616
if (!vscode.workspace.isTrusted) {
1717
throw new UserCancelledError('enforceTrust');
1818
}
1919

20+
if (typeof dockerComposeFileUri === 'string') {
21+
dockerComposeFileUri = vscode.Uri.parse(dockerComposeFileUri);
22+
}
23+
2024
// If a file is chosen, get its workspace folder, otherwise, require the user to choose
2125
// If a file is chosen that is not in a workspace, it will automatically fall back to quickPickWorkspaceFolder
2226
const folder: vscode.WorkspaceFolder = (dockerComposeFileUri ? vscode.workspace.getWorkspaceFolder(dockerComposeFileUri) : undefined) ||
@@ -59,7 +63,7 @@ async function compose(context: IActionContext, commands: ('up' | 'down' | 'upSu
5963
);
6064

6165
// Add the service list if needed
62-
terminalCommand.command = await addServicesOrProfilesIfNeeded(context, folder, terminalCommand.command);
66+
terminalCommand.command = await addServicesOrProfilesIfNeeded(context, folder, terminalCommand.command, preselectedServices, preselectedProfiles);
6367

6468
const client = await ext.orchestratorManager.getClient();
6569
const taskCRF = new TaskCommandRunnerFactory({
@@ -72,12 +76,14 @@ async function compose(context: IActionContext, commands: ('up' | 'down' | 'upSu
7276
}
7377
}
7478

75-
export async function composeUp(context: IActionContext, dockerComposeFileUri?: vscode.Uri, selectedComposeFileUris?: vscode.Uri[]): Promise<void> {
79+
// The parameters of this function should not be changed without updating the compose language service which uses this command
80+
export async function composeUp(context: IActionContext, dockerComposeFileUri?: vscode.Uri | string, selectedComposeFileUris?: vscode.Uri[]): Promise<void> {
7681
return await compose(context, ['up'], vscode.l10n.t('Choose Docker Compose file to bring up'), dockerComposeFileUri, selectedComposeFileUris);
7782
}
7883

79-
export async function composeUpSubset(context: IActionContext, dockerComposeFileUri?: vscode.Uri, selectedComposeFileUris?: vscode.Uri[]): Promise<void> {
80-
return await compose(context, ['upSubset'], vscode.l10n.t('Choose Docker Compose file to bring up'), dockerComposeFileUri, selectedComposeFileUris);
84+
// The parameters of this function should not be changed without updating the compose language service which uses this command
85+
export async function composeUpSubset(context: IActionContext, dockerComposeFileUri?: vscode.Uri | string, selectedComposeFileUris?: vscode.Uri[], preselectedServices?: string[], preselectedProfiles?: string[]): Promise<void> {
86+
return await compose(context, ['upSubset'], vscode.l10n.t('Choose Docker Compose file to bring up'), dockerComposeFileUri, selectedComposeFileUris, preselectedServices, preselectedProfiles);
8187
}
8288

8389
export async function composeDown(context: IActionContext, dockerComposeFileUri?: vscode.Uri, selectedComposeFileUris?: vscode.Uri[]): Promise<void> {
@@ -90,18 +96,19 @@ export async function composeRestart(context: IActionContext, dockerComposeFileU
9096

9197
const serviceListPlaceholder = /\${serviceList}/i;
9298
const profileListPlaceholder = /\${profileList}/i;
93-
async function addServicesOrProfilesIfNeeded(context: IActionContext, workspaceFolder: vscode.WorkspaceFolder, command: string): Promise<string> {
99+
async function addServicesOrProfilesIfNeeded(context: IActionContext, workspaceFolder: vscode.WorkspaceFolder, command: string, preselectedServices: string[], preselectedProfiles: string[]): Promise<string> {
94100
const commandWithoutPlaceholders = command.replace(serviceListPlaceholder, '').replace(profileListPlaceholder, '');
101+
95102
if (serviceListPlaceholder.test(command) && profileListPlaceholder.test(command)) {
96103
// If both are present, need to ask
97-
const { services, profiles } = await getComposeProfilesOrServices(context, workspaceFolder, commandWithoutPlaceholders);
104+
const { services, profiles } = await getComposeProfilesOrServices(context, workspaceFolder, commandWithoutPlaceholders, preselectedServices, preselectedProfiles);
98105
return command
99106
.replace(serviceListPlaceholder, services)
100107
.replace(profileListPlaceholder, profiles);
101108
} else if (serviceListPlaceholder.test(command)) {
102-
return command.replace(serviceListPlaceholder, await getComposeServiceList(context, workspaceFolder, commandWithoutPlaceholders));
109+
return command.replace(serviceListPlaceholder, await getComposeServiceList(context, workspaceFolder, commandWithoutPlaceholders, preselectedServices));
103110
} else if (profileListPlaceholder.test(command)) {
104-
return command.replace(profileListPlaceholder, await getComposeProfileList(context, workspaceFolder, commandWithoutPlaceholders));
111+
return command.replace(profileListPlaceholder, await getComposeProfileList(context, workspaceFolder, commandWithoutPlaceholders, preselectedProfiles));
105112
} else {
106113
return command;
107114
}

src/commands/compose/getComposeSubsetList.ts

Lines changed: 16 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -13,13 +13,21 @@ const composeCommandReplaceRegex = /(\b(up|down)\b).*$/i;
1313

1414
type SubsetType = 'services' | 'profiles';
1515

16-
export async function getComposeProfilesOrServices(context: IActionContext, workspaceFolder: vscode.WorkspaceFolder, composeCommand: string): Promise<{ services: string | undefined, profiles: string | undefined }> {
16+
export async function getComposeProfilesOrServices(context: IActionContext, workspaceFolder: vscode.WorkspaceFolder, composeCommand: string, preselectedServices?: string[], preselectedProfiles?: string[]): Promise<{ services: string | undefined, profiles: string | undefined }> {
1717
const profiles = await getServiceSubsets(workspaceFolder, composeCommand, 'profiles');
1818

19+
if (preselectedServices?.length && preselectedProfiles?.length) {
20+
throw new Error(vscode.l10n.t('Cannot specify both services and profiles to start. Please choose one or the other.'));
21+
}
22+
1923
// If there any profiles, we need to ask the user whether they want profiles or services, since they are mutually exclusive to use
2024
// Otherwise, if there are no profiles, we'll automatically assume services
2125
let useProfiles = false;
22-
if (profiles?.length) {
26+
if (preselectedProfiles?.length) {
27+
useProfiles = true;
28+
} else if (preselectedServices?.length) {
29+
useProfiles = false;
30+
} else if (profiles?.length) {
2331
const profilesOrServices: IAzureQuickPickItem<SubsetType>[] = [
2432
{
2533
label: vscode.l10n.t('Services'),
@@ -35,12 +43,12 @@ export async function getComposeProfilesOrServices(context: IActionContext, work
3543
}
3644

3745
return {
38-
profiles: useProfiles ? await getComposeProfileList(context, workspaceFolder, composeCommand, profiles) : '',
39-
services: !useProfiles ? await getComposeServiceList(context, workspaceFolder, composeCommand) : '',
46+
profiles: useProfiles ? await getComposeProfileList(context, workspaceFolder, composeCommand, profiles, preselectedProfiles) : '',
47+
services: !useProfiles ? await getComposeServiceList(context, workspaceFolder, composeCommand, preselectedServices) : '',
4048
};
4149
}
4250

43-
export async function getComposeProfileList(context: IActionContext, workspaceFolder: vscode.WorkspaceFolder, composeCommand: string, prefetchedProfiles?: string[]): Promise<string> {
51+
export async function getComposeProfileList(context: IActionContext, workspaceFolder: vscode.WorkspaceFolder, composeCommand: string, prefetchedProfiles?: string[], preselectedProfiles?: string[]): Promise<string> {
4452
const profiles = prefetchedProfiles ?? await getServiceSubsets(workspaceFolder, composeCommand, 'profiles');
4553

4654
if (!profiles?.length) {
@@ -51,15 +59,15 @@ export async function getComposeProfileList(context: IActionContext, workspaceFo
5159
// Fetch the previously chosen profiles list. By default, all will be selected.
5260
const workspaceProfileListKey = `vscode-docker.composeProfiles.${workspaceFolder.name}`;
5361
const previousChoices = ext.context.workspaceState.get<string[]>(workspaceProfileListKey, profiles);
54-
const result = await pickSubsets(context, 'profiles', profiles, previousChoices);
62+
const result = preselectedProfiles?.length ? preselectedProfiles : await pickSubsets(context, 'profiles', profiles, previousChoices);
5563

5664
// Update the cache
5765
await ext.context.workspaceState.update(workspaceProfileListKey, result);
5866

5967
return result.map(p => `--profile ${p}`).join(' ');
6068
}
6169

62-
export async function getComposeServiceList(context: IActionContext, workspaceFolder: vscode.WorkspaceFolder, composeCommand: string): Promise<string> {
70+
export async function getComposeServiceList(context: IActionContext, workspaceFolder: vscode.WorkspaceFolder, composeCommand: string, preselectedServices?: string[]): Promise<string> {
6371
const services = await getServiceSubsets(workspaceFolder, composeCommand, 'services');
6472

6573
if (!services?.length) {
@@ -70,7 +78,7 @@ export async function getComposeServiceList(context: IActionContext, workspaceFo
7078
// Fetch the previously chosen services list. By default, all will be selected.
7179
const workspaceServiceListKey = `vscode-docker.composeServices.${workspaceFolder.name}`;
7280
const previousChoices = ext.context.workspaceState.get<string[]>(workspaceServiceListKey, services);
73-
const result = await pickSubsets(context, 'services', services, previousChoices);
81+
const result = preselectedServices?.length ? preselectedServices : await pickSubsets(context, 'services', services, previousChoices);
7482

7583
// Update the cache
7684
await ext.context.workspaceState.update(workspaceServiceListKey, result);

src/utils/AlternateYamlLanguageServiceClientFeature.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,7 @@ export class AlternateYamlLanguageServiceClientFeature implements StaticFeature,
3030
advancedCompletions: false, // YAML extension does not have advanced completions for compose docs
3131
hover: false, // YAML extension provides hover, but the compose spec lacks descriptions -- https://github.com/compose-spec/compose-spec/issues/138
3232
imageLinks: false, // YAML extension does not have image hyperlinks for compose docs
33+
serviceStartupCodeLens: false, // YAML extension does not have service startup code lens for compose docs
3334
formatting: true,
3435
};
3536

0 commit comments

Comments
 (0)