1 What & Why
What: 什麼是構建docker映象?
構建docker映象在現有映象的基礎上,修改或新增個人的功能後,重新打包成新映象的過程
Why: 為什麼要構建docker映象?
docker映象方便部署及分享他人
2 Hello World
2.1 目標
- 利用現有映象ubuntu構建新映象
- 映象的功能是利用ubuntu的echo命令列印Hello world
2.2 建立資料夾
mkdir demo01-helloworld
cd demo01-helloworld
2.3 建立配置檔案
Docker以檔案Dockerfile
作為配置檔案,內容如下
Dockerfile
FROM ubuntu:latest
CMD ["/bin/echo", "Hello world!"]
以上內容非常簡單
FROM
用來配置基礎映象,這裡以ubuntu的最新版本的映象作為基礎映象CMD
表示映象中執行的命令,這裡等同於執行命令/bin/echo "Hello World!"
- 當前的格式為Exec格式
- 後面會介紹shell格式
2.4 構建映象
命令
docker image build . -t demo01-helloworld:0.0.1
-
.
表示當前資料夾裡的所有檔案 -
-t
等同於--tag
,作用是給映象打標籤,這裡的標籤名為demo01-helloworld
-
:
後是映象的版本號,如果省略則預設為latest
構建過程如下,當列印Successfully tagged demo01-helloworld:0.0.1
表明映象構建成功
$ docker image build . -t demo01-helloworld
Sending build context to Docker daemon 2.048kB
Step 1/2 : FROM ubuntu:latest
---> 4e2eef94cd6b
Step 2/2 : CMD ["/bin/echo", "Hello world!"]
---> Running in 581995f3af46
Removing intermediate container 581995f3af46
---> afa0f6e8fc94
Successfully built afa0f6e8fc94
Successfully tagged demo01-helloworld:0.0.1
可以用命令docker image ls
查詢所有映象,再次確認已經構建完成
$ docker image ls
REPOSITORY TAG IMAGE ID CREATED SIZE
demo01-helloworld 0.0.1 afa0f6e8fc94 19 seconds ago 73.9MB
執行映象,先生成容器,再啟動容器
$ docker container run demo01-helloworld:0.0.1
Hello world!
docker啟動時先判斷有沒有該容器,如果不存在則通過映象建立相應的容器,然後執行容器
2.5 注意
需要說明的是CMD
可以在構造映象的時候不指定,啟動容器的時候執行。如果啟動時指定了命令,則CMD
中指定的命令將不會執行,即被覆蓋,現象如下。你看懂了嗎?
$ docker container run demo01-helloworld:0.0.1 /bin/echo "Hello world! v2"
Hello world! v2
3 java應用
3.1 目標
- 利用現有映象openjdk構建新映象
- 映象的功能是執行java程式列印Hello java
3.2 建立資料夾
mkdir demo02-hellojava
cd demo02-java
3.3 建立java工程
選擇你喜歡的方式建立一個maven工程,可以從通過網頁下載模板,可以利用eclipse和idea等等
這裡採用mvn命令的方式建立
mvn archetype:generate -DgroupId=org.zwx.hellojava -DartifactId=demo02-hellojava -DinteractiveMode=false
結果如下
$ mvn archetype:generate -DgroupId=org.zwx.hellojava -DartifactId=demo02-hellojava -DinteractiveMode=false
[INFO] Scanning for projects...
[INFO]
[INFO] ------------------< org.apache.maven:standalone-pom >-------------------
[INFO] Building Maven Stub Project (No POM) 1
[INFO] --------------------------------[ pom ]---------------------------------
[INFO] ...省略一些內容
[INFO] Parameter: basedir, Value: /Users/zhouweixin/docker-demos
[INFO] Parameter: package, Value: org.zwx.hellojava
[INFO] Parameter: groupId, Value: org.zwx.hellojava
[INFO] Parameter: artifactId, Value: demo02-hellojava
[INFO] Parameter: packageName, Value: org.zwx.hellojava
[INFO] Parameter: version, Value: 1.0-SNAPSHOT
[INFO] project created from Old (1.x) Archetype in dir: /Users/zhouweixin/docker-demos/demo02-hellojava
[INFO] ------------------------------------------------------------------------
[INFO] BUILD SUCCESS
[INFO] ------------------------------------------------------------------------
[INFO] Total time: 16.557 s
[INFO] Finished at: 2020-09-28T17:55:09+08:00
[INFO] ------------------------------------------------------------------------
檔案目錄
.
├── pom.xml
└── src
├── main
│ └── java
│ └── org
│ └── zwx
│ └── hellojava
│ └── App.java
└── test
└── java
└── org
└── zwx
└── hellojava
└── AppTest.java
3.4 編譯執行
在打包之前先確定java應用可以正常執行
首先,修改檔案src/main/java/org/zwx/hellojava/App.java
package org.zwx.hellojava;
/**
* Hello world!
*
*/
public class App
{
public static void main( String[] args )
{
System.out.println( "Hello java!" );
}
}
然後,用mvn
命令編譯打包
$ mvn package
[INFO] Scanning for projects...
[INFO]
[INFO] -----------------< org.zwx.hellojava:demo02-hellojava >-----------------
[INFO] Building demo02-hellojava 1.0-SNAPSHOT
[INFO] --------------------------------[ jar ]---------------------------------
[INFO] ...省略一些內容
[INFO] --- maven-jar-plugin:2.4:jar (default-jar) @ demo02-hellojava ---
[INFO] Building jar: /Users/zhouweixin/docker-demos/demo02-hellojava/target/demo02-hellojava-1.0-SNAPSHOT.jar
[INFO] ------------------------------------------------------------------------
[INFO] BUILD SUCCESS
[INFO] ------------------------------------------------------------------------
[INFO] Total time: 1.531 s
[INFO] Finished at: 2020-09-28T17:59:40+08:00
[INFO] ------------------------------------------------------------------------
檔案目錄
.
├── pom.xml
├── src
│ └── ...省略一些內容
└── target
├── demo02-hellojava-1.0-SNAPSHOT.jar
└── ...省略一些內容
當你執行完命令mvn package
後,首先會編譯生成一些class檔案,然後打包成demo02-hellojava-1.0-SNAPSHOT.jar
,生成的檔案都在目錄target下
該jar檔案是執行檔案,具體執行命令如下
$ java -cp target/demo02-hellojava-1.0-SNAPSHOT.jar org.zwx.hellojava.App
Hello java!
3.5 拉取基礎映象
如前文所述構建映象需要一個基礎映象,基礎映象也可以不提前拉取,構建的時候如果不存在也會自動拉取
該例子中要想啟動java應用,你知道需要哪個環境嗎?
你應該是猜對了,僅僅需要java的執行時環境(jre)
首先到hub.docker.com上檢索jre的相關tag,這裡我們選擇的是8u265-jre
二話不說,先拉取映象(也可以不提前拉取)
$ docker pull openjdk:8u265-jre
8u265-jre: Pulling from library/openjdk
57df1a1f1ad8: Pull complete
71e126169501: Pull complete
1af28a55c3f3: Pull complete
a9777c2d5c29: Pull complete
9248106993db: Pull complete
1f74ab5b5b3e: Pull complete
Digest: sha256:e98dece4606dc1ec47c0c9ab6aa43931577232a5b7d6fd46f3ead7377727b412
Status: Downloaded newer image for openjdk:8u265-jre
docker.io/library/openjdk:8u265-jre
用互動的方式執行該映象並確定java的版本
$ docker container run -it openjdk:8u265-jre
root@0687c67dccd0:/# java -version
openjdk version "1.8.0_265"
OpenJDK Runtime Environment (build 1.8.0_265-b01)
OpenJDK 64-Bit Server VM (build 25.265-b01, mixed mode)
引數說明
-it
是-i
和-t
的縮寫-i
全稱是--interactive
,即互動模式,可以正常的輸入輸出-t
是一個偽TTY,即偽終端
3.6 構建映象
建立配置檔案Dockerfile
FROM openjdk:8u265-jre
COPY target/demo02-hellojava-1.0-SNAPSHOT.jar /usr/src/demo02-hellojava-1.0-SNAPSHOT.jar
CMD java -cp /usr/src/demo02-hellojava-1.0-SNAPSHOT.jar org.zwx.hellojava.App
引數說明
COPY
命令用於將本地檔案拷貝到基礎映象中,並且這個基礎映象中有java執行時環境,兩者結合滿足正常執行程式- 第一個引數為本地檔案目錄
- 第二個引數為基礎映象中的目錄
CMD
命令表示在基礎映象中執行的命令(可以不寫陣列的形式)
執行映象構建命令
$ docker image build . -t demo02-hellojava:0.0.1
Sending build context to Docker daemon 38.91kB
Step 1/3 : FROM openjdk:8u265-jre
---> d9d1d3243082
Step 2/3 : COPY target/demo02-hellojava-1.0-SNAPSHOT.jar /usr/src/demo02-hellojava-1.0-SNAPSHOT.jar
---> Using cache
---> 6c34d345bb51
Step 3/3 : CMD java -cp /usr/src/demo02-hellojava-1.0-SNAPSHOT.jar org.zwx.hellojava.App
---> Running in 0d9a33ea0ae1
Removing intermediate container 0d9a33ea0ae1
---> fc3cd9ee5218
Successfully built fc3cd9ee5218
Successfully tagged demo02-hellojava:0.0.1
啟動
$ docker container run demo02-hellojava:0.0.1
Hello java!
4 Dockfile中的命令
命令 | 功能 |
---|---|
FROM | 指定基礎映象 |
COPY | 複製檔案或資料夾 |
ENV | 設定環境變數 |
RUN | 執行一個命令,可以寫多個,通常用於安裝軟體包 |
CMD | 執行一個命令,只有一個被執行,可被docker run後面的命令所覆蓋,即如果命令列中有該命令,CMD中的將不會執行 |
ENTRYPOINT | 配置容器啟動時的命令,一定會執行 |
EXPOSE | 暴露的埠號 |