前言
Docker 代表的容器技术是近两年的大热技术,和人工智能、区块链等热点不同,容器技术的门槛并不高,每一个开发、测试、运维人员都能在日常工作中掌握和使用,是当今 IT 从业人员的必备技能之一。
本文主要讲解 Docker 技术栈及其应用实践,从环境安装到容器、镜像操作以及生产环境如何部署开发的微服务应用,希望本文对大家学习 Docker 技术有所帮助。
什么是容器
为什么需要容器?虚拟化不是已经够了么?
对于还没有接触到容器技术的小伙伴们而言,可能觉得我们并没有必要花费大量的时间和经历去学习容器技术。也可能有很多小伙伴会觉得容器技术就是“新瓶装旧酒”,没啥学习的必要。
在 IT 技术中,KVM、VMware 等虚拟化技术已经做得很好了。为什么还要学习容器技术呢?这就要聊一下虚拟化技术在实际业务中存在的问题了:
虚拟化技术的确可以让我们更好的利用服务器资源,也可以在宿主机上安装多个不同的操作系统如 CentOS、Ubuntu 以及 Windows 等等,运行多套不同的应用。但可能我们就是为了运行一个简单的应用如 Nginx,却还要在虚拟机里运行一个完整的操作系统,内核和其它无关程序,这种做法资源利用不高。
所以我们希望更多的关注应用程序本身,而不再分精力去关注操作系统与无关程序,操作系统内核直接与宿主机共享。
为了实现上面的方案,我们就需要一种更加轻量级的虚拟化技术——容器技术。
什么是容器?
在生活中,瓶子、罐子、盆、试管、箱子等用来装东西的都是容器。
而在 IT 行业中,容器技术是一种轻量级的虚拟化技术。主要特点有:
- 轻量:只打包了需要的 bins/libs(也就是命令和库文件)。与宿主机共享操作系统,直接使用宿主机的内核。
- 部署快:容器的镜像相对虚拟机的镜像小。部署速度非常快,秒级部署,
- 移植性好:Build once,Run anywhere(一次构建,随处部署运行)。
- 资源利用率更高:相对于虚拟机,不需要安装操作系统,所以几乎没有额外的 CPU、内存消耗。
Docker 容器技术介绍
Docker 技术是目前最火热的能实现容器技术的软件,使用 Go(Golang)语言开发。其官方地址:
https://www.docker.com/
Docker 版本
2017 之前版本:
1.7、 1.8、1.9、1.10、1.11、1.12、1.13
2017 年的 3 月 1 号之后,Docker 的版本命名开始发生变化,同时将 CE 版本和 EE 版本进行分开。
Docker 社区版(CE):为了开发人员或小团队创建基于容器的应用,与团队成员分享和自动化的开发管道。docker-ce 提供了简单的安装和快速的安装,以便可以立即开始开发。docker-ce 集成和优化,基础设施。
- 17-03-ce
- 17-06-ce
- 18-03-ce
- 18-06-ce
- 18-09-ce
Docker 企业版(EE):专为企业的发展和 IT 团队建立。docker-ee 为企业提供最安全的容器平台,以应用为中心的平台。
PS:所以我们安装的时候,要安装 docker-ce,千万不要搞错了哦!
Docker 底层内核相关技术
Docker 容器本质上是宿主机的进程。可以把 Docker 容器内部跑的进程看作是宿主机的线程。
Docker 通过 NameSpace 实现了资源隔离,通过 CGroups 实现了资源限制。
NameSpace
Linux 内核实现 NameSpace 的一个主要目的就是实现轻量级虚拟化(容器)服务。在同一个 NameSpace 下的进程可以感知彼此的变化,而对外界的进程一无所知。
Control Group
控制组(CGroups)是 Linux 内核的一个特性,主要用来对共享资源进行隔离、限制、审计等。
只有能控制分配到容器的资源,才能避免多个容器同时运行时对宿主机系统的资源竞争。
控制组可以提供对容器的内存、CPU、磁盘 IO 等资源进行限制和计费管理。
LXC 与 Docker 区别
LXC 为 Linux Container 的简写,可以提供轻量级的虚拟化。
Docker 的底层就是使用了 LXC 来实现的。Docker 以 LXC 为基础,实现了更多更强的功能。
Docker 内容小结
容器属于操作系统虚拟化,属于 Paas,容器可看作是一种轻量级,进程级的虚拟机。
相比于 KVM 虚拟机的优势:
- 不需要安装 OS,和宿主机共享
- 镜像存储空间小
- 启动速度快(容器为秒级,虚拟机一般需要 10 秒左右)
- 移植性更好,更轻便
- 性能更好
Docker 是一个实现容器的软件,底层使用 LXC。Docker 主要使用 NameSpace 命名空间技术实现资源隔离,使用 CGroup 实现资源限制。
Docker 容器化部署以及 Docker 加速器配置
环境要求
- 建议直接在 Linux 宿主机上跑 Docker(当然也可以在虚拟机里跑 Docker)
- 不能直接在 Windows 上跑 Docker(因为 NameSpace,CGroup 是 Linux 内核特性,Windows 没有)
- Windows 上可以先跑 Linux 虚拟机,再在 Linux 虚拟机上跑 Docker
Docker 安装
默认情况下,我们使用 yum 安装时,官方源比较慢,所以建议大家使用国内 yum 源。
### wget https://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo -O /etc/yum.repos.d/docker-ce.repo
### yum install docker-ce -y
注意:要安装 docker-ce 版,不要安装 Docker(否则可能安装 1.13 老版本)。
修改 docker.service
### vim /usr/lib/systemd/system/docker.service
14 ExecStart=/usr/bin/dockerd -H fd:// --containerd=/run/containerd/containerd.sock
15 ExecStartPost=/sbin/iptables -P FORWARD ACCEPT 添加此行内容
启动服务
### systemctl start docker
### systemctl enable docker
查看版本信息
### docker -v
Docker version 19.03.8, build afacb8b
一个故事带你了解容器生态圈
Docker 技术的三大核心概念,分别是:
- 镜像(image): 镜像就是打包好的环境与应用。
- 容器(contanier): 容器就是运行镜像的实例。 镜像看作是静态的,容器是动态的。
- 仓库(repository): 存放多个镜像的一个仓库。
我们通过一个小故事(案例)来引入镜像、容器和仓库的概念,看下图:
假设我们有一天需要快速构建一个基于 Nginx/MySQL 等应用的项目:咱们第一件事是干嘛,按照以往的构建思路,肯定是一个软件一个软件安装,安装完成后,在进行关联配置。可能我们需要花费一天的时间来安装和准备我们所需的应用环境,是不是特别麻烦。
那现在我教你一种法术叫做 Docker 技术,其拥有 Docker 客户端、Docker 服务器端(Docker daemon)、Docker Hub 官方仓库。
Docker Hub 被称之为仓库,你所要的所有应用都在这里哦(要啥有啥)。你安装完 Docker 后,我们可以通过专门的 Docker 命令去仓库拉取镜像到服务器端,然后 Docker 会将镜像构建成容器,让其跑起来。以后你需要啥应用,只需要通过 Docker 这个法术就能轻松构建你想要的任何应用啦,这就是容器技术!
镜像管理与 Docker Hub 镜像仓库
镜像主要分为两类:
- 操作系统类(如 CentOS、Ubuntu)
- 应用程序类
查看镜像列表
通过 docker images
命令查看本地当前镜像列表,默认为空;使用 man docker-images
得到参数说明:
### docker images
搜索镜像
通过 docker search
查找官方镜像,使用 man docker-search
得到参数说明。
官方仓库地址:https://hub.docker.com/。
### docker search centos
拉取镜像
通过 docker pull
拉取(下载)镜像,使用 man docker-pull
得到参数说明:
### docker pull centos
### docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
centos latest 470671670cac 3 months ago 237MB
说明:
- 镜像下载默认是去找 Docker 官方仓库下载,它在国外网络,所以网速慢(有时甚至会访问不到)
- 镜像下载时显示的大小与最终
docker images
显示的大小不一致(因为有压缩算法,解压后就变大了)
问题:如果镜像 pull 非常慢,怎么解决?
- Docker 镜像加速器(国内有公司将官方仓库下载放到国内网络,我们指定从国内网络下载)
- 可以从网速好的宿主机上 pull 下来,然后导出给网速慢的宿主机导入
镜像加速器
### vim /etc/docker/daemon.json
{
"registry-mirrors": ["http://hub-mirror.c.163.com"]
}
### systemctl daemon-reload
### systemctl restart docker
删除镜像
通过 docker rmi
删除镜像,man docker-rmi
查看参数帮助:
### docker rmi centos
补充:还可以通过 docker rmi 镜像 ID
删除。
Docker Hub 镜像仓库
思考一个问题:刚才我们拉取的镜像都来自哪里?
答:Docker Hub。
Docker Hub 为最大的公开仓库,也就是官方仓库:
https://hub.docker.com/
搜索你想要的镜像,然后进去看看都有点啥:
这个还涉及到一个问题,CentOS 有多个版本,能不能指定我们下载的版本呢?当前可以啦,看下图:
看到这里你会发现,Docker 从 Hub 上拉取镜像是非常容易的,学会了吧。那接下来我们来聊聊镜像下载本地后,如何让它跑起来。
容器常见操作
查看容器列表
列表所有状态的容器,现在为空列表。使用 man docker-ps
得到参数说明:
### docker ps -a
运行容器
### docker run -it --name=c1 centos /bin/bash
[root@5a17b9560f33 /]### cat /etc/redhat-release
CentOS Linux release 8.1.1911 (Core)
[root@5a17b9560f33 /]### exit
exit
### docker start c1
c1
### docker attach c1
[root@5a17b9560f33 /]#
说明:
-
-i
等同于--interactive
,表示交互;-t
等同于--tty
,表示给一个终端用于交互。 -
--name=c1
用于指定容器名。 -
/bin/bash
指定 CentOS 镜像启动为容器时的启动命令,不指也可以,因为 CentOS 镜像的默认启动命令就是它。 -
cat /etc/redhat-release
看到 CentOS 8.1,而uname -r
查看的内核是 CentOS 7.6 的, 证明了容器使用的是 Docker host 的内核。 - exit 退出容器后,容器会变为 exit 状态。如果同时按下
ctrl+p+q
三个按键退出后,容器仍为 UP 状态。 -
docker attach
可连接进入容器内部交互, 但需要容器为启动状态。
或者用下面的命令连接上去交互式操作(连上去后,直接用 exit 退出,容器仍然为 UP 状态):
### docker exec -it c1 /bin/bash
如果需要获取容器的输出信息(如日志),我们可以通过 docker logs 容器名称或容器 ID
。
与容器交互拷贝文件
将本地 /etc/fstab 拷贝到 c1 容器的 /root/ 目录下: