Docker Exec:您在 Docker 中運行命令的首選命令


你曾經需要查看Docker容器內部發生了什麼嗎?容器應該是幂等的:如果出了問題,重新部署一個新容器。然而,現實生活往往並不那麼簡單。您需要在容器中運行命令來識別問題所在。這就是docker exec命令發揮作用的地方。

本文將教您如何使用docker exec命令在運行中的Docker容器上運行命令。

先決條件

要按照本文中的示例進行操作,您需要遵循以下步驟。

  • 任何最近版本的Docker Desktop都可以在Windows、Linux或macOS上運行。本教程使用在Windows 10上運行的v3.1.0版本。

啟動一個NGINX容器

Docker exec在容器中運行命令。但是,要做到這一點,您必須首先有一個容器來運行這些命令。讓我們從下載Docker映像並創建演示容器開始。

  1. 創建一個新目錄,本教程使用C:\gitrepos\test,用於保存用於容器的文件。

2. 創建一個名為 dockerfile(無擴展名) 的文件,其中包含以下代碼。 Dockerfile 定義了創建容器所需的步驟。

FROM nginx:alpine
 COPY index.html /usr/share/nginx/html/index.html

3. 接下來,在同一目錄中創建一個名為 index.html 的文件,其中包含以下代碼。 這是一個 HTML 文件,當容器啟動時,將顯示一條 Hello World 消息。

<!DOCTYPE html> 
<html lang="en"> 
<head> 
    <meta charset="UTF-8"> 
    <meta name="viewport" content="width=device-width, initial-scale=1.0"> 
    <meta http-equiv="X-UA-Compatible" content="ie=edge"> 
    <title>Hello World - Nginx Docker</title> 
    <style> 
       h1{ font-weight:lighter; font-family: Arial, Helvetica, sans-serif; 
       } 
    </style> 
    </head> 
    <body> 
       <h1> 
          Hello World 
       </h1> 

    </body> 
    </html>

4. 現在創建 Nginx Docker 容器。 由於 Dockerfile 在當前工作目錄中,請使用 指定該目錄,以便讓 Docker 引擎知道在那裡查找。 還要確保使用 t 參數為容器標記為 my-ngnix,以便將來更輕鬆地引用。

docker build -t my-nginx .
Creating a Docker container with the build command.

5. 現在容器已經建立,使用 Docker run 命令啟動容器。

# rm - 通知 Docker 在停止後刪除容器 
# d - 在命令執行後返回控制台 
# p - 將內部容器端口 80 映射到外部端口 80 docker run --rm -d -p 80:80 my-nginx
Start the container with the Docker run command.

6. 最後,打開您的 Web 瀏覽器,並訪問 http://localhost/ 以查看以下內容。

Output of the running NGINX container.

使用 Docker Exec 命令執行命令

在Docker容器中运行命令时,可能需要以交互方式执行。交互式命令意味着输入一个命令,获取反馈,输入另一个命令等。交互式命令接管了您的会话,阻止您执行其他操作。

但是,如果您已经提前知道要发送到容器的命令,并且想要在后台运行命令怎么办?在这种情况下,您可以运行非交互式命令。非交互式命令允许您发送命令给Docker,并立即返回对控制台的控制。

定位容器的名称和ID

现在,您已经构建了容器,可以在容器内执行命令。在运行命令之前,找到NGINX容器的名称或ID。在Docker命令中,名称或ID都可以使用。考虑到这一点,记住ID可能比记住名称更具挑战性!

要显示任何运行中容器的信息,请运行Docker ps命令以输出以下信息。

docker ps
Displaying running Docker containers.

将唯一ID e17e4b6be01a 或随机生成的名称 mystifying_chandrasekhar 复制到剪贴板以备后用。

使用Docker Exec运行非交互式命令

作为运行非交互式命令的示例,请复制并运行以下命令,以返回/var/log目录中文件的列表,使用ls -l命令。将容器名称 mystifying_chandrasekhar 之后的所有内容传递给Docker exec命令。

