目录
一.镜像说明
1.Docker 镜像中有没有内核
从镜像大小上面来说,一个比较小的镜像只有1MB多点或几MB,而内核文件需要几十MB, 因此镜像里面是没有内核的,镜像在被启动为容器后将直接使用宿主机的内核,而镜像本身则只提供相应的rootfs,即系统正常运行所必须的用户空间的文件系统,比如: /dev/,/proc,/bin,/etc等目录,容器当中/boot目录是空的,而/boot当中保存的就是与内核相关的文件和目录。
2.为什么没有内核
由于容器启动和运行过程中是直接使用了宿主机的内核,不会直接调用物理硬件,所以也不会涉及到硬件驱动,因此也无需容器内拥有自已的内核和驱动。而如果使用虚拟机技术,对应每个虚拟机都有自已独立的内核
3.容器中的程序后台运行会导致此容器启动后立即退出
Docker容器如果希望启动后能持续运行,就必须有一个能前台持续运行的进程,如果在容器中启动传统的服务,如:httpd,php-fpm等均为后台进程模式运行,就导致 docker 在前台没有运行的应用,这样的容器启动后会立即退出。所以一般会将服务程序以前台方式运行,对于有一些可能不知道怎么实现前台运行的程序,只需要在你启动的该程序之后添加类似于 tail ,top 这种可以前台运行的程序即可. 比较常用的方法,如 tail -f /etc/hosts
#httpd
ENTRYPOINT [ "/usr/sbin/apache2" ]
CMD ["-D", "FOREGROUND"]
#nginx
ENTRYPOINT [ "/usr/sbin/nginx", "-g", "daemon off;" ]
#用脚本运行容器
cat run_haproxy.sh
#!/bin/bash
haproxy -f /etc/haproxy/haproxy.cfg
tail -f /etc/hosts
tail -n1 Dockerfile
CMD ["run_haproxy.sh"]
4.docker 镜像的生命周期
5.镜像的制作方式
Docker 镜像制作类似于虚拟机的镜像(模版)制作,即按照公司的实际业务需求将需要安装的软件、相关配置等基础环境配置完成,然后将其做成镜像,最后再批量从镜像批量生成容器实例,这样可以极大的简化相同环境的部署工作.
Docker的镜像制作分为手动制作(基于容器)和自动制作(基于DockerFile),企业通常都是基于Dockerfile制作镜像
总结:
-
下载官方或者别人制作好的 镜像进行修改
-
利用dockerfile 生成自己的镜像
docker commit #通过修改现有容器,将之手动构建为镜像
docker build #通过Dockerfile文件,批量构建为镜像
二.手动构建镜像
1.基于容器手动制作镜像步骤
docker commit 格式
docker commit [OPTIONS] CONTAINER [REPOSITORY[:TAG]]
# REPOSITORY 软件名
# TAG 版本号
#选项 OPTIONS
-a, --author string: 指定提交镜像时的作者信息。格式通常是 "作者姓名 <电子邮件地址>",例如 "John Hannibal Smith hannibal@ateam.com"。
-c, --change list: 在创建的镜像上应用 Dockerfile 指令。这个选项允许你在提交镜像时执行额外的 Dockerfile 操作,类似于在 Dockerfile 中使用的指令。
-m, --message string: 提交时的提交消息,用于描述这次提交的目的或变更内容。
-p, --pause: 在提交镜像时是否暂停容器。默认情况下为 true,即在提交之前暂停容器。
#说明:
制作镜像和CONTAINER状态无关,停止状态也可以制作镜像
如果没有指定[REPOSITORY[:TAG]],REPOSITORY和TAG都为<none>
提交的时候标记TAG号: 生产当中常用,后期可以根据TAG标记创建不同版本的镜像以及创建不同版本的容器
基于容器手动制作镜像步骤具体如下:
下载一个系统的官方基础镜像,如: CentOS 或 Ubuntu
基于基础镜像启动一个容器,并进入到容器
在容器里面做配置操作
< 安装基础命令
< 配置运行环境
< 安装服务和配置服务
< 放业务程序代码提交为一个新镜像 docker commit
基于自己的的镜像创建容器并测试访问
2.实战案例
2.1 基于busybox 制作 httpd 镜像
docker run -it --name b1 busybox
#启动 busybox 容器
/ # hostname -i
/ # httpd --help 进入容器查看 httpd 的帮助
/ # mkdir /data/html -p 新建主站点目录
/ # echo testpage > /data/html/index.html 新建站点目录
/ # httpd -f -h /data/html/ -f 前台启动 -h 指定主站点
/ # httpd --help
BusyBox v1.36.1 (2023-05-18 22:34:17 UTC) multi-call binary.
Usage: httpd [-ifv[v]] [-c CONFFILE] [-p [IP:]PORT] [-u USER[:GRP]] [-r REALM] [-h HOME]
or httpd -d/-e/-m STRING
Listen for incoming HTTP requests
-i Inetd mode
-f Run in foreground #前台运行
-v[v] Verbose
-p [IP:]PORT Bind to IP:PORT (default *:80)
-u USER[:GRP] Set uid/gid after binding to port
-r REALM Authentication Realm for Basic Authentication
-h HOME Home directory (default .) #指定主站点, 否则是当前目录
-c FILE Configuration file (default {/etc,HOME}/httpd.conf)
-m STRING MD5 crypt STRING
-e STRING HTML encode STRING
-d STRING URL decode STRING
docker commit -a "zhou" -c 'CMD /bin/httpd -fv -h /data/html' -c "EXPOSE 80" b1 httpd-busybox:v1.0
docker images
启动制作好的容器
docker run -d --name web1 -P httpd-busybox:v1.0
# 将容器启动然后 -
docker port web1
#测试
curl 192.168.240.11:32770
2.2 基于官方镜像生成的容器制作tomcat镜像
下载启动 tomcat 容器
docker run -d -p 8080:8080 tomcat
#下载启动 tomcat 容器
修改容器
docker ps -a
docker exec -it 0b3c bash
# 进入容器
ls
cp -a webapps.dist/* webapps/
打包成镜像
docker commit -m "add webapps app" -a "zhou" 0b3c4d7e9e2e tomcat
docker images
启动镜像
docker run -d --name t1 -p 8081:8080 tomcat
2.3 基于CentOS的基础镜像利用yum安装手动制作nginx的镜像
启动容器
docker run -it --name c1 centos:latest bash
cat /etc/redhat-release
wget http://mirrors.aliyun.com/repo/Centos-8.repo
#在宿主机中下载 yum 文件
docker ps -a
#查看相关容器 id
docker cp Centos-8.repo e12b218ed4b3:/
#使用 docker cp 命令将文件拷贝进 容器
Successfully copied 4.61kB to e12b218ed4b3:/
yum install wget -y
#进入容器测试
安装nginx ,修改配置文件
yum install nginx net-tools vim -y
vim /etc/nginx/nginx.conf
daemon off;
#前台执行
#生成页面
echo "nginx page in docker" > /usr/share/nginx/html/index.html
打包成镜像
docker commit -a 'zhou' -m 'yum nginx' -c "EXPOSE 80 443" c1 centos:nginx-v1
启动容器
docker run -d -p 80:80 --name n1 centos:nginx-v1 nginx
alias rmc="docker ps -aq | xargs -n 1 docker rm -f"
#批量删除容器
三.自动构建镜像
1.Dockerfile使用详解
DockerFile 是一种被Docker程序解释执行的脚本,由一条条的命令组成的,每条命令对应linux下面的一条命令,Docker程序将这些DockerFile指令再翻译成真正的linux命令,其有自己的书写方式和支持的命令,Docker程序读取DockerFile并根据指令生成Docker镜像,相比手动制作镜像的方式,DockerFile更能直观的展示镜像是怎么产生的,有了DockerFile,当后期有额外的需求时,只要在之前的DockerFile添加或者修改响应的命令即可重新生成新的Docker镜像,避免了重复手动制作镜像的麻烦,类似与shell脚本一样,可以方便高效的制作镜像Docker守护程序 Dockerfile 逐一运行指令,如有必要,将每个指令的结果提交到新镜像,然后最终输出新镜像的ID。Docker守护程序将自动清理之前发送的上下文
请注意,每条指令都是独立运行的,并会导致创建新镜像,比如 RUN cd /tmp 对下一条指令不会有任何影响。
Docker将尽可能重用中间镜像层(缓存),以显著加速 docker build 命令的执行过程,这由 Using cache 控制台输出中的消息指示
1.1 Dockerfile镜像制作和使用流程
Dockerfile 构建过程
-
从基础镜像运行一个容器
-
执行一条指令,对容器做出修改
-
执行类似docker commit的操作,提交一个新的中间镜像层(可以利用中间层镜像创建容器进行调试和排错)
-
再基于刚提交的镜像运行一个新容器
-
执行Dockerfile中的下一条指令,直至所有指令执行完毕
1.2 Dockerfile文件的制作镜像的分层结构
1.3 Dockerfile文件格式
Dockerfile 是一个有特定语法格式的文本文件
dockerfile 官方说明: https://docs.docker.com/engine/reference/builder/
帮助: man 5 dockerfile
1.4 Docker 文件说明
-
每一行以Dockerfile的指令开头,指令不区分大小写,但是惯例使用大写
-
使用 # 开始作为注释
-
每一行只支持一条指令,每条指令可以携带多个参数
-
指令按文件的顺序从上至下进行执行
-
每个指令的执行会生成一个新的镜像层,为了减少分层和镜像大小,尽可能将多条指令合并成一条指令
-
制作镜像一般可能需要反复多次,每次执行dockfile都按顺序执行,从头开始,已经执行过的指令已经缓存,不需要再执行,如果后续有一行新的指令没执行过,其往后的指令将会重新执行,所以为加速镜像制作,将最常变化的内容放下dockerfile的文件的后面
1.5 Dockerfile 相关指令
dockerfile 文件中的常见指令:
常用指令 | 含义 |
---|---|
FROM |