Skip to content

Commit 9662b9d

Browse files
committed
Support image source on darwin
Signed-off-by: Paweł Gronowski <[email protected]>
1 parent 20a30f2 commit 9662b9d

File tree

4 files changed

+32
-16
lines changed

4 files changed

+32
-16
lines changed

__tests__/docker/install.test.itg.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -41,8 +41,8 @@ aarch64:https://cloud.debian.org/images/cloud/bookworm/20231013-1532/debian-12-g
4141
});
4242
// prettier-ignore
4343
test.each([
44-
{type: 'archive', version: 'v26.1.4', channel: 'stable'} as InstallSourceArchive,
4544
{type: 'image', tag: '27.3.1'} as InstallSourceImage,
45+
{type: 'archive', version: 'v26.1.4', channel: 'stable'} as InstallSourceArchive,
4646
])(
4747
'install docker %s', async (source) => {
4848
if (process.env.ImageOS && process.env.ImageOS.startsWith('ubuntu')) {

src/docker/assets.ts

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -176,6 +176,8 @@ disk: 60GiB
176176
# This file: Mount the home as read-only, /tmp/lima as writable
177177
mounts:
178178
- location: "~"
179+
- location: {{toolDir}}
180+
mountPoint: /tool
179181
- location: "/tmp/lima"
180182
writable: true
181183
@@ -221,7 +223,17 @@ provision:
221223
EOF
222224
fi
223225
export DEBIAN_FRONTEND=noninteractive
224-
curl -fsSL https://get.docker.com | sh -s -- --channel {{dockerBinChannel}} --version {{dockerBinVersion}}
226+
if [ {{srcType}} == "archive" ]; then
227+
curl -fsSL https://get.docker.com | sh -s -- --channel {{srcArchiveChannel}} --version {{srcArchiveVersion}}
228+
elif [ {{srcType}} == "image" ]; then
229+
wget https://raw.githubusercontent.com/moby/moby/{{srcImageTag}}/contrib/init/systemd/docker.service \
230+
https://raw.githubusercontent.com/moby/moby/v{{srcImageTag}}/contrib/init/systemd/docker.service \
231+
-O /etc/systemd/system/docker.service || true
232+
sed -i 's|^ExecStart=.*|ExecStart=/tool/dockerd|' /etc/systemd/system/docker.service
233+
sed -i 's|containerd.service||' /etc/systemd/system/docker.service
234+
systemctl daemon-reload
235+
systemctl enable --now docker
236+
fi
225237
226238
probes:
227239
- script: |

src/docker/install.ts

Lines changed: 14 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -127,13 +127,16 @@ export class Install {
127127
const cli = await HubRepository.build('dockereng/cli-bin');
128128
extractFolder = await cli.extractImage(tag);
129129

130-
// Daemon is only available for Windows and Linux
131-
if (['win32', 'linux'].includes(platform)) {
130+
if (['win32', 'linux', 'darwin'].includes(platform)) {
132131
core.info(`Downloading dockerd from moby/moby-bin:${tag}`);
133132
const moby = await HubRepository.build('moby/moby-bin');
134-
await moby.extractImage(tag, extractFolder);
133+
134+
// On macOS, we extract the Linux version of dockerd which will be run in a lima VM.
135+
const extractPlatform = platform == 'darwin' ? 'linux' : undefined;
136+
137+
await moby.extractImage(tag, extractFolder, extractPlatform);
135138
} else {
136-
core.info(`dockerd not supported on ${platform}`);
139+
core.warning(`dockerd not supported on ${platform}, only the Docker cli will be available`);
137140
}
138141
break;
139142
}
@@ -192,10 +195,7 @@ export class Install {
192195
}
193196

194197
private async installDarwin(): Promise<string> {
195-
if (this.source.type !== 'archive') {
196-
throw new Error('Only archive source is supported on macOS');
197-
}
198-
const src = this.source as InstallSourceArchive;
198+
const src = this.source;
199199
const limaDir = path.join(os.homedir(), '.lima', this.limaInstanceName);
200200
await io.mkdirP(limaDir);
201201
const dockerHost = `unix://${limaDir}/docker.sock`;
@@ -226,12 +226,16 @@ export class Install {
226226
handlebars.registerHelper('stringify', function (obj) {
227227
return new handlebars.SafeString(JSON.stringify(obj));
228228
});
229+
const srcArchive = src as InstallSourceArchive;
229230
const limaCfg = handlebars.compile(limaYamlData)({
230231
customImages: Install.limaCustomImages(),
231232
daemonConfig: limaDaemonConfig,
232233
dockerSock: `${limaDir}/docker.sock`,
233-
dockerBinVersion: src.version.replace(/^v/, ''),
234-
dockerBinChannel: src.channel
234+
srcType: src.type,
235+
srcArchiveVersion: srcArchive.version?.replace(/^v/, ''),
236+
srcArchiveChannel: srcArchive.channel,
237+
srcImageTag: (src as InstallSourceImage).tag,
238+
toolDir: this.toolDir
235239
});
236240
core.info(`Writing lima config to ${path.join(limaDir, 'lima.yaml')}`);
237241
fs.writeFileSync(path.join(limaDir, 'lima.yaml'), limaCfg);

src/hubRepository.ts

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -42,12 +42,12 @@ export class HubRepository {
4242

4343
// Unpacks the image layers and returns the path to the extracted image.
4444
// Only OCI indexes/manifest list are supported for now.
45-
public async extractImage(tag: string, destDir?: string): Promise<string> {
45+
public async extractImage(tag: string, destDir?: string, osPlatform?: string): Promise<string> {
4646
const index = await this.getManifest<Index>(tag);
4747
if (index.mediaType != MEDIATYPE_IMAGE_INDEX_V1 && index.mediaType != MEDIATYPE_IMAGE_MANIFEST_LIST_V2) {
4848
throw new Error(`Unsupported image media type: ${index.mediaType}`);
4949
}
50-
const digest = HubRepository.getPlatformManifestDigest(index);
50+
const digest = HubRepository.getPlatformManifestDigest(index, osPlatform);
5151
const manifest = await this.getManifest<Manifest>(digest);
5252

5353
const paths = manifest.layers.map(async layer => {
@@ -115,9 +115,9 @@ export class HubRepository {
115115
return <T>JSON.parse(body);
116116
}
117117

118-
private static getPlatformManifestDigest(index: Index): string {
118+
private static getPlatformManifestDigest(index: Index, osPlatform?: string): string {
119119
// This doesn't handle all possible platforms normalizations, but it's good enough for now.
120-
let pos: string = os.platform();
120+
let pos: string = osPlatform || os.platform();
121121
if (pos == 'win32') {
122122
pos = 'windows';
123123
}

0 commit comments

Comments
 (0)