1. 程式人生 > 其它 >Dockerfile的使用以及docker部署java專案

Dockerfile的使用以及docker部署java專案

https://blog.csdn.net/xibei19921101/article/details/108385022

DockerFile定製一切
docker可以利用簡單的編寫程式構建出任何你想要的環境,同時可以跟業務程式碼相結合,快速構建和生成所需要的應用。

Dockerfile用來建立一個自定義的Image,包含了使用者指定的軟體依賴等。使用Docker的build命令可以直接構建新的Image。它簡化了從頭到尾的流程並極大地簡化了部署工作。

一、Dockerfile語法
Dockerfile語法由兩部分構成:註釋和命令+引數

簡單示例:構建一個簡單的映象

Dockerfile可以將檔名字設定為Dockerfile,若是別的檔名需結合-f指令,指定Dockerfile的檔名

在/gangye/dockerImageTestFile目錄下編寫兩個Dockerfile檔案,一個就為Dockerfile,另一個命名為helloDockerFile,裡面的內容一致,皆為:

FROM centos
#只是單純的列印"hello world"
RUN echo "hello world"


檢視當前docker中的已有的映象

根據之前的Dockerfile建立映象

docker build -t my_first_docker_image /gangye/dockerImageTestFile/
建立後再檢視已有的映象,剛剛的build執行語句已生效

上述中執行使用另一個檔名為helloDockerFile的Dockerfile,執行後報錯:

Error checking context: 'no permission to read from '/proc/sys/net/ipv4/route/flush''.

解決方案:docker建立映象最好是在自定義的Dockerfile檔案中執行建立

.的含義:.表示docker使用當前目錄作為構建上下文。這個目錄與shell的工作目錄一樣,不是docker的工作目錄。

二、Dockerfile命令
Dockerfile 的指令如下。

FROM
FROM命令可能是最重要的Dockerfile命令。此命令定義了使用哪個基礎映象啟動構建流程。基礎映象可以為任意映象。如果基礎映象沒有被發現,則Docker將試圖從Docker image index來查詢該映象。

格式為FROM <image>或FROM <image>:<tag>。

第一條指令必須為FROM指令(雖然目前最新的docker版本支援第一條不一定是FROM指令,但是為避免後續出錯,最好第一條指令就是FROM)。並且,在同一個Dockerfile中建立多個映象時,可以使用多個FROM指令(每個映象一次)。

MAINTAINER
格式為MAINTAINER <name>,指定維護者資訊。其實就是類似javadoc註釋中的@author,用於宣告創作者,一般都放在檔案比較靠上的位置。

RUN
從名稱上就可以看出,RUN是執行或執行的意思。

格式為RUN <command>或RUN["executable","paraml","param2"]。

前者將在Shell終端中執行命令,即/bin/sh -c;後者則使用exec執行。指定使用其他終端可以通過第二種方式實現,例如,RUN["/bin/bash","-c","echo hello"]。

每條RUN指令將在當前映象基礎上執行指定命令,並提交為新的映象。當命令較長時可以使用"\"來換行。

EXPOSE
格式為EXPOSE <port>[<port>...]。

告訴Docker服務端容器暴露的埠號,供互聯絡統使用。

CMD
支援三種格式:

CMD ["executable","paraml","param2"]使用exec執行,推薦方式;
CMD command paraml param2在/bin/sh中執行,提供給需要互動的應用;
CMD ["paraml","param2"]提供給ENTRYPOINT的預設引數。
指定啟動容器時執行的命令,每個Dockerfile只能有一條CMD命令。如果指定了多條命令,則只有最後一條會被執行。

如果使用者啟動容器時指定了執行的命令,則會覆蓋CMD指定的命令。

ENTRYPOINT
兩種格式:

1.ENTRYPOINT["executable","paraml","param2"]

2.ENTRYPOINT command paraml param2(Shell中執行)。

配置容器啟動後執行的命令,並且不可被Docker RUN叫提供的引數覆蓋。

每個Dockerfile中只能有一個ENTRYPOINT,當指定多個時,只有最後一個生效。

ENV
格式為ENV <key> <value>。指定一個環境變數,會被後續RUN叫指令使用,並在容器執行時保持。

例如 :

ENV PG_MAJOR 9.3

ENV PG_VERSION 9.3.4

RUN curl - SL http://example.com/postgres-$PG_VERSION.tar.xz | tar-xJC/usr/src/postgress && …

ENV PATH /usr/local/postgres-$PG_MAJOR/bin:$PATH
ADD
格式為ADD <src> <dest>。

該命令將複製指定的<src>到容器中的<dest>,其中<src>可以是 Dockerfile 所在目錄的一個相對路徑:也可以是一個URL;還可以是一個tar檔案(自動解壓為目錄)。

