Skip to content

Commit 5216f9a

Browse files
authored
Fix support for project name attribute (#831) (#833)
1 parent 85499b3 commit 5216f9a

File tree

8 files changed

+72
-4
lines changed

8 files changed

+72
-4
lines changed

CHANGELOG.md

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,9 @@ Notable changes.
44

55
## May 2024
66

7+
### [0.62.0]
8+
- Fix support for project name attribute. (https://github.com/devcontainers/cli/issues/831)
9+
710
### [0.61.0]
811
- Use --depth 1 to make dotfiles install process faster (https://github.com/devcontainers/cli/pull/830)
912
- Enable --cache-to and --cache-from in devcontainer up (https://github.com/devcontainers/cli/pull/813)

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
{
22
"name": "@devcontainers/cli",
33
"description": "Dev Containers CLI",
4-
"version": "0.61.0",
4+
"version": "0.62.0",
55
"bin": {
66
"devcontainer": "devcontainer.js"
77
},

src/spec-node/dockerCompose.ts

Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -653,8 +653,18 @@ export async function getProjectName(params: DockerCLIParameters | DockerResolve
653653
throw err;
654654
}
655655
}
656-
if (composeConfig?.name) {
657-
return toProjectName(composeConfig.name, newProjectName);
656+
for (let i = composeFiles.length - 1; i >= 0; i--) {
657+
try {
658+
const fragment = yaml.load((await cliHost.readFile(composeFiles[i])).toString()) || {} as any;
659+
if (fragment.name) {
660+
return toProjectName(fragment.name, newProjectName);
661+
}
662+
} catch (error) {
663+
// fallback when parsing fails due to custom yaml tags (e.g., !reset)
664+
if (composeConfig?.name && composeConfig.name !== 'devcontainer') {
665+
return toProjectName(composeConfig.name, newProjectName);
666+
}
667+
}
658668
}
659669
const configDir = workspace.configFolderPath;
660670
const workingDir = composeFiles[0] ? cliHost.path.dirname(composeFiles[0]) : cliHost.cwd; // From https://github.com/docker/compose/blob/79557e3d3ab67c3697641d9af91866d7e400cfeb/compose/config/config.py#L290

src/test/cli.up.test.ts

Lines changed: 27 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -92,7 +92,7 @@ describe('Dev Containers CLI', function () {
9292
assert.equal(upResult!.outcome, 'success');
9393
});
9494
});
95-
describe('for docker-compose with image without features with custom project name', () => {
95+
describe('for minimal docker-compose with custom project name', () => {
9696
let upResult: UpResult | null = null;
9797
const testFolder = `${__dirname}/configs/compose-with-name`;
9898
before(async () => {
@@ -105,6 +105,32 @@ describe('Dev Containers CLI', function () {
105105
assert.equal(upResult!.composeProjectName, 'custom-project-name');
106106
});
107107
});
108+
describe('for minimal docker-compose with custom project name and custom yaml', () => {
109+
let upResult: UpResult | null = null;
110+
const testFolder = `${__dirname}/configs/compose-with-name-and-custom-yaml`;
111+
before(async () => {
112+
// build and start the container
113+
upResult = await devContainerUp(cli, testFolder, { 'logLevel': 'trace', extraArgs: `--docker-compose-path trigger-compose-v2` });
114+
});
115+
after(async () => await devContainerDown({ composeProjectName: upResult?.composeProjectName }));
116+
it('should succeed', () => {
117+
assert.equal(upResult!.outcome, 'success');
118+
assert.equal(upResult!.composeProjectName, 'custom-project-name-custom-yaml');
119+
});
120+
});
121+
describe('for minimal docker-compose without custom project name', () => {
122+
let upResult: UpResult | null = null;
123+
const testFolder = `${__dirname}/configs/compose-without-name`;
124+
before(async () => {
125+
// build and start the container
126+
upResult = await devContainerUp(cli, testFolder, { 'logLevel': 'trace', extraArgs: `--docker-compose-path trigger-compose-v2` });
127+
});
128+
after(async () => await devContainerDown({ composeProjectName: upResult?.composeProjectName }));
129+
it('should succeed', () => {
130+
assert.equal(upResult!.outcome, 'success');
131+
assert.equal(upResult!.composeProjectName, 'compose-without-name_devcontainer');
132+
});
133+
});
108134

109135
// Additional tests to verify the handling of persisted files
110136
describe('for docker-compose with Dockerfile with features', () => {
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
{
2+
"dockerComposeFile": "docker-compose.yml",
3+
"service": "app",
4+
"workspaceFolder": "/workspace"
5+
}
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
version: '3.8'
2+
3+
name: custom-project-name-custom-yaml
4+
5+
services:
6+
app:
7+
image: ubuntu:latest
8+
ports: !reset []
9+
volumes:
10+
- ..:/workspace:cached
11+
command: sleep infinity
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
{
2+
"dockerComposeFile": "docker-compose.yml",
3+
"service": "app",
4+
"workspaceFolder": "/workspace"
5+
}
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
version: '3.8'
2+
3+
services:
4+
app:
5+
image: ubuntu:latest
6+
volumes:
7+
- ..:/workspace:cached
8+
command: sleep infinity

0 commit comments

Comments
 (0)