1.Alipne鏡像
目前比較流行的 rootfs 應該就是 alpine 了,因為他的體積特別小,最簡單的環境只需要 5M 。Docker 官方已開始推薦使用 Alpine 替代之前的 Ubuntu 做為基礎鏡像環境。
Alpine 操作系統是一個面向安全的輕型 Linux 發行版。它不同於通常 Linux 發行版,Alpine 采用了 musl libc 和 busybox 以減小系統的體積和運行時資源消耗,但功能上比 busybox 又完善的多,因此得到開源社區越來越多的青睞。在保持瘦身的同時,Alpine 還提供了自己的包管理工具 apk,可以通過 https://pkgs.alpinelinux.org/packages 網站上查詢包信息,也可以直接通過 apk 命令直接查詢和安裝各種軟件。
Alpine 由非商業組織維護的,支持廣泛場景的 Linux發行版,它特別為資深/重度Linux用戶而優化,關注安全,性能和資源效能。Alpine 鏡像可以適用於更多常用場景,並且是一個優秀的可以適用於生產的基礎系統/環境。
Alpine Docker 鏡像也繼承了 Alpine Linux 發行版的這些優勢。相比於其他 Docker 鏡像,它的容量非常小,僅僅只有 5 MB 左右(對比 Ubuntu 系列鏡像接近 200 MB),且擁有非常友好的包管理機制。官方鏡像來自 docker-alpine 項目。
目前 Docker 官方已開始推薦使用 Alpine 替代之前的 Ubuntu 做為基礎鏡像環境。這樣會帶來多個好處。包括鏡像下載速度加快,鏡像安全性提高,主機之間的切換更方便,占用更少磁盤空間等。
下表是官方鏡像的大小比較:
一句話,alpine可以替代Ubuntu作為基礎鏡像。體積小。
直接運行alpine進行下載:
E:\docker\dockerTest\dockerfiletest>docker run alpine echo '123' Unable to find image 'alpine:latest' locally latest: Pulling from library/alpine c9b1b535fdd9: Pull complete Digest: sha256:ab00606a42621fb68f2ed6ad3c88be54397f981a7b70a79db3d1172b11c4367d Status: Downloaded newer image for alpine:latest '123' E:\docker\dockerTest\dockerfiletest>docker images REPOSITORY TAG IMAGE ID CREATED SIZE alpine latest e7d92cdc71fe 3 weeks ago 5.59MB hello-world latest fce289e99eb9 13 months ago 1.84kB hub.c.163.com/library/nginx latest 46102226f2fd 2 years ago 109MB hub.c.163.com/library/nginx 1.9 af4b3d7d5401 3 years ago 191MB
2.制作簡單的鏡像
1.什么是dockerfile?
Dockerfile 是一個用來構建鏡像的文本文件,文本內容包含了一條條構建鏡像所需的指令和說明。相當於告訴docker我要做什么事情。
2.docker build
相當於是執行dockerfile里面的每一件事情,制作一個鏡像。
3.構建第一個鏡像
(1)新建一個干凈的文件夾下面建一個Dockerfile文件,內容如下:
FROM alpine:latest MAINTAINER qlq qlq@163.com CMD echo "hello dockerfile"
如下:
E:\docker\dockerTest\dockerfiletest>ls Dockerfile E:\docker\dockerTest\dockerfiletest>cat Dockerfile FROM alpine:latest MAINTAINER qlq qlq@163.com CMD echo "hello dockerfile"
解釋:
FROM:定制的鏡像都是基於 FROM 的鏡像,這里的 alpine就是定制需要的基礎鏡像。后續的操作都是基於 alpine。
MAINTAINER: 指定鏡像的作者名稱和郵箱(可以省略)
CMD:需要執行的命令,相當於在shell腳本中執行的命令。
補充:與CMD有相同功能的有RUN、ENTRYPOINT,三個都能執行命令,但是有區別:
RUN命令執行命令並創建新的鏡像層,通常用於安裝軟件包。在構建鏡像的時候執行。多條命名會依次執行,每執行一次鏡像多一層。
CMD命令設置容器啟動后默認執行的命令及其參數,但CMD設置的命令能夠被docker run命令后面的命令行參數替換。此命令會在容器啟動且 docker run 沒有指定其他命令時運行。多個只有最后一條生效。
ENTRYPOINT配置容器啟動時的執行命令(不會被忽略,一定會被執行,即使運行 docker run時指定了其他命令)。相當於是容器的入口。多個只有最后一條生效。
我們可用兩種方式指定 RUN、CMD 和 ENTRYPOINT 要運行的命令:Shell 格式和 Exec 格式:
Shell格式:<instruction> <command>。例如:apt-get install python3
Exec格式:<instruction> ["executable", "param1", "param2", ...]。例如: ["apt-get", "install", "python3"]
CMD 和 ENTRYPOINT 推薦使用 Exec 格式,因為指令可讀性更強,更容易理解。RUN 則兩種格式都可以。
注意:Dockerfile 的RUN指令每執行一次都會在 docker 上新建一層。所以過多無意義的層,會造成鏡像膨脹過大。例如:
FROM centos RUN yum install wget RUN wget -O redis.tar.gz "http://download.redis.io/releases/redis-5.0.3.tar.gz" RUN tar -xvf redis.tar.gz 以上執行會創建 3 層鏡像。可簡化為以下格式: FROM centos RUN yum install wget \ && wget -O redis.tar.gz "http://download.redis.io/releases/redis-5.0.3.tar.gz" \ && tar -xvf redis.tar.gz
(2)構建鏡像:
E:\docker\dockerTest\dockerfiletest>docker build -t hello_dockerfile . #構建鏡像 Sending build context to Docker daemon 2.048kB Step 1/3 : FROM alpine:latest ---> e7d92cdc71fe Step 2/3 : MAINTAINER qlq qlq@163.com ---> Running in 0eed5430920c Removing intermediate container 0eed5430920c ---> 099d9254c7b7 Step 3/3 : CMD echo "hello dockerfile" ---> Running in 70ba59845b28 Removing intermediate container 70ba59845b28 ---> 779eab29d6dc Successfully built 779eab29d6dc Successfully tagged hello_dockerfile:latest SECURITY WARNING: You are building a Docker image from Windows against a non-Windows Docker host. All files and directories added to build context will have '-rwxr-xr-x' permissions. It is recommended to double check and reset permissions for sensitive files and directories. E:\docker\dockerTest\dockerfiletest>docker images #運行鏡像 REPOSITORY TAG IMAGE ID CREATED SIZE hello_dockerfile latest 779eab29d6dc 5 seconds ago 5.59MB alpine latest e7d92cdc71fe 3 weeks ago 5.59MB hello-world latest fce289e99eb9 13 months ago 1.84kB hub.c.163.com/library/nginx latest 46102226f2fd 2 years ago 109MB hub.c.163.com/library/nginx 1.9 af4b3d7d5401 3 years ago 191MB E:\docker\dockerTest\dockerfiletest>docker run hello_dockerfile hello dockerfile
解釋:
docker build -t hello_dockerfile .
(1)構建鏡像時的-t表示給鏡像一個tag,可以指定為name:version形式。
(2) 最后的點代表上下文路徑,是指 docker 在構建鏡像,有時候想要使用到本機的文件(比如復制),docker build 命令得知這個路徑后,會將路徑下的所有內容打包。
由於 docker 的運行模式是 C/S。我們本機是 C,docker 引擎是 S。實際的構建過程是在 docker 引擎下完成的,所以這個時候無法用到我們本機的文件。這就需要把我們本機的指定目錄下的文件一起打包提供給 docker 引擎使用。
如果未說明最后一個參數,那么默認上下文路徑就是 Dockerfile 所在的位置。
注意:上下文路徑下不要放無用的文件,因為會一起打包發送給 docker 引擎,如果文件過多會造成過程緩慢。
4.指令詳解-Dockerfile語法
0.FROM
基礎鏡像。定制的鏡像都是基於 FROM 的鏡像。下面的操作都是基礎該鏡像。
1.RUN
用於執行后面跟着的命令行命令。只在構建鏡像的時候執行,一般用於構建鏡像的時候下載文件。
語法:
shell格式:
RUN <命令行命令>
# <命令行命令> 等同於,在終端操作的 shell 命令。
exec格式:
RUN ["可執行文件", "參數1", "參數2"] # 例如: # RUN ["./test.php", "dev", "offline"] 等價於 RUN ./test.php dev offline
2. COPY
復制指令,從上下文目錄中復制文件或者目錄到容器里指定路徑。
語法:
COPY [--chown=<user>:<group>] <源路徑1>... <目標路徑> COPY [--chown=<user>:<group>] ["<源路徑1>",... "<目標路徑>"]
[--chown=<user>:<group>]:可選參數,用戶改變復制到容器內文件的擁有者和屬組。
<源路徑>:源文件或者源目錄,這里可以是通配符表達式,其通配符規則要滿足 Go 的 filepath.Match 規則。
<目標路徑>:容器內的指定路徑,該路徑不用事先建好,路徑不存在的話,會自動創建。
3. ADD
ADD 指令和 COPY 的使用格式一致(同樣需求下,官方推薦使用 COPY)。Add還可以將遠程的文件拷貝到目錄下,比如http服務器上文件。與COPY不同之處如下:
ADD 的優點:在執行 <源文件> 為 tar 壓縮文件的話,壓縮格式為 gzip, bzip2 以及 xz 的情況下,會自動復制並解壓到 <目標路徑>。
ADD 的缺點:在不解壓的前提下,無法復制 tar 壓縮文件。會令鏡像構建緩存失效,從而可能會令鏡像構建變得比較緩慢。具體是否使用,可以根據是否需要自動解壓來決定。
4.CMD
類似於 RUN 指令,用於運行程序,但二者運行的時間點不同:
CMD 在docker run 時運行。
RUN 是在 docker build。
作用:為啟動的容器指定默認要運行的程序,程序運行結束,容器也就結束。CMD 指令指定的程序可被 docker run 命令行參數中指定要運行的程序所覆蓋。
注意:如果 Dockerfile 中如果存在多個 CMD 指令,僅最后一個生效。
5.ENTRYPOINT(一般用作容器的入口)
類似於 CMD 指令,但其不會被 docker run 的命令行參數指定的指令所覆蓋,而且這些命令行參數會被當作參數送給 ENTRYPOINT 指令指定的程序。
但是, 如果運行 docker run 時使用了 --entrypoint 選項,此選項的參數可當作要運行的程序覆蓋 ENTRYPOINT 指令指定的程序。
優點:在執行 docker run 的時候可以指定 ENTRYPOINT 運行所需的參數。
注意:如果 Dockerfile 中如果存在多個 ENTRYPOINT 指令,僅最后一個生效。
6.ENV
設置環境變量,定義了環境變量,那么在后續的指令中,就可以使用這個環境變量。
語法:
ENV <key> <value>
ENV <key1>=<value1> <key2>=<value2>...
7.ARG
構建參數,與 ENV 作用一至。不過作用域不一樣。ARG 設置的環境變量僅對 Dockerfile 內有效,也就是說只有 docker build 的過程中有效,構建好的鏡像內不存在此環境變量。
構建命令 docker build 中可以用 --build-arg <參數名>=<值> 來覆蓋。
語法:
ARG <參數名>[=<默認值>]
8.VOLUME(重要)
定義匿名數據卷。在啟動容器時忘記掛載數據卷,會自動掛載到匿名卷。
語法:
VOLUME ["<路徑1>", "<路徑2>"...] VOLUME <路徑>
作用:
避免重要的數據,因容器重啟而丟失,這是非常致命的。
避免容器不斷變大。
可以做到多個容器共享數據。
9.EXPOSE
僅僅只是聲明端口。
語法:
EXPOSE <端口1> [<端口2>...]
作用:
幫助鏡像使用者理解這個鏡像服務的守護端口,以方便配置映射。
在運行時使用隨機端口映射時,也就是 docker run -P 時,會自動隨機映射 EXPOSE 的端口。
10.WORKDIR
指定工作目錄。用 WORKDIR 指定的工作目錄,會在構建鏡像的每一層中都存在。(WORKDIR 指定的工作目錄,必須是提前創建好的)。
docker build 構建鏡像過程中的,每一個 RUN 命令都是新建的一層。只有通過 WORKDIR 創建的目錄才會一直存在。
語法:
WORKDIR <工作目錄路徑>
3. 基於nginx構建鏡像
1.創建Dockerfile文件,內容如下
FROM ubuntu MAINTAINER qlq qlq@163.com RUN apt-get update RUN apt-get install -y nginx COPY index.html /var/www/html ENTRYPOINT ["/usr/sbin/nginx", "-g", "daemon off;"] EXPOSE 80
解釋:
(1)FROM...指定鏡像依賴於ubuntu鏡像
(2)MAINTAINER...指定鏡像維護者信息
(3)RUN apt-get update 相當於在ubuntu系統中執行更新軟件
(4)RUN apt-get install -y nginx 是ubuntu系統安裝nginx,-y表示直接安裝不詢問。
(5)COPY inde... 是將當前目錄下的index.html拷貝到鏡像中/var/www/html 目錄下。(nginx默認的首頁在此目錄下,相當於更換nginx默認首頁)
(6)ENTRYPOINT... 是執行命令,相當於運行鏡像時執行"/usr/sbin/nginx -g daemon off;"
(7)EXPOSE 80 是指定該容器的端口是80
index.html內容如下:
"今天是周五!!!"
2.構建鏡像
docker build -t qlq/hello-nginx .
3.查看鏡像並且運行鏡像
E:\docker\dockerTest\dockerfiletest2>docker images REPOSITORY TAG IMAGE ID CREATED SIZE qlq/hello-nginx latest 8d51cb07e20b 3 minutes ago 152MB hello_dockerfile latest 779eab29d6dc About an hour ago 5.59MB alpine latest e7d92cdc71fe 3 weeks ago 5.59MB ubuntu latest ccc6e87d482b 4 weeks ago 64.2MB hello-world latest fce289e99eb9 13 months ago 1.84kB hub.c.163.com/library/nginx latest 46102226f2fd 2 years ago 109MB hub.c.163.com/library/nginx 1.9 af4b3d7d5401 3 years ago 191MB E:\docker\dockerTest\dockerfiletest2>docker run -d -p 8070:80 qlq/hello-nginx #運行鏡像,將本機8070端口映射到容器的80端口 0055dcf8b0bb792e06627eb10b0f817e039f15c4a00411346d99ebcab6521220 E:\docker\dockerTest\dockerfiletest2>docker ps -a CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES 0055dcf8b0bb qlq/hello-nginx "/usr/sbin/nginx -g …" 45 seconds ago Up 43 seconds 0.0.0.0:8070->80/tcp wizardly_buck b9b2d73a9b27 hello_dockerfile "/bin/sh -c 'echo \"h…" About an hour ago Exited (0) About an hour ago frosty_sammet 0a75d125d0c5 alpine "echo '123'" About an hour ago Exited (0) About an hour ago silly_murdock
4.本地瀏覽器訪問nginx服務
由於我這里是windows虛擬機訪問,因為docker是運行在Linux上的,在Windows中運行docker,實際上還是在Windows下先安裝了一個Linux環境,然后在這個系統中運行的docker。也就是說,所有的東西都是在虛擬的linux環境中,而不是我們的宿主環境Windows。所以我們也不能通過localhost直接訪問。需要先查看linux虛擬環境的IP,如下:查看本機虛擬linux環境的ip地址
E:\docker\dockerTest\dockerfiletest2>docker-machine ip default 192.168.99.100
瀏覽器訪問:
4. 鏡像推送到阿里雲
制作鏡像的目的就是可以在服務其間共享 ,就好比git、svn實現代碼托管,docker倉庫registry(注冊表)的目的就是為了實現鏡像共享。
1.登錄網易雲后台創建鏡像倉庫
到阿里雲網站創建鏡像:https://cr.console.aliyun.com/cn-hangzhou/instances/repositories
例如我創建的鏡像倉庫如下:
2.按照操作指南推送、拉取鏡像(有點像git操作)
1.登錄阿里雲Docker Registry
C:\Users\Administrator>docker login --username={username} registry.cn-hangzhou.aliyuncs.com Password: Login Succeeded
注意:用戶名不是登錄的賬號,是右上角的用戶名,為阿里雲賬號全名,密碼為開通服務時設置的密碼。
2.給鏡像打個tag
C:\Users\Administrator>docker tag 8d51cb07e20b registry.cn-hangzhou.aliyuncs.com/qlq_repository/nginx_test:1.0 C:\Users\Administrator>docker images REPOSITORY TAG IMAGE ID CREATED SIZE registry.cn-hangzhou.aliyuncs.com/qlq_repository/nginx_test 1.0 8d51cb07e20b 30 hours ago 152MB qlq/hello-nginx latest 8d51cb07e20b 30 hours ago 152MB hello_dockerfile latest 779eab29d6dc 32 hours ago 5.59MB alpine latest e7d92cdc71fe 4 weeks ago 5.59MB ubuntu latest ccc6e87d482b 4 weeks ago 64.2MB hello-world latest fce289e99eb9 13 months ago 1.84kB
8d51cb07e20b 是鏡像ID。
3.將鏡像推送到服務器
C:\Users\Administrator>docker push registry.cn-hangzhou.aliyuncs.com/qlq_repository/nginx_test:1.0 The push refers to repository [registry.cn-hangzhou.aliyuncs.com/qlq_repository/nginx_test] a3b9aa970bc0: Pushed 3cf5ba3c83a0: Pushed fbe31d7fb8d4: Pushed f55aa0bd26b8: Pushed 1d0dfb259f6a: Pushed 21ec61b65b20: Pushed 43c67172d1d1: Pushed 1.0: digest: sha256:bff6d848fe12db25b125d1fb313b657a1511e761b7ad1339fa3b58724e40681d size: 1783
4.刪掉鏡像重新拉取
(1)刪掉鏡像
C:\Users\Administrator>docker images REPOSITORY TAG IMAGE ID CREATED SIZE registry.cn-hangzhou.aliyuncs.com/qlq_repository/nginx_test 1.0 8d51cb07e20b 30 hours ago 152MB hello_dockerfile latest 779eab29d6dc 32 hours ago 5.59MB alpine latest e7d92cdc71fe 4 weeks ago 5.59MB ubuntu latest ccc6e87d482b 4 weeks ago 64.2MB hello-world latest fce289e99eb9 13 months ago 1.84kB C:\Users\Administrator>docker rmi 8d51cb07e20b Untagged: registry.cn-hangzhou.aliyuncs.com/qlq_repository/nginx_test:1.0 Untagged: registry.cn-hangzhou.aliyuncs.com/qlq_repository/nginx_test@sha256:bff6d848fe12db25b125d1fb313b657a1511e761b7ad1339fa3b58724e40681d Deleted: sha256:8d51cb07e20bc1d7ba5cdd8fad0f71e8d0648c5e0014edec2c3479e6abd97e07 Deleted: sha256:c8ae0526637186e2cbe1f32921cdeb54b1d99567768b78c9afb773d96cb13a86 Deleted: sha256:229ffc761a761e6158c4922e7a325099128dcd430ea96e0bc971cadc60445209 Deleted: sha256:b52023bf894ea07a5a0aa9c496b9e566c0dffb3fd7839b8b1884f43a6c4dea50 Deleted: sha256:fd2cc76d6ec190609d884fef2b920a12ac7a1914d9f431df2018d47db3f90c84 Deleted: sha256:989bdbfef3339a3128ac2e9c604058665e90d5d645b8be420da21b97d0a1f198 Deleted: sha256:e19041d97f93ead73404e6bdb9e98217b0610174bc2a86d0b38d126d35ef84c0 Deleted: sha256:a2adcb468f641388b71b54b3ee71b50875a66a65d804827081af889221ebac47 Deleted: sha256:b7adbc510303bfc49523ed4cfea0f2822e0c74e73e48638d3a6a6d30acc32dba C:\Users\Administrator>docker images REPOSITORY TAG IMAGE ID CREATED SIZE hello_dockerfile latest 779eab29d6dc 32 hours ago 5.59MB alpine latest e7d92cdc71fe 4 weeks ago 5.59MB ubuntu latest ccc6e87d482b 4 weeks ago 64.2MB hello-world latest fce289e99eb9 13 months ago 1.84kB
(2)拉取鏡像並啟動
C:\Users\Administrator>docker pull registry.cn-hangzhou.aliyuncs.com/qlq_repository/nginx_test:1.0 1.0: Pulling from qlq_repository/nginx_test 5c939e3a4d10: Already exists c63719cdbe7a: Already exists 19a861ea6baf: Already exists 651c9d2d6c4f: Already exists c26963fcdbc6: Pull complete 68b742b548f6: Pull complete 476724010f32: Pull complete Digest: sha256:bff6d848fe12db25b125d1fb313b657a1511e761b7ad1339fa3b58724e40681d Status: Downloaded newer image for registry.cn-hangzhou.aliyuncs.com/qlq_repository/nginx_test:1.0 C:\Users\Administrator>docker images REPOSITORY TAG IMAGE ID CREATED SIZE registry.cn-hangzhou.aliyuncs.com/qlq_repository/nginx_test 1.0 8d51cb07e20b 30 hours ago 152MB hello_dockerfile latest 779eab29d6dc 32 hours ago 5.59MB alpine latest e7d92cdc71fe 4 weeks ago 5.59MB ubuntu latest ccc6e87d482b 4 weeks ago 64.2MB hello-world latest fce289e99eb9 13 months ago 1.84kB C:\Users\Administrator>docker run -d -p 8085:80 8d51cb07e20b cb713f70138793b5f2bea4b43ecccd7aaecc77284b80705e2060e1acde39648b
3.阿里雲后台可以看鏡像的信息