一.Dockerfile命令图解
二.dockerfile命令详解
1.FROM
功能为指定基础镜像,并且必须是第一条指令。
如果不以任何镜像为基础,那么写法为:FROM scratch。
同时意味着接下来所写的指令将作为镜像的第一层开始
语法:
FROM <image>
FROM <image>:<tag>
FROM <image>:<digest>
三种写法,其中<tag>和<digest> 是可选项,如果没有选择,那么默认值为latest
2.RUN
功能为运行指定的命令
RUN命令有两种格式
RUN <command>
RUN ["executable", "param1", "param2"]
第一种后边直接跟shell命令
在linux操作系统上默认 /bin/sh -c
在windows操作系统上默认 cmd /S /C
第二种是类似于函数调用。
可将executable理解成为可执行文件,后面就是两个参数
两种写法比对:
RUN /bin/bash -c 'source ����/.���ℎ��;��ℎ�HOME/.bashrc;echoHOME
RUN ["/bin/bash", "-c", "echo hello"]
注意:多行命令不要写多个RUN,原因是Dockerfile中每一个指令都会建立一层.
多少个RUN就构建了多少层镜像,会造成镜像的臃肿、多层,不仅仅增加了构建部署的时间,还容易出错。
RUN书写时的换行符是\ ,多个shell命令之间用&&连接
3.CMD
功能为容器启动时要运行的命令
语法有三种写法
CMD ["executable","param1","param2"]
CMD ["param1","param2"]
CMD command param1 param2
第三种比较好理解了,就是shell这种执行方式和写法
第一种和第二种其实都是可执行文件加上参数的形式
补充细节:这里边包括参数的一定要用双引号,就是",不能是单引号。千万不能写成单引号。
原因是参数传递后,docker解析的是一个JSON array
4.RUN & CMD
不要把RUN和CMD搞混了。
RUN是构建容器时就运行的命令以及提交运行结果
CMD是容器启动时执行的命令,在构建时并不运行,构建时仅仅指定了这个命令到底是个什么样子
5.LABEL
功能是为镜像指定标签
语法:
LABEL <key>=<value> <key>=<value> <key>=<value> ...
一个Dockerfile种可以有多个LABEL,如下:
LABEL "com.example.vendor"="ACME Incorporated"
LABEL com.example.label-with-value="foo"
LABEL version="1.0"
LABEL description="This text illustrates
that label-values can span multiple lines."
但是并不建议这样写,最好就写成一行,如太长需要换行的话则使用符号
如下:
LABEL multi.label1="value1"
multi.label2="value2"
other="value3"
说明:LABEL会继承基础镜像种的LABEL,如遇到key相同,则值覆盖
6.EXPOSE
功能为暴露容器运行时的监听端口给外部
但是EXPOSE并不会使容器访问主机的端口
如果想使得容器与主机的端口有映射关系,必须在容器启动的时候加上 -P参数
7.ENV
功能为设置环境变量
语法有两种
ENV <key><value>
ENV <key>=<value> ...
两者的区别就是第一种是一次设置一个,第二种是一次设置多个
8.ADD
一个复制命令,把文件复制到景象中。
如果把虚拟机与容器想象成两台linux服务器的话,那么这个命令就类似于scp,只是scp需要加用户名和密码的权限验证,而ADD不用。
语法如下:
ADD <src>... <dest>
ADD ["<src>",... "<dest>"]
<dest>路径的填写可以是容器内的绝对路径,也可以是相对于工作目录的相对路径
<src>可以是一个本地文件或者是一个本地压缩文件,还可以是一个url
如果把<src>写成一个url,那么ADD就类似于wget命令
如以下写法都是可以的:
ADD test relativeDir/
ADD test /relativeDir
ADD http://example.com/foobar /
尽量不要把<scr>写成一个文件夹,如果<src>是一个文件夹了,复制整个目录的内容,包括文件
9.COPY
一个复制命令
语法如下:
COPY <src>... <dest>
COPY ["<src>",... "<dest>"]
与ADD的区别
COPY的<src>只能是本地文件,其他用法一致
三.dockerfile文件案例
FROM node:14.15.5-alpine as NODE_BUILD
WORKDIR /build
RUN echo "https://mirrors.aliyun.com/alpine/v3.11/main/" >/etc/apk/repositories && echo "https://mirrors.aliyun.com/alpine/v3.11/community/" >>/etc/apk/repositories
# 添加Python
RUN apk --no-cache --virtual build-dependencies add \
python \
make \
g++ \
bash
# 复制源码
COPY . .
RUN rm -rf .git \
rm -rf .idea \
rm -rf node_modules \
rm -rf package-lock.json \
echo "sass_binary_site=http://npm.taobao.org/mirrors/node-sass/" > /root/.npmrc \
npm i --registry=https://registry.npmmirror.com \
npm run build
FROM nginx:1.23.2-alpine
MAINTAINER unizone.tech
LABEL orgnization="unizone corp" version=1.0
# 删除nginx 默认配置
RUN rm /etc/nginx/nginx.conf
RUN rm /etc/nginx/conf.d/default.conf
# 添加配置
ADD nginx.conf /etc/nginx/
# 添加配置default.conf
ADD default.conf /etc/nginx/conf.d/
# 生成dist文件夹下的文件copy到nginx下面去
COPY --from=NODE_BUILD /build/dist /usr/share/nginx/html/
EXPOSE 8080 8081
RUN echo "https://mirrors.aliyun.com/alpine/v3.11/main/" >/etc/apk/repositories && echo "https://mirrors.aliyun.com/alpine/v3.11/community/" >>/etc/apk/repositories && apk add --no-cache tzdata && echo 'Asia/Shanghai' >/etc/timezone && echo 'Asia/Shanghai' > /etc/timezone && ln -sf /usr/share/zoneinfo/Asia/Shanghai /etc/localtime
四.基于dockerfile构建镜像
- 用dockerfile文件创建镜像,在dockerfile文件目录下执行命令:
docker build -t 自定义镜像名 .
docker build -t nginx-test .
- 创建一个容器并运行命令:
docker run [可选参数] 镜像名 [向启动容器中传入的命令]
-d:会创建一个守护式容器在后台运行,这样创建容器后不会自动登录容器
-p:表示端口映射,即宿主机端口:容器中端口。 比如:-p 8080:80 就是将容器中的80端口,映射到主机中的8080端口
–name:为创建的容器命名。(默认会随机给名字,不支持中文字符!!!)
-v:表示目录映射关系,即宿主机目录:容器中目录。注意:最好做目录映射,在宿主机上做修改,然后共享到容器上;宿主机目录是绝对路径
–network=host:表示将主机的网络环境映射到容器中,使容器的网络与主机相同。每个 Docker 容器都有自己的网络连接空间连接到虚拟 LAN。使用此命令则会让容器和主机共享一个网络空间
-i:表示以《交互模式》运行容器
-t:表示容器启动后会进入其命令行。加入这两个参数后,容器创建就能登录进去。即分配一个伪终端。
docker run --name h5-dockerfile -p 666:80 -v C:\Users\dell\usr\local\nginx\www\h5Dockerfile\nginx.conf:/etc/nginx/nginx.conf -v C:\Users\dell\usr\local\nginx\www\h5Dockerfile\dist:/usr/share/nginx/html --privileged=true -d nginx-file