場景假設:將環境和應用打包成一個映象。當我們使用Mysql時將資料儲存在了Mysql容器裡、刪除了Mysql容器就等於刪除跑路了。要求資料持久化。
一)什麼是容器資料卷?
當我們正在使用docker容器的時候、會產生一系列的資料檔案、這些資料檔案在我們關閉docker容器時是會消失的、但是其中產生的部分內容我們是希望能夠把它給儲存起來另作用途的,Docker將應用與執行環境打包成容器釋出,我們希望在執行過程鍾產生的部分資料是可以持久化的的,而且容器之間我們希望能夠實現資料共享。
資料共享傳遞:容器之間配置資訊的傳遞,資料卷的生命週期會一致持續到沒有容器使用它為止,換言之,只要有一個容器仍在使用該資料卷,該資料卷一直都可以進行資料共享,通俗地來說,如果此時我們把父容器關閉掉,兩個字容器之間依舊可以進行資料共享,而且通過繼承子容器生成的新容器,一樣可以與子容器進行資料共享。這就是docker容器間的資料傳遞共享。
通俗地來說,docker容器資料卷可以看成使我們生活中常用的u盤,它存在於一個或多個的容器中,由docker掛載到容器,但不屬於聯合檔案系統,Docker不會在容器刪除時刪除其掛載的資料卷。
特點:
1:資料卷可以在容器之間共享或重用資料
2:資料卷中的更改可以直接生效
3:資料卷中的更改不會包含在映象的更新中
4:資料卷的生命週期一直持續到沒有容器使用它為止
當我們正在使用docker容器的時候、容器之間有一個資料共享的技術、docker容器中產生的資料儲存到本地
二)新增資料卷的方式
-
1.使用命令來掛載
docker run -it -v 主機目錄、容器目錄 容器id
這個命令會在宿主機和容器內分別建立兩個目錄,兩個目錄是對接的,裡面的資料可以共享。如果我們不知道資料卷是否掛載成功時,我們可以通過以下方式來檢查資料卷的掛載結果。
docker inspect 容器id、name
在本機伺服器上儲存
#先進入home目錄檢測home目錄下
[root@xiaozhang1999 ~]# cd /home
[root@xiaozhang1999 home]# ls
[root@xiaozhang1999 home]# docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
tomcattunc latest 276239fa14a3 22 hours ago 672MB
tomcat 9.0 5505f7218e4d 7 days ago 667MB
tomcat latest 5505f7218e4d 7 days ago 667MB
tomcat ssss 5505f7218e4d 7 days ago 667MB
redis latest fad0ee7e917a 3 weeks ago 105MB
mysql 5.7 2c9028880e58 6 weeks ago 447MB
mysql latest c0cdc95609f1 6 weeks ago 556MB
portainer/portainer latest 580c0e4e98b0 3 months ago 79.1MB
hello-world latest d1165f221234 3 months ago 13.3kB
centos latest 300e315adb2f 6 months ago 209MB
[root@xiaozhang1999 home]# docker run -it -v /home/ceshi:/home centos
[root@185d7e114c39 /]# cd home
[root@185d7e114c39 home]# ls
# Ctrl+P+Q退出centos
[root@185d7e114c39 home]# [root@xiaozhang1999 home]#
#檢測本地home目錄下是否生成了本機目錄
[root@xiaozhang1999 home]# ll
total 0
drwxr-xr-x 2 root root 6 Jun 24 14:40 ceshi
#檢視掛載的詳情
[root@xiaozhang1999 home]# docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
185d7e114c39 centos "/bin/bash" 13 minutes ago Up 13 minutes eloquent_leakey
[root@xiaozhang1999 home]# docker inspect eloquent_leakey
檢視掛載容器的詳情:docker inspect eloquent_leakey.
//命令返回的是JSON格式的格式的字串
"HostConfig": {
"Binds": [
"/home/ceshi:/home"
],
"ContainerIDFile": "",
"LogConfig": {
"Type": "json-file",
"Config": {}
},
//內容與上面輸入的內容一致、則掛載成功。運算元據卷的內容是雙向同步的。
"Mounts": [
{
"Type": "bind",
"Source": "/home/ceshi",
"Destination": "/home",
"Mode": "",
"RW": true,
"Propagation": "rprivate"
}
],
我們再掛載的時候還可以給資料卷加上許可權,假如我們要宿主機只能讀取容器的資料卷內容不能修改,我們可以新增只讀許可權
docker run -it -v /宿主機絕對路徑目錄 : /容器內目錄 :ro 映象名.至於只寫的話我們一般不會用到,要麼就是讀寫,要麼就是隻讀,而且我們可以通過docker inspect 來檢視容器的volumesRW來檢視容器內資料卷的讀寫許可權。
雙向同步(容器到主機)
(主機到容器)
好處:修改只需要在本地伺服器上修改即可、容器內會自動同步。
-
2.利用dockerfile的形式新增
dockerFile對於docker映象而言就如同java中某個類的.class檔案對應上該類的.java檔案。
首先在linux伺服器根目錄上新建docker資料夾並建立DockerFile檔案,使用volume命令(出於可移植可分享的的考慮,用以上 -v /宿主機絕對路徑目錄 : /容器內目錄 的這種方式不能夠直接在dockerFile中直接實現,因為宿主機目錄是依賴於特定的宿主機的,並不能保證所有的宿主機都存在這樣特定的目錄)
編寫的dockerFile檔案如下
FROM 映象名
VOLUME ["/生成的目錄路徑"] -- privileged=true
CMD echo "success build"
CMD /bin/bash
相當於命令列: docker run -it -v /宿主機目錄路徑 : /生成的目錄路徑
然後我們通過命令列docker build執行我們寫好的dockerFile檔案(docker build和docker commit兩個命令都可以建立docker映象,docker commit 需要在容器內進行,docker build 不需要)
docker build -f /docker/DockerFile -t 名稱空間/映象名
執行後輸入docker images就可以發現自己通過DockerFile所build的映象,裡面有掛載資料卷,那麼問題來了宿主機所對應的目錄是什麼呢?同上,我們可以通過docker inspect來檢視當前容器的Volumes,裡面會有宿主機的資料卷目錄。