COPY
格式為 COPY <src> <dest> 。

複製本地主機的<src> ( Dockerfile所在目錄的相對路徑)到容器中的<dest>。

當使用本地目錄為源目錄時,推薦使用COPY。

VOLUME
格式為VOLUME ["/data"]。

建立一個可以從本地主機或其他容器掛載的掛載點 , 一般用來存放資料庫和需要保持的資料等。

WORKDIR
格式為WORKDIR /path/to/workdir。

為後續的RUN、CMD、ENTRYPOINT指令配置工作目錄。

可以使用多個WORKDIR指令,後續命令如果引數是相對路徑,則會基於之前命令指定的路徑。例如:

WORKDIR /a

WORKDIR b

WORKDIR c

RUN pwd

最終路徑為/a/b/c 。

USER
格式為USER daemon。

指定執行容器時的使用者名稱或UID,後續的RUN也會使用指定使用者。

當服務不需要管理員許可權時,可以通過該命令指定執行使用者。並且可以在之前建立所需要的使用者,例如,RUN groupadd -r postgres && useradd -r -g postgres postgres。要臨時獲取管理員許可權可以使用go鈕,而不推薦使用sudo。

ONBUILD
格式為ONBUILD [INSTRUCTION]。

配置當建立的映象作為其他新建立映象的基礎映象時,所執行的操作指令。

例如,Dockerfile使用如下內容建立了映象image-A 。

[...]

ONBUILD ADD . /app/src

ONBUILD RUN /usr/local/bin/python-build --dir /app/src

[...]

如果基於A建立新的映象,新的Dockerfile中使用FROM image-A指定基礎映象,則會自動執行ONBUILD指令內容,等價於在後面添加了兩條指令。

FROM image-A

#Automatically run the following

ADD . /app/src

RUN /usr/local/bin/python-build --dir /app/src
使用ONBUILD指令的映象,推薦在標籤中註明,例如,ruby:1.9-onbuild。

三、Dockerfile構建過程
Dockerfile其實可以看作一個命令集,每行均為一條命令,每行的第一個單詞就是命令command,後面的字串是該命令所要接收的引數。比如ENTRYPOINT /bin/bash。ENTRYPOINT命令的作用就是將後面的引數設定為映象的entrypoint。

docker build的流程

(1)提取Dockerfile(evaluator.go/RUN)。
(2)將Dockerfile按行進行分析(parser/parser.go/Parse),每行第一個單詞(如CMD、FROM等)叫作command。根據command,將之後的字串用對應的資料結構進行接收。
(3)根據分析的command,在dispatchers.go中選擇對應的函式進行處理(dispatchers.go)。
(4)處理完所有的命令,如果需要打標籤,則給最後的映象打上tag,結束。
Dockerfile逆向

通過docker history image可以看到該映象的歷史來源。即使沒有Dockerfile,也可以通過history來逆向產生Dockerfile。

四、構建Java環境
1.首先做好準備工作,建立一個目錄,在目錄下,建立Dockerfile檔案,以及準備好jdk以及一個可執行的jar檔案

2.在Dockerfile中編寫內容

# Set the base image to centos
FROM centos

###############################################################
# Dockerfile to build java container images
# Based on CentOS
# File Author / Maintainer
###############################################################
MAINTAINER qigangye [email protected]

RUN mkdir /var/tmp/jdk
COPY jdk-8u221-linux-x64.tar.gz /var/tmp/jdk
RUN tar xzf /var/tmp/jdk/jdk-8u221-linux-x64.tar.gz -C /var/tmp/jdk
RUN rm -rf /var/tmp/jdk/jdk-8u221-linux-x64.tar.gz
# 將目錄中的springboot_demo-1.0-SNAPSHOT.jar複製到容器中
ADD springboot_demo-1.0-SNAPSHOT.jar app.jar

ENV JAVA_HOME=/var/tmp/jdk/jdk1.8.0_221
ENV PATH=$JAVA_HOME/bin:$PATH
ENV CLASSPATH=.:$JAVA_HOME/lib/dt.jar:$JAVA_HOME/lib/tool.jar

EXPOSE 7001

ENTRYPOINT ["java","-jar","/app.jar"]
注意:若第一行不是FROM的指令,有的版本的docker會報Please provide a source image with `from` prior to commit這個錯,升級docker的版本,或者將第一行的指令改為FROM即可

3.在目錄下執行docker build

docker build -t jdk8demo .
注意最後面的小數點,上面已說明,代表當前目錄

4.檢視所有映象

5.執行映象,並檢視當前啟動的容器以及所有容器

docker run --name javademo -d -p 7001:7001 jdk8demo


6.使用postman工具測試部署的java專案,成功