如何在我終止 Docker 容器時執行指令碼?


簡介

在容器終止時執行指令碼是指在停止或移除 Docker 容器時執行指令碼或命令的過程。這在各種場景中都非常有用,例如清理資源、記錄資訊或觸發其他操作。

容器終止是指停止或移除 Docker 容器的過程。這可以使用 docker stop 或 docker rm 命令手動完成,也可以透過使用容器編排工具或容器生命週期管理功能自動完成。

示例 1:ONBUILD

要使用 **ONBUILD** Dockerfile 命令在容器終止時執行指令碼,請按照以下步驟操作:

  • 為將用作容器基礎的映象建立一個 Dockerfile。在 Dockerfile 中,使用 **ONBUILD** 命令指定要在容器終止時執行的指令碼或命令。

FROM alpine:3.11

ONBUILD RUN echo "Container terminated" >> /tmp/terminated.log
  • 使用 **docker build** 命令構建映象。將 **<image_name>** 替換為所需的映象名稱。

$ docker build -t <image_name> .
  • 為基於包含 **ONBUILD** 命令的映象的容器建立一個 Dockerfile。在 Dockerfile 中,使用 **FROM** 命令指定包含 **ONBUILD** 命令的映象作為基礎映象。

FROM <image_name> 
  • 使用 **docker build** 命令構建容器。將 <container_name> 替換為所需的容器名稱。

$ docker build -t <container_name> . 
  • 使用 **docker run** 命令執行容器。將 **<container_name>** 替換為您在上一步中構建的容器的名稱。

$ docker run <container_name> 

當您停止或移除容器時,將執行 **ONBUILD** 命令中指定的指令碼或命令。在此示例中,指令碼將訊息“容器已終止”寫入 **/tmp/terminated.log** 檔案。

示例 2:HEALTHCHECK

要使用 **HEALTHCHECK** Dockerfile 命令在容器終止時執行指令碼,請按照以下步驟操作:

  • 為將用作容器基礎的映象建立一個 Dockerfile。在 Dockerfile 中,使用 **HEALTHCHECK** 命令指定定期執行以檢查容器執行狀況的指令碼或命令。該指令碼或命令應設計為檢測容器何時停止或被移除,如果出現這種情況,則以非零狀態碼退出。

FROM alpine:3.11

HEALTHCHECK --interval=5s --timeout=3s \
  CMD [ -f /tmp/terminated ] || exit 1
  • 使用 **docker build** 命令構建映象。將 **<image_name>** 替換為所需的映象名稱。

$ docker build -t <image_name> . 
  • 為基於包含 **HEALTHCHECK** 命令的映象的容器建立一個 Dockerfile。在 Dockerfile 中,使用 **FROM** 命令指定包含 **HEALTHCHECK** 命令的映象作為基礎映象。

FROM <image_name> 
  • 使用 **docker build** 命令構建容器。將 <container_name> 替換為所需的容器名稱。

$ docker build -t <container_name> .
  • 使用 **docker run** 命令執行容器。將 <container_name> 替換為您在上一步中構建的容器的名稱。

$ docker run <container_name> 

當您停止或移除容器時,將定期執行 **HEALTHCHECK** 命令中指定的指令碼或命令。如果指令碼或命令以非零狀態碼退出,則容器將被視為不健康,並將被停止或移除。在此示例中,指令碼將檢查 **/tmp/terminated** 檔案是否存在,如果存在則以非零狀態碼退出。

示例 3:--init 標誌

要使用 **--init** 標誌在容器終止時執行指令碼,請按照以下步驟操作:

  • 建立要在容器終止時執行的指令碼或命令。該指令碼或命令應設計為執行為 init 系統,並應處理諸如 **SIGTERM** 和 **SIGINT** 等訊號,以檢測容器何時被停止或移除。

#!/bin/bash

echo "Starting init system"

trap "echo 'Received signal to terminate'; exit 0" SIGTERM SIGINT

while true; do
  sleep 1
done
  • 將指令碼或命令儲存到檔案,並使用 **chmod** 命令使其可執行。

$ chmod +x myscript.sh 
  • 為將用作容器基礎的映象建立一個 Dockerfile。在 Dockerfile 中,使用 **COPY** 命令將指令碼或命令檔案複製到容器。

FROM alpine:3.11

COPY myscript.sh /usr/local/bin/myscript
  • 使用 **docker build** 命令構建映象。將 <image_name> 替換為所需的映象名稱。

$ docker build -t <image_name> .
  • 使用 **docker run** 命令執行容器,並使用 --init 標誌在容器中執行 init 系統。將 <image_name> 替換為您在上一步中構建的映象的名稱,並將 <container_name> 替換為所需的容器名稱。

$ docker run --init --name <container_name> <image_name> 

當您停止或移除容器時,將執行 **--init** 標誌中指定的 init 系統。init 系統將處理諸如 **SIGTERM** 和 **SIGINT** 等訊號,以檢測容器何時被停止或移除,並將執行相應的操作。在此示例中,init 系統將訊息“收到終止訊號”寫入控制檯,然後以狀態碼 0 退出。

結論

在本文中,我們瞭解瞭如何在容器終止時執行指令碼。我們瞭解到,有多種方法可以在容器終止時執行指令碼,例如 **ONBUILD** 和 **HEALTHCHECK** Dockerfile 命令以及 **--init** 標誌。我們還看到了如何使用每種選項的示例,並討論了選擇正確選項以及最佳化指令碼執行的效能和可靠性的最佳實踐。

更新於:2023年2月17日

2K+ 次瀏覽

啟動您的 職業生涯

透過完成課程獲得認證

開始學習
廣告