從 Docker 容器複製檔案到主機
在 Docker 1.8 之前,我們只能將檔案從容器複製到主機。但是,隨著容器變得更加流行,將檔案複製到容器中或從容器中複製檔案已成為必要。
我們可能想要從 docker 容器複製檔案的常見原因之一是與我們的團隊成員共享日誌檔案。但是,不允許複製/dev
、/proc
、/sys
、tmpfs
下的資源等敏感資訊。
本文將討論如何使用 DockerFile、docker cp
命令從 Docker 容器中複製檔案,並將目錄作為卷掛載到主機。
這需要正確安裝和配置 Docker 和 Docker 容器。這適用於 Linux 和 WSL 環境。
使用 docker cp
將檔案從 Docker 容器複製到主機
docker cp
命令是我們可以用來將檔案和目錄以及從主機複製到 docker 容器的最簡單方法之一。我們將使用 Ubuntu 20.4.5 和當時最新版本的 Docker,即 19.03。
語法:
$ docker cp [OPTIONS] CONTAINER: SRC_PATH DEST_PATH|-
其中,
SRC_PATH
指定我們要複製的檔案在主機上的源路徑。DEST_PATH
是在容器上儲存檔案的目標路徑。
使用此命令,我們可以通過交換引數 SRC_PATH
和 DEST_PATH
來將檔案複製到容器中或從容器中複製檔案。此命令的一個優點是我們可以將檔案和目錄複製到正在執行或已停止的容器中或從中複製。
docker cp
命令類似於 Unix cp -a
;因此,這意味著它還遞迴地複製目錄。此外,該命令還假定容器的所有路徑都相對於根目錄。
我們將首先建立我們的目標容器;因此,我們還需要一個映象。我們將使用 Docker 登錄檔中提供的官方 Ubuntu 映像。
$ docker pull ubuntu
然後,我們將以分離和互動模式建立一個 docker 容器。這允許我們的容器在後臺執行。
$ docker run -it -d ubuntu
e10b4a7bbc59131d30492a87dd70b8ea74fa686ed5036ec918b6596fc83efe2b
使用 exec
命令,我們將使用命令 docker exec
和 -it
標誌執行互動式 SSH 會話。這將允許我們在容器內互動地執行命令。
要建立一個簡單的文字檔案,我們將導航到 /usr/share
資料夾。
我們將首先使用相應的容器 ID 進入容器。
$ docker exec -it e10b4a7bbc59 /bin/bash
root@e10b4a7bbc59:/#
我們將導航容器內的資料夾 /usr/share/
以建立我們的文字檔案。
$ docker exec -it e10b4a7bbc59 /bin/bash
root@e10b4a7bbc59:/# cd usr
root@e10b4a7bbc59:/usr# cd share
root@e10b4a7bbc59:/usr/share#
我們將使用 touch
命令建立一個名為 new_file.txt
的檔案。我們將很快將此檔案從該容器複製到我們的主機。
因此,最好記下儲存檔案的目錄,因為我們將在將檔案複製到主機時使用該位置。
root@e10b4a7bbc59:/usr/share# touch new_file.txt
要驗證我們是否已建立檔案,請執行 ls
命令列出此目錄中的所有檔案,如下所示。
root@e10b4a7bbc59:/usr/share# ls
adduser bash-completion debianutils dpkg keyrings man pam polkit-1
apport bug dict gcc libc-bin menu pam-configs sensible-utils
base-files common-licenses doc gdb lintian misc perl5 tabset
base-passwd debconf doc-base info locale new_file.txt pixmaps terminfo
現在我們已經成功地在容器中建立了一個檔案,我們想將這個檔案從這個容器複製到我們的主機 - 使用 exit
命令從容器退出到主 shell。
我們將在終端中執行 docker cp
命令並將 new_file.txt
複製到主機的目錄中。但是,我們首先需要注意三個重要的事情:
- 容器標識;
- 目標檔案在容器中的位置;
- 我們將複製檔案的主機中的目標目錄。
$ docker cp e10b4a7bbc59:/usr/share/new_file.txt ./new_file.txt
通過執行該命令,我們已成功將 new._file.txt
複製到主機。我們可以通過在該特定資料夾中執行 ls
命令來驗證這一點。
isaac@DESKTOP-HV44HT6:~/isaac$ ls
adduser bash-completion debianutils dpkg keyrings man `new_file.txt` pixmaps terminfo
apport bug dict gcc libc-bin menu pam polkit-1
base-files common-licenses doc gdb lintian misc pam-configs sensible-utils
base-passwd debconf doc-base info locale my-app perl5 tabset
使用 Docker Mounts 將檔案從 Docker 容器複製到主機
我們還可以使用 docker mounts 將檔案從 docker 容器複製到主機。
繫結掛載是最早的解決方案之一,它允許我們通過將 docker 容器掛載到主機系統上的目錄來持久化資料。
繫結掛載允許我們通過引用目標目錄的絕對檔案路徑來引用確切的目錄。除了將檔案從容器複製到主機之外,我們還可以建立依賴於主機系統目錄的服務。
要建立 docker 掛載,我們可以在建立 docker 容器時使用 -v
或 --mount
標誌。除了這個標誌之外,我們還將指定我們想要對映到 docker 容器上的目錄的主機上的目錄。
這種方法通常是首選,因為我們可以在 docker 容器內建立多個掛載。我們還可以建立目錄來從多個容器傳輸檔案。
要將我們的目錄掛載到 docker 容器,我們必須指定以下欄位,這些欄位應始終以正確的順序由冒號分隔。這些包括:
- 我們要掛載的主機目錄的路徑;
- 我們應該掛載該目錄的容器中目錄的路徑;
- 其他可選選項如
ro
指定只讀模式。
語法:
docker run -t -i -v <host_dir>:<container_dir
在下面的示例中,我們使用 Ruby 官方映象來建立容器並將本地目錄掛載到容器上的目錄中。完成此操作後,我們可以輕鬆地將檔案從容器複製到本地目錄,反之亦然。
$ docker run -it -v $HOME/Desktop/new_container:/new_container --name new_container ruby bash
root@7a00af9d4d96:/#
我們可以輕鬆地在 docker 容器和主機目錄之間複製檔案。另外,請注意,在主機目錄中建立的檔案將自動在掛載到主機的 docker 容器目錄中可用。
使用 COPY
將檔案從 Docker 容器複製到主機
當使用 docker 檔案建立 docker 映象時,我們還可以使用 COPY
命令在 docker 主機和容器之間複製檔案。
語法:
COPY <SRC> <DEST>
在下面的 DockerFile 中,我們將 ./app.py
指定為源目錄,將 /var/www/app.py
指定為目標目錄。
# base image
FROM python
# Set your working directory
WORKDIR /var/www/
# Copy the necessary filesls
COPY ./app.py /var/www/app.py
COPY ./requirements.txt /var/www/requirements.txt
# Install the necessary packages
RUN pip install -r /var/www/requirements.txt
# Run the app
ENTRYPOINT ["echo", "Hello, Developer"]
這個 DockerFile 建立一個簡單的 Flask 應用程式的映象,該應用程式在控制檯上列印一條訊息。
Isaac Tony is a professional software developer and technical writer fascinated by Tech and productivity. He helps large technical organizations communicate their message clearly through writing.
LinkedIn