🚀 在 VS Code 中

在容器啟動時啟動程序

當您在開發容器中工作時,您可能希望在每次容器啟動時執行命令或啟動某些內容。最簡單的方法是使用 devcontainer.json 中的 postStartCommand 屬性。例如,如果您希望每次連線到容器時都執行 yarn install 以保持依賴套件為最新狀態,您可以新增以下內容

"postStartCommand": "yarn install"

影片:在容器建立時執行 npm install



在其他情況下,您可能想要啟動一個程序並保持其執行。這可以使用 nohup 並使用 & 將程序放入背景來完成。例如

"postStartCommand": "nohup bash -c 'your-command-here &'"

影片:在容器啟動時執行 'npm start'



熟悉 Linux 的使用者可能會期望能夠使用 systemctl 命令來啟動和停止由名為 systemd 的系統管理的背景服務。不幸的是,systemd 有額外的負擔,因此通常不適用於容器。

在許多情況下,您可以改為執行命令(例如,sshd)。在 Debian/Ubuntu 上,通常在 /etc/init.d 下有您可以直接執行的腳本。

"postStartCommand": "/etc/init.d/ssh start"

這些系統也包含一個 service 命令,它將根據安裝的內容使用 systemctl/etc/init.d 腳本。

"postStartCommand": "service ssh start"

影片:在容器中啟動 SSH 服務

改為將啟動命令新增至 Docker 映像檔

雖然 postStartCommand 很方便,並允許您在原始碼樹狀結構中執行命令,但您也可以改為使用自訂 ENTRYPOINTCMD,將這些步驟新增至 Dockerfile。

當在 devcontainer.json 中參考 Dockerfile 時,預設的 entrypoint 和 command 會被覆寫。首先,使用 overrideCommand 屬性停用此行為。

"overrideCommand": false

overrideCommand 屬性預設為 true,因為許多映像檔在未指定命令時會立即結束。相反地,我們需要在 Dockerfile 中處理此問題。

接下來,請考慮這個 Dockerfile

FROM mcr.microsoft.com/devcontainers/base:1-ubuntu

COPY docker-entrypoint.sh /
RUN chmod +x /docker-entrypoint.sh
ENTRYPOINT [ "/docker-entrypoint.sh" ]
CMD [ "sleep", "infinity" ]

此處的 CMD 可確保容器預設保持執行。將您的啟動步驟保留在 ENTRYPOINT 中,可讓您在使用 docker run 搭配您的映像檔或使用 Docker Compose 時,安全地覆寫命令。這會解析為以下內容

/docker-entrypoint.sh sleep infinity

接下來,建立一個 docker-entrypoint.sh 腳本

#!/usr/bin/env bash

echo "Hello from our entrypoint!"

exec "$@"

您在此檔案中執行的任何內容都會在每次容器啟動時觸發。但是,務必包含最後一行 exec "$@",因為這會導致範例中的 sleep infinity 命令觸發。

最後,如果您使用 Docker Compose,請確保您的容器未設定 entrypointcommand 屬性。