每天晚上回到寝室都没事做,一直对Docker很好奇,正好学一下《Docker--从入门到实践》做此笔记。
镜像操作
docker images -f dangling=true
显示虚悬镜像,所谓虚悬镜像是当拉去了一个新版本的镜像后,原来的镜像就没有标签名,称之为虚悬镜像。
docker rmi $(docker images -q -f dangling=true)
删除虚悬镜像
docker images tag_name
显示符合tag_name条件的所有镜像
docker run --name webserver -d -p 80:80 nginx
生成一个名字为webserver的容器,以nginx镜像生成,端口映射到本机的80端口,这样可以在http://localhost访问
- -p <宿主端口>: <容器端口>:端口映射,将容器内端口(右)映射到主机(左)。
docker diff container_name
查看容器的文件具体的改动(相对于镜像)
docker commit [选项] <容器ID或容器名> [<仓库名> [:<标签>]]
docker commit \
> --author "[email protected]" \
> --message "modify default index" \
> webserver \
> nginx:v2
sha256:f3fbd32761750b4b23e509085db2639d0651b1e88ff27a9b5a697a6c03d8a1f2
保存修改到新镜像中,其中nginx:v2 v2为新镜像的标签,但是会造成较多垃圾,使镜像极为臃肿。
使用Dockerfile定制镜像
行尾\表示换行,#注释
# Dockerfile
From nginx
Run echo "233
" > /usr/share/nginx/html/index.html
From 指定基础镜像,必须为第一条指令,其中 scratch为虚拟镜像,表示从零开始构建;Run执行命令,
- shell格式 如上
- exec格式 Run ["可执行文件","参数1","参数2"],类似函数调用
Dockerfile中每条指令新建一层,Union FS最大层数127。
docker build -t nginx:v3 .
使用当前文件夹中的Dockerfile定制镜像(不要忽视最后的.,它用来指定上下文目录,表示将当前目录下所有文件发送到服务端)
docker build 构建镜像并非在本地而是在服务端,上下文概念就是为了让服务端获取本地文件,会将上下文目录下所有文件打包发送到服务端
➜ docker docker build -t nginx:v3 . # 或 ./Dockerfile
Sending build context to Docker daemon 2.048 kB
Step 1/2 : FROM nginx
---> 6b914bbcb89e
Step 2/2 : RUN echo "23333
" > /usr/share/nginx/html/index.html
---> Running in 04b53f187929
---> eb25b3b9aca7
Removing intermediate container 04b53f187929
Successfully built eb25b3b9aca7
如果在上下文目录下增加文件,相应的发送数据也会变大
➜ docker docker build -t nginx:v3 .
Sending build context to Docker daemon 11.78 kB
Step 1/2 : FROM nginx
---> 6b914bbcb89e
Step 2/2 : RUN echo "23333
" > /usr/share/nginx/html/index.html
---> Using cache
---> eb25b3b9aca7
Successfully built eb25b3b9aca7
可以看到文件由2.048kB变到了11.78kB
docker build [选项] <上下文路径>
- -f file_name 指定此文件为Dockerfile
➜ docker docker build -t nginx:v3 -f ./config . # 将上面的Dockerfile重命名为config
Sending build context to Docker daemon 2.048 kB
Step 1/2 : FROM nginx
---> 6b914bbcb89e
Step 2/2 : RUN echo "23333
" > /usr/share/nginx/html/index.html
---> Running in 04dd44d844d1
---> 17e8d87be6c3
Removing intermediate container 04dd44d844d1
Successfully built 17e8d87be6c3
docker build还支持
-
docker build URL
从给出的URL构建,一般是从github
-
docker build context.tar.gz
从给定的压缩包构建
-
docker build - < Dockerfile
从标准输入读取Dockerfile构建
-
docker build - < context.tar.gz
从标准输入读取压缩包构建
Dockerfile 命令
COPY <源路径> <目标路径>
将文件config从上下文目录中源路径的文件复制到新的一层目标路径中,源文件的元数据都会被保留如读写权限支持通配符
ADD <源路径> <目标路径>
源文件的元数据不会被保留,且会自动解压压缩文件。根据官方准则,只在需要自动解压时使用ADD
CMD
- shell 格式:CMD <命令>
- 参数列表格式:CMD ["参数1"...]。在指定了ENTRYPOINT指令后用CMD指定具体的参数
- exec格式:CMD ["可执行文件","参数1"...]
实际运行时 shell格式会被变更成exec格式,如
CMD echo $HOME
会被变更为
CMD ["sh","-c","echo $HOME"]
Docker是进程,需要在前台运行
ENTRYPOINT入口点
它的格式和CMD相同。当指定了 ENTRYPOINT 后, CMD 的含义就发生了改变,不再是直接的运行其命
令,而是将 CMD 的内容作为参数传给 ENTRYPOINT 指令,换句话说实际执行时,将变为:
""
使用场景1:像命令一样使用镜像
#Dockerfile
FROM ubuntu:16.04
RUN apt-get update \
&& apt-get install -y curl \
&& rm -rf /var/lib/apt/lists/*
ENTRYPOINT [ "curl", "-s", "http://ip.cn" ]
使用上面的配置文件构建镜像
docker build -t myip .
使用时
$ docker run myip (-i)
当前 IP:61.148.226.66 来自:北京市 联通
可以增加参数(如果是使用CMD是不行的)
ENV设置环境变量
ENV
ENV= =
一次定义多层使用
ARG 构建参数
ARGM<参数名>[=<默认值>]
ARG设置的是构建环境的环境变量
VOLUME定义匿名卷
VOLUME ["<路径1>","<路径2>"]
VOLUME <路径>
容器运行时应该保持容器存储层不发生写操作,对于数据库类需要动态保存数据的应用,它的数据文件应该保存在卷(Volume)中,为了防止运行时用户忘记将动态文件所保存目录挂载为卷,在 Dockerfile 中,我们可以事先指定某些目录挂载为匿名卷,这样在运行时如果用户不指定挂载,其应用也可以正常运行,不会向容器存储层写入大量数据。
VOLUME /data
运行时/data会自动挂载为匿名卷,任何向 /data 中写入的信息都不会记录进容器存储层。
docker run -d -v mydata:/data xxxx
在这行命令中,就使用了 mydata 这个命名卷挂载到了 /data 这个位置,替代
了 Dockerfile 中定义的匿名卷的挂载配置。
WORKDIR 指定工作目录
WORKDIR <工作目录路径>
要注意Dockerfile中执行的命令都不在同一个进程执行环境
RUN cd /root
RUN touch text.txt
这里第一个RUN命令它的工作目录是/root,执行第二个命令时它的工作目录是默认目录而不是/root
USER 指定当前用户
USER <用户名>
更改以后层的运行用户,类似于WORKDIR
HEALTHCHECK健康检查
HEALTHCHECK [选项] CMD <命令> :设置检查容器健康状况的命令
HEALTHCHECK NONE :如果基础镜像有健康检查指令,使用这行可以屏蔽掉
其健康检查指令
- --interval=<间隔> :两次健康检查的间隔,默认为 30 秒;
- --timeout=<时长> :健康检查命令运行超时时间,如果超过这个时间,本次
健康检查就被视为失败,默认 30 秒; - --retries=<次数> :当连续失败指定次数后,则将容器状态视为
unhealthy ,默认 3 次。
#Dockerfile
FROM nginx
RUN apt-get update && apt-get install -y curl && rm -rf /var/lib
/apt/lists/*
HEALTHCHECK --interval=5s --timeout=3s \
CMD curl -fs http://localhost/ || exit 1
五秒检查一次容器运行情况,如果三秒没有回应报错
运行后
docker ps
显示运行状态
ONBUILD 为他人做嫁衣裳
ONBUILD <其它指令>
ONBUILD 是一个特殊的指令,它后面跟的是其它指令,比如 RUN , COPY 等,
而这些指令,在当前镜像构建时并不会被执行。只有当以当前镜像为基础镜像,去
构建下一级镜像的时候才会被执行。
docker 删除镜像
docker rmi [选项] <镜像1> [<镜像2>...]
docker rmi **短ID**
- docekr rmi <镜像名:标签>
Docker 镜像部分结束
docker run
docker run -it --rm ubuntu:14.04 bash
运行容器,启动镜像中的bash进行交互式操作并在退出时删除这个容器
- i : 交互式操作,启动的行为完成后进程不会立即结束
- t :terminal,启动终端,这里指定为bash
在执行docker run这个命令时Docker在后台进行的标准操作有:
- 检查本地是否存在指定的镜像,不存在就从公有仓库下载
- 利用镜像创建并启动一个容器
- 分配一个文件系统,并在只读的镜像层外面挂载一层可读写层
- 从宿主主机配置的网桥接口中桥接一个虚拟接口到容器中去
- 从地址池配置一个 ip 地址给容器
- 执行用户指定的应用程序
- 执行完毕后容器被终止
docker run -d ubuntu:14.04 ××××××
在后台执行容器,执行后会返回容器ID可以使用docker logs ID/name查看输出信息,如果没注意id,可以使用docker ps查看正在运行中的容器ID
- docker stop 查看终止状态的容器可以使用docker ps -a
- docker restart 重启正在运行的容器
- docker attach 进入正在运行的容器,不适合多人协作,nsenter是更好的选择.
docker的导入和导出
docker export ID/name >XXXX.tar
导出容器到文件
docker import XXXX.tar name/ubuntu:tag
从文件导入容器
注:用户既可以使用 docker load 来导入镜像存储文件到本地镜像库,也可以
使用 docker import 来导入一个容器快照到本地镜像库。这两者的区别在于容
器快照文件将丢弃所有的历史记录和元数据信息(即仅保存容器当时的快照状
态),而镜像存储文件将保存完整记录,体积也要大。此外,从容器快照文件导入
时可以重新指定标签等元数据信息。
docker rm
删除一个终止状态的容器,要删除正在运行的容器,加上-f参数,会发送终止命令给容器继而删除
docker rm $(docker ps -a -q)清除所有终止容器
docker hub
- docker login输入账号信息
- 无需登录就可用docker search 查找Docker hub的镜像
略过了docker 私有仓库,用到了再看。明天更新docker 数据管理
数据卷
数据卷是可供一个或多个容器使用的特殊目录,绕过了UFS
- 数据卷可以在容器之间共享和重用
- 对数据卷的修改会立马生效
- 对数据卷的更新,不会影响镜像
- 数据卷默认会一直存在,即使容器被删除
*数据卷的使用,类似于 Linux 下对目录或文件进行 mount,镜像中的被指定
为挂载点的目录中的文件会隐藏掉,能显示看的是挂载的数据卷 *
docker run -v /myvol ubuntu
挂在一个数据卷到容器的/myvol目录
docker run -v /home/dvwang/docker/test:/home ubuntu
挂载主机的 /home.../test到容器的/home。目录和文件都可以必须是绝对路径 Dockerfile因为移植不能使用这个功能
docker run -v /home/dvwang/docker/test:/home:ro ubuntu
同上,只是挂载为只读
docker inspect ID/name
查看数据卷的具体信息
docker run -d -v /dbdate --name dbdata mongo
创建一个以MongoDB镜像为基础名字为dbdata的容器,在其他容器中使用 --volume-from(可使用多个)来挂载dbdata中的数据卷
利用数据卷来备份和恢复暂时略过
Docker网络功能
-P|-p端口映射功能
- -p 指定要映射的端口
- -P 随机映射一个49000~49900的端口到容器开放的网络端口
➜ ~ docker run -d -P nginx
➜ ~ docker ps -l
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
fe84de5fe039 nginx "nginx -g 'daemon ..." 17 seconds ago Up 16 seconds 0.0.0.0:32769->80/tcp, 0.0.0.0:32768->443/tcp gifted_darwin
可以看到主机的32769端口被映射到容器的80端口
映射到指定地址的端口
➜ ~ docker run -d -p 127.0.0.1:5000:5000 nginx
➜ ~ docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
473d9de29644 nginx "nginx -g 'daemon ..." 23 seconds ago Up 23 seconds 80/tcp, 443/tcp, 127.0.0.1:5000->5000/tcp laughing_keller
fe84de5fe039 nginx "nginx -g 'daemon ..." 29 minutes ago Up 29 minutes 0.0.0.0:32769->80/tcp, 0.0.0.0:32768->443/tcp gifted_darwin
映射到指定地址的任意端口
➜ ~ docker run -d -p 127.0.0.1::2000 nginx
9463fc6a4c92e87d9118259c986d282c2bd478ec7b6d551e47622c4465643029
➜ ~ docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
9463fc6a4c92 nginx "nginx -g 'daemon ..." 3 seconds ago Up 3 seconds 80/tcp, 443/tcp, 127.0.0.1:32770->2000/tcp goofy_kalam
473d9de29644 nginx "nginx -g 'daemon ..." 7 minutes ago Up 7 minutes 80/tcp, 443/tcp, 127.0.0.1:5000->5000/tcp laughing_keller
fe84de5fe039 nginx "nginx -g 'daemon ..." 36 minutes ago Up 36 minutes 0.0.0.0:32769->80/tcp, 0.0.0.0:32768->443/tcp gifted_darwin
docker port ID
查看端口使用情况
注意
- 容器有自己的内部网络和 ip 地址(使用 docker inspect 可以获取所有的
变量,Docker 还可以有一个可变的网络配置。) - -p 标记可以多次使用来绑定多个端口
容器互联
复习一下docker run
docker run --name myimage image
使用images创建容器并命名为myimage
--link可以让容器之间安全的通信
下面的因为目前实在用不到并且看不懂。暂时不看