Docker常用命令

容器创建命令

docker create 
docker run

常用参数:

- i 让容器的标准输入保持打开

- t 分配一个伪终端

- d 容器处于守护进程运行

-- name 设置容器的名字

- p 可以映射宿主机端口至容器端口,如 -p 8080:8081,左边为宿主机端口,右边为容器端口

- v 可以挂在宿主机目录至容器目录,如-v/data:/tmp/data, 左边为宿主机目录,右边为容器目录

容器管理命令

docker ps

docker ps 是查看正在运行的容器,可以添加-a 参数,查看所有容器的信息。

停止容器

docker stop

启动容器

docker start

重启容器

docker restart

删除容器

docker rm

如果是正在运行的容器,会提示删除失败,可以通过 -f 参数强制删除。

docker rm -f my_ubuntu

查看容器日志

docker logs

暂停容器

docker pause

恢复暂停的容器

docker unpause

进入容器

如果我们创建容器时,使用了 -d 参数,那么容器就会在后台运行。

docker attach命令

docker attach

该命令用于连接容器(进入容器) 如docker attach my_ubuntu 进入名为my_ubuntu的容器 docker attach连接容器,有一个致命的缺点,那就是当多个窗口同时attach到同一个容器时,所有窗口都会同步显示,当某个窗口阻塞了,那么所有的窗口都会被阻塞掉。例如,我通过两个终端attach到这个my_ubuntu容器,所有的操作都会被同步

docker exec命令 该命令不是连接容器,而是在容器中执行命令,用法如下:

docker exec -it

其中是需要执行的命令

如在my_ubuntu容器下执行 /bin/bash 命令:

docker exec -it my_ubuntu /bin/bash

/bin/bash 这个命令,其实就是运行一个bash终端,所以我们就可以通过在容器中执行 /bin/bash命令来连接容器。

查看容器变更

容器也是支持查看变更的内容的

docker diff

提交容器

Docker也可以像git一样,可以把变动提交为新的镜像。命令如下:

docker commit repo/name:tag

提交后的镜像,可以推送到仓库上,方便测试部署等。

优雅地写Dockerfile

注意点减少构建时间

构建顺序影响缓存的利用率:镜像的构建顺序很重要,当向Dockerfile中添加文件,或者修改其中的某一行时,那一部分的缓存会失效,该缓存的后续步骤都会中断,需要重新构建。所以优化缓存的最佳方法是把不需要经常更改的行放在最前面,更改最频繁的行放到最后面

只拷贝需要的文件,防止缓存溢出;当拷贝文件到镜像中时,尽量只拷贝需要的文件,切忌使用 COPY . 指令拷贝整个目录。

最小化可缓存的执行层;每一个 RUN 指令都会被看作是可缓存的执行单元。太多的 RUN 指令会增加镜像的层数,增大镜像体积,而将所有的命令都放到同一个 RUN 指令中又会破坏缓存,从而延缓开发周期。

减小镜像体积

删除不必要依赖:apt 可以通过添加参数 -–no-install-recommends 来确保不会安装不需要的依赖项

删除包管理工具缓存

可维护性

尽量使用官方镜像

使用更具体的标签(尽量不要使用latest标签)

使用体积最小的基础镜像(alpine风格的镜像是基于体积更小的Alpine Linux发行版制作的,体积更小)

重复利用

在一致的环境中从源代码构建(源代码是构建Docker镜像的最终来源,Dockerfile里面只提供了构建步骤)

在单独的步骤中获取依赖项

使用多阶段构建来删除构建时的依赖项(多阶段构建可以由多个 FROM 指令识别,每一个 FROM 语句表示一个新的构建阶段,阶段名称可以用 AS 参数指定。)

总结瘦身方法代码自查删除不需要的代码和依赖包(可以查看requirement.txt文件中是否有已经不需要的包,另外可以使用.dockerignore)

更换更小的官方基础镜像 比如:

REPOSITORY TAG IMAGE VIRTUAL SIZE
alpine latest ..... 4.799MB
debian latest ..... 84.98MB
ubuntu latest ..... 188.3MB
centos latest ..... 210MB

