Docker之主機拷貝檔案到docker映象容器
上一篇《Docker之自定義映象製作與執行(一)》我們已經知道怎麼執行自定義映象了,但是我們的專案執行環境一般都是會帶有配置檔案的,那麼這麼將這些配置檔案拷貝到映象中呢?我們就來實踐一下:
首先啟動自定義映象容器:jpress
docker run -d -p 8888:8080 jpress
檢視容器程序
docker ps
進入容器內部
至此,我們已經看到容器內部的情況了,接下來我們把自己自定義的檔案拷貝到/usr/local 目錄下,首先我們看下/usr/local目錄下有哪些檔案
cd /usr/local
拷貝單個檔案到docker容器中:
因為我的系統是Windows的,所以在F盤下建立一個檔案copy.txt,內容為:
之前安裝docker是我安裝在D:\java_dev目錄下的,可以在docker終端檢視
那麼我們就要先把docker終端目錄切換到F盤下:
我們已經看到了copy.txt的檔案了,接下來就準備將這個檔案拷貝到容器的/usr/local目錄下
docker cp copy.txt 7a25b276ce7e:/usr/local/
說明一下:7a25b276ce7e是指Jpress容器的ID或者name
然後我們再看一下docker容器中是不是多了一個copy.txt檔案
我們看到jpress容器已經在第二次執行的時候多了一個copy.txt檔案了,那麼我們來檢視是不是確實是我們主機上的檔案呢?
cat copy.txt
可以看出就是我本機上的檔案,為什麼會出現不一樣呢,那是因為cat顯示中文異常問題,小夥伴可以通過設定cat編碼集解決。
拷貝資料夾到docker容器中:
首先我們還是在F盤中有一個logs資料夾,裡面有相關日誌的幾個檔案
然後還是在docker終端切換到F盤下,執行命令
docker cp logs 7a25b276ce7e:/usr/local/
然後我們看下/usr/local/目錄下是否拷貝成功
可以看到我們已經把檔案成功的拷貝到/usr/local目錄下面了。
注意:通過上面的方法將檔案拷貝到容器有一個很大的缺點,那就是當容器stop之後,然後再啟動執行,之前拷貝的檔案都已經不存在了,這個是為什麼呢?
Docker映象是由多個檔案系統
(只讀層)疊加而成.當我們啟動一個容器的時候,Docker會載入映象層並在其上新增一個讀寫層.如果執行中的容器修改了現有的一個已存在的檔案,那該檔案將會從讀寫層下的只讀層複製到讀寫層,該檔案的只讀版本仍然存在,只是已經被讀寫層中該檔案的副本所隱藏.當刪除Docker容器,並通過該映象重新啟動時,之前的更改將會丟失.在Docker中,只讀層以及在頂部的讀寫層的組合被稱為Union File System(聯合檔案系統)解決方案:通過Docker Volume修改docker的檔案掛載,後續我會說明怎麼使用它。
第二種拷貝檔案方案:
那有沒有什麼可以直接一點呢?當然有,那就是在構建的時候就拷貝進去,那麼就需要修改Dockerfile 檔案,我們來操作一下。
首先我們把之前的docker容器服務停止一下
我們先把之前的copy.txt和logs檔案拷貝到Dockerfile檔案目錄下,這樣便於檔案拷貝,該檔案在docker預設安裝目錄下:
然後我們來編輯Dockerfile檔案
vi Dockerfile
接下來就是重新構建映象
docker build -t jpress:latest .
由於我本地已經把jpress.war檔案刪除了,所以構建失敗,但是正因為失敗,我們可以發現為什麼之前拷貝的檔案在重啟之後會消失,因為映象容器是構建在/tmp 臨時檔案下的,你一旦重啟服務之後,這個tmp就會重新整理到最初狀態,所以檔案就不存在了。
檔案不存在了,要麼參照我之前一篇文章《Docker之自定義映象製作與執行(一)》去github上下載,要麼參照下一篇檔案從docker容器中拷貝出來。
檔案已經準備好,重新構建映象:
docker build -t jpress:latest .
可以看到我們的映象已經重新構建成功了,那我們再看一下本地的映象有哪些
docker images
可以看出jpress就是我們剛才構建的映象,從構建時間可以看出,接下來我們再看下剛才構建的映象是否把我們所需要的檔案都拷貝到我們知道的目錄下了呢?
我們先執行一下容器,然後進入容器內部檢視各個檔案所在的位置是否存在
好了,我們已經看到所有的檔案已經完全拷貝到映象之中了,那麼再也不怕丟失,即使是重啟服務也沒事了。