docker exec mystifying_chandrasekhar ls -l /var/log
Executing a directory listing within the NGINX container.

使用Docker命令避免控制台輸出

通過立即將 shell 控制返回給用戶,大型操作可以避免將控制台綁定。使用分離的 d 選項放棄控制台輸出。下面的命令通過容器中的 touch 命令創建文件 /tmp/execWorks,並且不在控制台上顯示任何輸出。

docker exec -d mystifying_chandrasekhar touch /tmp/execWorks

使用Docker Exec執行互動命令

到目前為止,您已經了解了如何使用 docker exec 在 Docker 容器中運行非互動命令。但是,您可能會遇到必須排除容器故障的情況,例如,當您需要互動式地向容器發出命令時。在這種情況下,您需要互動式地運行命令。

使用 docker exec 互動運行命令需要兩個選項,即 iti 選項保持 STDIN 開放,允許向容器發送命令,而 t 選項則分配了一個 虛擬TTY(PTY),一個通訊通道,用於輸入命令。

複製並粘貼以下命令以打開運行中的 Docker 容器的互動式命令提示符,使用 Bourne(sh)shell,如提示符更改為 /#

docker exec -it mystifying_chandrasekhar sh
Running an interactive Docker shell.

一旦進入 shell,現在運行以下命令以示範從容器內部列出文件。最後,運行 exit 命令離開互動式 shell。

ls -l /var/log
exit
Open an interactive command prompt to the container.

要在特定目錄中開啟一個互動提示,傳遞路徑到w選項告訴Docker在指定的目錄啟動shell。

將環境變量傳遞給正在運行的容器

許多程序使用環境變量在啟動時設置配置。例如,大多數Java應用程序要求將JAVA_HOME環境變量設置為Java路徑。

您可以使用e選項傳遞環境變量給會話。例如,也許您需要將一個名為MYVAR的環境變量填充到運行中的容器。為此,使用e選項並提供MYVAR="<某個值>"的鍵/值對,如下所示。

docker exec -it -e MYVAR="hello" mystifying_chandrasekhar sh
echo $MYVAR
Pass environment variables

通過文件傳遞環境變量

如果您有許多環境變量或共享配置,將這些變量存儲在文件中可能更容易。通過相對或絕對路徑將文件傳遞給Docker,使用--env-file選項。這種技術經常用於向容器提供安全憑證。切勿將憑證提交到版本控制!

創建一個名為env-vars.txt的文本文件,其中包含要傳遞的環境變量及其值。這個文件可以隨你喜歡命名,不需要.txt文件擴展名。

Text file with environmental variables defined.

使用env-file選項將環境變量傳遞給Docker。使用下面截圖中顯示的echo命令驗證變量是否可用。

# 傳遞 env-vars.txt 檔案並打開交互提示
docker exec -it --env-file env-vars.txt mystifying_chandrasekhar sh
# 驗證 Docker 容器中是否可用環境變數
echo $MYVAR
echo $FOO
echo $SOMETHING
Passing a environmental variables file to Docker and verifying the environment variables exist in the container.

以不同使用者身分互動與運行容器

在生產中,應用程式通常以特定使用者身分運行,以限制其訪問權限。如果在生產中以特定使用者運行應用程式,則在測試命令時也應該如此。

在此示例中,Docker 容器以 nginx 使用者身分運行。將使用者傳遞給 w 選項,告訴 Docker 以 nginx 帳戶啟動容器。在容器內運行的 whoami 命令確認確實使用了 nginx 使用者。

docker exec -it -u nginx mystifying_chandrasekhar sh
whoami
Running the container as the nginx user.

下一步

您已經學會了如何使用 docker exec 命令在運行的容器內執行命令。利用 exec 命令進入和查詢運行中的容器,您在解決 Docker 容器問題時擁有了一個強大的新工具。

現在試著更進一步,使用 Git 版本控制將靜態網站拉入容器,而不是複製單個文件。如果 Git 對您是新的,那麼文章 Visual Studio Code 和 Git 的初學者指南 是一個很好的起點。

Source:
https://adamtheautomator.com/docker-exec/