减少层 减少Dockerfile文件中RUN的次数

多阶段构建 还不太懂,待了解

另外一些奇淫技巧使用dive查看 docker 镜像的层,可以帮助你分析减少镜像体积

使用docker-slim 可以自动帮助你减少镜像体积,对于 Web 应用较为有用

安装软件时去除依赖

# ubuntu
apt-get install -y — no-install-recommends
#alpine
apk add --no-cache && apk del build-dependencies
# centos

yum install -y ... && yum clean all使用--flatten参数,减少层(不推荐)

使用docker-squash压缩层

Dockerfile常用操作

镜像的定制实际上就是定制每一层所添加的配置、文件。如果我们可以把每一层修改、安装、构建、操作的命令都写入一个脚本,用这个脚本来构建、定制镜像。这个脚本就是Dockerfile

FROM指定基础镜像

FROM 就是指定基础镜像,因此一个 Dockerfile 中 FROM 是必备的指令,并且必须是第一条指令。

FROM ubuntu
.....

如果你以scratch为基础镜像的话,意味着你不以任何镜像为基础,接下来所写的指令 将作为镜像第一层开始存在

RUN 执行命令

RUN指令是用来执行命令行命令的。由于命令行的强大能力,RUN指令在定制镜像时是最常用的指令之一。 格式: 1. Shell格式 RUN 2. exec格式:RUN ["可执行文件","参数1","参数2"],这更像是函数调用中的格式

可以使用&&对多个不同命令进行串联。这样就不需要多次RUN

FROM debian:jessie
RUN buildDeps='gcc libc6-dev make' \
&& apt-get update \
&& apt-get install -y $buildDeps \
&& wget -O redis.tar.gz "http://download.redis.io/releases/redis-3.2.5.tar.gz" \
&& mkdir -p /usr/src/redis \
&& tar -xzf redis.tar.gz -C /usr/src/redis --strip-components=1 \
&& make -C /usr/src/redis \
&& make -C /usr/src/redis install \
&& rm -rf /var/lib/apt/lists/* \
&& rm redis.tar.gz \
&& rm -r /usr/src/redis \
&& apt-get purge -y --auto-remove $buildDeps

这里行尾添加\ 的命令换行方式,以及可以以#注释。 上述语句在最后还清理了apt缓存文件。 这是很重要的一步,镜像是多层存储,每一层的东西并不会在下一层被删除,会一直跟随着镜像。因此镜像构建时,一定要确保每一层只添加真正需要添加的东西,任何无关的东西都应该清理掉。

构建镜像

使用docker build命令进行镜像构建,格式为:

docker build [选项]

镜像上下文构建

当我们进行镜像构建的时候,并非所有定制都会通过RUN指令完成,经常会需要将一些本地文件复制进镜像,比如通过COPY指令,ADD指令等。而docker build命令构建镜像其实并非在本地构建,而是服务端,也就是Docker引擎中构建。那么在这种客户端/服务端的架构中,如何才能让服务端获得本地文件呢?

这就引入上下文的概念。当构建的时候,用户会指定构建镜像上下文的路径,docker build命令得知这个路径后,会将路径下的所有内容打包,然后上传给Docker引擎,这样Docker引擎收到这个上下文包后,展开就会获得构建镜像所需的一切文件。

COPY ./package.json /app/

注意:COPY 这类指令中的源文件的路径都是相对路径。

这并不是要复制执行 docker build 命令所在的目录下的 package.json,也不是复制 Dockerfile 所在目录下的 package.json,而是复制 上下文(context) 目录下的 package.json。

一般来说,应该会将 Dockerfile 置于一个空目录下,或者项目根目录下。如果该目录下没有所需文件,那么应该把所需文件复制一份过来。如果目录下有些东西确实不希望构建时传给 Docker 引擎,那么可以用 .gitignore 一样的语法写一个 .dockerignore,该文件是用于剔除不需要作为上下文传递给 Docker 引擎的。

参考文献