Skip to content

Commit 687c2f1

Browse files
committed
feat: nerdctl
Signed-off-by: thediveo <[email protected]>
1 parent e73276f commit 687c2f1

File tree

10 files changed

+348
-0
lines changed

10 files changed

+348
-0
lines changed

README.md

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,9 @@ Alpine](https://github.com/devcontainers/features/blob/091886b3568dad70f835cc428
1414
https://github.com/libbpf/bpftool binary releases, especially avoiding the
1515
usual pain of upstream Debian/Ubuntu kernel-specific bpftool packages.
1616

17+
- [cni-plugins](src/cni-plugins/README.md) – installs CNI plugins directly from
18+
upstream https://github.com/containernetworking/plugins binary releases.
19+
1720
- [docsify](src/docsify/README.md) – automatically serves ./docs workspace
1821
directory via `docsify serve` in the background (with the specific workspace
1922
location being configurable).
@@ -40,6 +43,9 @@ Alpine](https://github.com/devcontainers/features/blob/091886b3568dad70f835cc428
4043
- [local-pkgsite](src/local-pkgsite/README.md) – a local Go pkgsite serving the
4144
module documentation, with automatic project reload and browser refresh.
4245

46+
- [nerdctl](src/nerdctl/README.md) – installs `nerdctl` directly from upstream
47+
https://github.com/containerd/nerdctl binary releases.
48+
4349
- [pin-github-action](src/pin-github-action/README.md) – provides mheaps's
4450
`pin-github-action` for pinning GitHub actions to specific hashes.
4551

src/nerdctl/NOTES.md

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
## Combining with `docker-in-docker` Feature
2+
3+
Please note that the `docker-in-docker` feature is only available for
4+
Debian/Docker-based base images.
5+
6+
In order to use nerdctl with the `containerd` included in the
7+
[`docker-in-docker`](https://github.com/devcontainers/features/tree/main/src/docker-in-docker)
8+
feature, you need to explicitly configure the non-standard API endpoint URL for
9+
`containerd` as follows:
10+
11+
```json
12+
"features": {
13+
"ghcr.io/devcontainers/features/docker-in-docker:2": {
14+
"dockerDashComposeVersion": "none",
15+
"installDockerBuildx": false
16+
},
17+
"ghcr.io/devcontainers/features/nerdctl:0": {
18+
"containerd-api": "unix:///run/docker/containerd/containerd.sock"
19+
}
20+
}
21+
```
22+
23+
## OS Support
24+
25+
Tested with:
26+
- [ghcr.io/almalinux/almalinux](https://ghcr.io/almalinux/almalinux),
27+
- [mcr.microsoft.com/devcontainers/base:debian](https://mcr.microsoft.com/en-us/artifact/mar/devcontainers/base/about#about:_debian),
28+
- [fedora](https://hub.docker.com/_/fedora),
29+
- [mcr.microsoft.com/devcontainers/base:ubuntu](https://mcr.microsoft.com/en-us/artifact/mar/devcontainers/base/about#about:_ubuntu).
30+
31+
## Acknowledgement
32+
33+
[@containerd/nerdctl](https://github.com/containerd/nerdctl)

src/nerdctl/README.md

Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
2+
# containerd control CLI (nerdctl)
3+
4+
Installs nerdctl from upstream.
5+
6+
## Example Usage
7+
8+
```json
9+
"features": {
10+
"ghcr.io/thediveo/devcontainer-features/nerdctl:0": {}
11+
}
12+
```
13+
14+
## Options
15+
16+
| Options Id | Description | Type | Default Value |
17+
|-----|-----|-----|-----|
18+
| version | version of cni-plugins to install | string | latest |
19+
| containerd-api | path to containerd API endpoint | string | unix:///run/containerd/containerd.sock |
20+
21+
## Combining with `docker-in-docker` Feature
22+
23+
Please note that the `docker-in-docker` feature is only available for
24+
Debian/Docker-based base images.
25+
26+
In order to use nerdctl with the `containerd` included in the
27+
[`docker-in-docker`](https://github.com/devcontainers/features/tree/main/src/docker-in-docker)
28+
feature, you need to explicitly configure the non-standard API endpoint URL for
29+
`containerd` as follows:
30+
31+
```json
32+
"features": {
33+
"ghcr.io/devcontainers/features/docker-in-docker:2": {
34+
"dockerDashComposeVersion": "none",
35+
"installDockerBuildx": false
36+
},
37+
"ghcr.io/devcontainers/features/nerdctl:0": {
38+
"containerd-api": "unix:///run/docker/containerd/containerd.sock"
39+
}
40+
}
41+
```
42+
43+
## OS Support
44+
45+
Tested with:
46+
- [ghcr.io/almalinux/almalinux](https://ghcr.io/almalinux/almalinux),
47+
- [mcr.microsoft.com/devcontainers/base:debian](https://mcr.microsoft.com/en-us/artifact/mar/devcontainers/base/about#about:_debian),
48+
- [fedora](https://hub.docker.com/_/fedora),
49+
- [mcr.microsoft.com/devcontainers/base:ubuntu](https://mcr.microsoft.com/en-us/artifact/mar/devcontainers/base/about#about:_ubuntu).
50+
51+
## Acknowledgement
52+
53+
[@containerd/nerdctl](https://github.com/containerd/nerdctl)
54+
55+
56+
---
57+
58+
_Note: This file was auto-generated from the [devcontainer-feature.json](https://github.com/thediveo/devcontainer-features/blob/main/src/nerdctl/devcontainer-feature.json). Add additional notes to a `NOTES.md`._
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
{
2+
"name": "containerd control CLI",
3+
"id": "nerdctl",
4+
"version": "0.0.1",
5+
"description": "Installs nerdctl from upstream.",
6+
"options": {
7+
"version": {
8+
"type": "string",
9+
"default": "latest",
10+
"description": "version of cni-plugins to install"
11+
},
12+
"containerd-api": {
13+
"type": "string",
14+
"default": "unix:///run/containerd/containerd.sock",
15+
"description": "path to containerd API endpoint"
16+
}
17+
}
18+
}

src/nerdctl/install.sh

Lines changed: 169 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,169 @@
1+
#!/usr/bin/env bash
2+
3+
# Distribution and package manager detection are licensed by Microsoft
4+
# Corporation under the MIT License, please refer to:
5+
# https://github.com/devcontainers/features/blob/main/src/go/install.sh:
6+
#
7+
# Copyright (c) Microsoft Corporation. All rights reserved. Licensed under the
8+
# MIT License. See https://go.microsoft.com/fwlink/?linkid=2090316 for license
9+
# information
10+
11+
set -e
12+
13+
NERDCTL_VERSION="${VERSION:-"latest"}"
14+
CONTAINERD_API="${CONTAINERD_API:-"unix:///run/containerd/containerd.sock"}"
15+
16+
REPOSLUG="containerd/nerdctl"
17+
QUERYLATEST_URL="https://api.github.com/repos/${REPOSLUG}/releases/latest"
18+
RELEASE_URL="https://github.com/${REPOSLUG}/releases/download/"
19+
20+
echo "installing feature nerdctl..."
21+
22+
if [ "$(id -u)" -ne 0 ]; then
23+
echo -e 'Script must be run as root. Use sudo, su, or add "USER root" to your Dockerfile before running this script.'
24+
exit 1
25+
fi
26+
27+
# Bring in ID, ID_LIKE, VERSION_ID, VERSION_CODENAME
28+
. /etc/os-release
29+
# Get an adjusted ID independent of distro variants
30+
MAJOR_VERSION_ID=$(echo ${VERSION_ID} | cut -d . -f 1)
31+
if [ "${ID}" = "debian" ] || [ "${ID_LIKE}" = "debian" ]; then
32+
ADJUSTED_ID="debian"
33+
elif [[ "${ID}" = "rhel" || "${ID}" = "fedora" || "${ID}" = "mariner" || "${ID_LIKE}" = *"rhel"* || "${ID_LIKE}" = *"fedora"* || "${ID_LIKE}" = *"mariner"* ]]; then
34+
ADJUSTED_ID="rhel"
35+
if [[ "${ID}" = "rhel" ]] || [[ "${ID}" = *"alma"* ]] || [[ "${ID}" = *"rocky"* ]]; then
36+
VERSION_CODENAME="rhel${MAJOR_VERSION_ID}"
37+
else
38+
VERSION_CODENAME="${ID}${MAJOR_VERSION_ID}"
39+
fi
40+
else
41+
echo "Linux distro ${ID} not supported."
42+
exit 1
43+
fi
44+
45+
if [ "${ADJUSTED_ID}" = "rhel" ] && [ "${VERSION_CODENAME-}" = "centos7" ]; then
46+
# As of 1 July 2024, mirrorlist.centos.org no longer exists.
47+
# Update the repo files to reference vault.centos.org.
48+
sed -i s/mirror.centos.org/vault.centos.org/g /etc/yum.repos.d/*.repo
49+
sed -i s/^#.*baseurl=http/baseurl=http/g /etc/yum.repos.d/*.repo
50+
sed -i s/^mirrorlist=http/#mirrorlist=http/g /etc/yum.repos.d/*.repo
51+
fi
52+
53+
# Setup INSTALL_CMD & PKG_MGR_CMD
54+
if type apt-get > /dev/null 2>&1; then
55+
PKG_MGR_CMD=apt-get
56+
INSTALL_CMD="${PKG_MGR_CMD} -y install --no-install-recommends"
57+
elif type microdnf > /dev/null 2>&1; then
58+
PKG_MGR_CMD=microdnf
59+
INSTALL_CMD="${PKG_MGR_CMD} ${INSTALL_CMD_ADDL_REPOS} -y install --refresh --best --nodocs --noplugins --setopt=install_weak_deps=0"
60+
elif type dnf > /dev/null 2>&1; then
61+
PKG_MGR_CMD=dnf
62+
INSTALL_CMD="${PKG_MGR_CMD} ${INSTALL_CMD_ADDL_REPOS} -y install --refresh --best --nodocs --noplugins --setopt=install_weak_deps=0"
63+
else
64+
PKG_MGR_CMD=yum
65+
INSTALL_CMD="${PKG_MGR_CMD} ${INSTALL_CMD_ADDL_REPOS} -y install --noplugins --setopt=install_weak_deps=0"
66+
fi
67+
68+
# Clean up
69+
clean_up() {
70+
case ${ADJUSTED_ID} in
71+
debian)
72+
rm -rf /var/lib/apt/lists/*
73+
;;
74+
rhel)
75+
rm -rf /var/cache/dnf/* /var/cache/yum/*
76+
rm -rf /tmp/yum.log
77+
rm -rf ${GPG_INSTALL_PATH}
78+
;;
79+
esac
80+
}
81+
clean_up
82+
83+
pkg_mgr_update() {
84+
case $ADJUSTED_ID in
85+
debian)
86+
if [ "$(find /var/lib/apt/lists/* | wc -l)" = "0" ]; then
87+
echo "Running apt-get update..."
88+
${PKG_MGR_CMD} update -y
89+
fi
90+
;;
91+
rhel)
92+
if [ ${PKG_MGR_CMD} = "microdnf" ]; then
93+
if [ "$(ls /var/cache/yum/* 2>/dev/null | wc -l)" = 0 ]; then
94+
echo "Running ${PKG_MGR_CMD} makecache ..."
95+
${PKG_MGR_CMD} makecache
96+
fi
97+
else
98+
if [ "$(ls /var/cache/${PKG_MGR_CMD}/* 2>/dev/null | wc -l)" = 0 ]; then
99+
echo "Running ${PKG_MGR_CMD} check-update ..."
100+
set +e
101+
${PKG_MGR_CMD} check-update
102+
rc=$?
103+
if [ $rc != 0 ] && [ $rc != 100 ]; then
104+
exit 1
105+
fi
106+
set -e
107+
fi
108+
fi
109+
;;
110+
esac
111+
}
112+
113+
# Checks if packages are installed and installs them if not
114+
check_packages() {
115+
case ${ADJUSTED_ID} in
116+
debian)
117+
if ! dpkg -s "$@" > /dev/null 2>&1; then
118+
pkg_mgr_update
119+
${INSTALL_CMD} "$@"
120+
fi
121+
;;
122+
rhel)
123+
if ! rpm -q "$@" > /dev/null 2>&1; then
124+
pkg_mgr_update
125+
${INSTALL_CMD} "$@"
126+
fi
127+
;;
128+
esac
129+
}
130+
131+
case $(uname -m) in
132+
x86_64) ARCH="amd64";;
133+
aarch64 | armv8*) ARCH="arm64";;
134+
*) echo "Unsupported architecture: $(uname -m)"; exit 1;;
135+
esac
136+
137+
export DEBIAN_FRONTEND=noninteractive
138+
139+
if ! type curl > /dev/null 2>&1; then
140+
check_packages curl
141+
fi
142+
143+
if [ "$NERDCTL_VERSION" = "latest" ]; then
144+
# get latest release
145+
NERDCTL_VERSION=$(curl -s ${QUERYLATEST_URL} | grep '"tag_name":' | sed -E 's/.*"([^"]+)".*/\1/')
146+
fi
147+
148+
echo version: $NERDCTL_VERSION
149+
echo for arch: $ARCH
150+
151+
URL="${RELEASE_URL}${NERDCTL_VERSION}/nerdctl-${NERDCTL_VERSION#v}-linux-${ARCH}.tar.gz"
152+
echo "${URL}"
153+
154+
curl -sSL -o /tmp/nerdctl.tar.gz "${URL}"
155+
ls -lH /tmp/nerdctl.tar.gz
156+
tar xzof /tmp/nerdctl.tar.gz -C /usr/local/bin/ nerdctl
157+
chmod 0755 /usr/local/bin/nerdctl
158+
rm /tmp/nerdctl.tar.gz
159+
160+
mkdir -p /etc/nerdctl
161+
cat <<EOF >"/etc/nerdctl/nerdctl.toml"
162+
debug = false
163+
debug_full = false
164+
address = "${CONTAINERD_API}"
165+
EOF
166+
167+
clean_up
168+
169+
echo "Done!"

test/nerdctl/almalinux.sh

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
#!/usr/bin/env bash
2+
set -e
3+
4+
source dev-container-features-test-lib
5+
6+
check "nerdctl" bash -c "nerdctl --version"
7+
8+
reportResults

test/nerdctl/debian.sh

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
#!/usr/bin/env bash
2+
set -e
3+
4+
source dev-container-features-test-lib
5+
6+
# as we're combining this test with docker-in-docker, containerd's socket isn't
7+
# in its default location and we explicitly specify it in this feature's options
8+
# (whalewatchers: hold my beer...)
9+
check "nerdctl" bash -c "sudo nerdctl ps"
10+
11+
reportResults

test/nerdctl/fedora.sh

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
#!/usr/bin/env bash
2+
set -e
3+
4+
source dev-container-features-test-lib
5+
6+
# as we're combining this test with docker-in-docker, containerd's socket isn't
7+
# in its default location and we explicitly specify it in this feature's options
8+
# (whalewatchers: hold my beer...)
9+
check "nerdctl" bash -c "nerdctl --version"
10+
11+
reportResults

test/nerdctl/scenarios.json

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
{
2+
"almalinux": {
3+
"image": "ghcr.io/almalinux/almalinux:9",
4+
"features": {
5+
"nerdctl": {}
6+
}
7+
},
8+
"debian": {
9+
"image": "mcr.microsoft.com/devcontainers/base:debian-12",
10+
"features": {
11+
"ghcr.io/devcontainers/features/docker-in-docker:2": {
12+
"dockerDashComposeVersion": "none",
13+
"installDockerBuildx": false
14+
},
15+
"nerdctl": {
16+
"containerd-api": "unix:///run/docker/containerd/containerd.sock"
17+
}
18+
}
19+
},
20+
"fedora": {
21+
"image": "fedora",
22+
"features": {
23+
"nerdctl": {}
24+
}
25+
}
26+
}

test/nerdctl/test.sh

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
#!/usr/bin/env bash
2+
set -e
3+
4+
source dev-container-features-test-lib
5+
6+
check "nerdctl" bash -c "nerdctl --version"
7+
8+
reportResults

0 commit comments

Comments
 (0)