关注分享主机优惠活动
国内外VPS云服务器

docker/k8s/云

摘要:执行容器内部操作的任务。 作为容器执行驱动程序,它负责创建容器运行的命名空间、统计和限制容器的资源使用情况以及实际操作容器内的进程等。 通常,在启动时,它首先配置为运行一系列检查,然后打开供用户使用。

https://segmentfault.com/a/11... 容器、隔离和云的概述。 在这篇文章中,我们将详细介绍目前广泛使用的docker和k8s,并展示云建设的生态环境体系。

Docker1.与其他VM的比较

容器开发,请参考上面的文章了解更多信息。

>

典型图:VM和Container 相比之下,区别在于操作系统。

chroot 1979
Linux 虚拟服务器 2001
流程容器 2006
LXC 2008
Docker 2013
Windows 容器 2017
虚拟机 容器
分离 操作系统 内核命名空间
可分配、可测量 硬件页面映射 cgroups
移动性 快照、图像 AUFS
安全性 gresc patch

缺点

相对于KVM等虚拟化解决方案,隔离性还是有欠缺的。 。    所有容器通用的运行时库的网络管理相对简单。  这主要基于名称空间分离。   与 KVM 等虚拟化解决方案相比,cgroup 和 cpuset 提供的 CPU 能力很难衡量(这就是 dotcloud 主要收取内存安装费的原因)。   Docker 运行磁盘。 管理相对有限(磁盘配额)。  当用户进程死亡时,容器就会被销毁,不方便收集容器内的日志等用户数据。  

优点:

轻量级功能。    它启动很快并且使用很少的资源,因为docker只能加载每个容器的变化部分。   Docker不仅仅是一个容器,还是一个高级的容器引擎、一个应用程序部署平台和一个应用程序镜像存储。  

2. docker生态系统——————不仅仅是一个容器

镜像是一个包含执行环境的只读模板。

容器运行状态镜像,docker使用容器来运行应用程序

registry是存储容器镜像的仓库

一个Dockerfile包含一个构建集合的脚本图像的命令和参数

3. 执行过程

Docker守护进程通过Docker服务器模块接受Docker客户端请求,用引擎处理请求,然后根据它执行指定的作业。它作为创建和运行。 请求类型。 Docker守护进程运行在Docker主机上,负责创建、运行和监控容器,以及构建和存储镜像。

执行流程的作业的角色可能是:
从 Docker 注册表检索映像
通过图形驱动程序执行容器映像本地化操作
启动容器

Graphs
Graphs负责管理Docker架构中下载的容器镜像,记录下载的容器镜像之间的关系。
另一方面,Graph 存储包含版本信息的本地文件系统映像。 另一方面,它还通过GraphDB记录了所有文件系统镜像之间的关系。
GraphDB是一个基于SQLite构建的小型图数据库,实现节点命名和记录节点之间的关系。 它仅实现了大多数图形数据库所具有的一小部分,但提供了一个简单的接口来表示节点之间的关系。
Graph本地目录中存储的每个容器镜像的具体信息包括容器镜像元数据、容器镜像大小信息以及容器镜像所代表的具体rootfs。

networkdriver进行容器网络环境的配置
networkdriver的目的是完成Docker容器网络环境的配置,包括在Docker启动时为Docker环境创建一个网桥。 创建Docker容器时创建专用虚拟机的网卡设备。 它还为Docker容器分配IP和端口,与主机进行端口映射,并配置容器的防火墙策略。

Execdriver执行容器内部完成的执行工作
对于Docker容器来说,execdriver负责创建容器运行的命名空间,并负责创建容器运行的命名空间。容器运行,负责统计和限制,并负责容器内进程的实际执行。 在实现 execdriver 时,我们最初能够使用 LXC 驱动程序来调用 LXC 接口并操作容器配置和生命周期。 不过,execdriver 现在默认使用本机驱动程序,不再依赖 LXC。 这具体体现在ExecDriverflag参数中,该参数是在守护进程启动过程中加载的。 该参数在配置文件中设置为“native”。 这可以被认为是 Docker 1.2 版本的重大变化,或者是 Docker 跨平台实现的先驱。

libcontainer
在 Docker 架构中使用用Go语言设计和实现的库。 最初的设计意图是让库可以直接访问内核中容器相关的API,而不需要依赖依赖。
libcontainer的存在允许Docker直接调用libcontainer并最终操作容器的命名空间、cgroup、apparmors、网络设备和防火墙规则。 您不需要依赖 LXC 或任何其他包来完成这一系列操作。
libcontainer提供了一套标准接口来满足上层容器管理的需要。

Docker run流程(1)Docker客户端接收docker run命令。  解析请求并收集请求参数后,将HTTP请求发送到Docker Server。   HTTP请求方式为POST,请求URL为/containers/create? +xxx; (2) Docker服务器接受上述HTTP请求,并将其传递给mux.Router。   mux.Router 通过 URL 和请求方法来确定执行请求的具体处理程序。   (3) mux.Router将请求路由分发到相应的handler,具体为PostContainersCreate。   (4) Handler PostImageCreate 创建名为“create”的作业并开始运行该作业。   (5) 执行Container.Create操作,因为名为“create”的作业正在运行。 这需要获取容器映像以便为 Docker 容器创建 rootfs。 即调用graphdriver。   (6) Graph 驱动程序从 Graph 中检索创建 Docker 容器 rootfs 所需的所有映像。   (7) 所有图形驱动程序都是 rootfs。 镜像由Docker容器加载并安装到指定的文件目录中。   (8) 如果以上操作全部成功,并且没有返回错误或异常,则Docker客户端会收到Docker服务器返回的返回状态。然后发出第二个 HTTP 请求。    请求方法为“POST”,请求URL为“/containers/”+container_ID+“/start”。   (9)Docker服务器接收到上述HTTP请求,传递给mux.Router,通过URL和请求方法确定执行。    请求的特定处理程序。   (10) mux.Router 将请求路由分发到相应的处理程序,具体为 PostContainersStart。   (11) 在 PostContainersStart 处理程序中,创建名为“start”的作业并开始运行。   (12)名为“start”的作业完成前期配置工作后,开始配置和创建网络环境,并调用networkdriver。   (13)networkdriver必须为指定的Docker容器创建一个网络接口设备,并为其分配IP和端口。    当你设置防火墙规则时,相应的操作会转发到libcontainer的netlink包来完成。   (14)netlink完成网络环境的配置和Docker容器的创建。   (15)返回名为“start”的作业,执行一些辅助任务。  操作完成后,作业开始执行用户指令并调用execdriver。   (16) 调用execdriver初始化Docker容器内的运行环境,包括命名空间、资源控制和隔离、用户命令执行等。  相应的操作会转发给libcontainer来完成。    ;(17) 调用libcontainer,初始化Docker容器内部的运行环境,最后用户执行启动所需的命令。    

4.docker技术

命名空间分离

1.进程命名空间:每个命名空间都是独立的。 维护自己的进程号和父子关系结构。 子空间中的进程对父空间可见。 新fork出来的进程在父子命名空间中生成进程号
2.网络命令命名空间:完全独立的网络协议视图,用于网络隔离。 这包括网络设备接口、IPV4 IPV6协议栈、路由表、防火墙规则、socks等。 使用虚拟网络设备将容器内部的虚拟网卡绑定到容器的docker0上。 在 localhost 桥上
3. 与 ipc 命名空间、信号量、消息队列和共享内存的进程间交互。 位于同一 IPC 空间的事物可以交互,不同的事物则不能交互。
4.挂载命名空间与chroot类似,将进程放置并运行在特定目录中。 不同命名空间的进程可以引用不同的文件结构,文件目录是分开的。 chroot(PATH) 函数必须以 root 身份运行。 执行后,根目录将更改为PATH中指定的位置。
5. UTS命名空间 在UNIX Time-共享系统中,每个容器可以有独立的主机名和域名。 默认主机名是容器 ID。
6. 用户命名空间 每个容器可以有不同的用户和组ID,容器内特定的内部用户可以用来运行程序。 每个容器都有一个 root 帐户。

配额和衡量指标

1. cpu、io、mem 等:cgroups
2. 网卡
Docker 创建容器流程:
1.创建一对veth虚拟接口,分别放置在本地主机和新容器命名空间中
2、将虚拟接口连接到一个网卡 将本地主机端连接到默认的docker0 连接到网桥或者指定网桥并给它一个以 veth 开头的唯一名称。
3. 将容器一端的虚拟接口放入新容器中,并重命名为eth0。 ,仅在容器内可见
4. 从网桥的可用地址进行分配。 给eth0一个空闲地址(172.17.0.2/16),并将默认路由网卡设置为docker0的IP(172.17.42.1/)。 16)

vethpair是veth网卡发出的一对虚拟网卡,数据包可以直接到达它的p。你瞧,两者之间存在虚拟链接。 不同网络命名空间之间的交互
Veth网卡与传统以太网的唯一区别在于xmit接口。 向对等点发送数据会触发对等点的 Rx 进程。
3.磁盘/网络配额
虽然cgroup提供了IOPS等限制机制,但它们在用户可用的磁盘大小和网络带宽方面仍然非常有限。
对于磁盘/网络配额有两种想法:
1)。 使用 docker run -v 命令将外部存储挂载到容器目录。 配额受到主机方向的限制并在设备映射器驱动程序中更新。 使用真实设备可以让您更好地控制。
2)。 使用磁盘配额来限制AUFS的操作文件大小。 维护一个 UID 池,并在每次创建容器时从中获取用户名,使用该用户名在容器内和主机上创建用户,并在主机上使用设置配额来按 UID 设置用户名限制磁盘。 。 在网络上,docker使用veth。 ,您可以使用tc来控制主机上的veth设备。

便携式

REDHAT 使用 AUFS 作为 Docker 容器的文件系统来实现 AFUS 的驱动程序 (RHEL DEVIDE MAPPER) 功能。

这提供了以下好处:
1) 节省存储空间 - 多个容器可以共享基础镜像存储
2) 快速部署 - 部署多个容器时,基础镜像可以避免多份副本
br> 3) 节省更多内存 [ k4]多个容器共享基础镜像和操作系统的磁盘缓存机制,因此多个容器中的进程会命中缓存。内容概率大幅提升
4) 升级更方便 - 相比 copy-on-write 类型 FS,base-image 还可以挂载为可写,更新基础镜像。以及其上的容器
5) 允许您修改该目录中的文件而不更改基本 - 映像 -。 所有写操作都发生在最顶层的可写层,这显着增加了基础镜像可以共享的文件内容。
上述五项1-3可以通过copy-on-write FS来实现。 图4所示的实施例可以使用其他活接安装方法来实现。 只需要5个AUFS就可以很好的实现。 这就是为什么 Docker 从一开始就构建在 AUFS 之上。

AUFS工作流程:
1.Boot:bootfs+rootfs
bootfs(引导文件系统)主要包含引导加载程序和内核。 引导加载程序主要引导并加载内核。 如果启动成功,就会加载内核。 进入内存后,bootfs 被卸载。
rootfs(根文件系统)包含典型 Linux 系统上的标准目录和文件,例如 /dev、/proc、/bin 和 /etc。
2.典型的Linux启动后,首先将rootfs设置为只读,执行一系列检查,然后将其切换为“读写”以供用户使用。 Docker 还以只读模式加载 rootfs,并在初始化期间检查它。 然而,读写文件系统使用联合挂载挂载到只读rootfs上,允许重新配置底层FS(文件系统)。 设置为只读最重要的是,这套只读和可写的结构组成了容器运行时,每个FS称为一个FS层。
3.由于AUFS的性质,对只读层中的文件/目录的所有更改仅存在于上层可写层中。 这样,多个容器就可以共享一个只读层,不存在冲突。 因此,docker将只读层称为“image”-。 对于容器来说,整个rootfs都是read-write,但所有的改变实际上都是写入到最上面的可写层,并且镜像不会保存用户的状态。 ,可用于模板、重建和克隆。

5.部署平台

每次用户向Git服务器发送推送时,Jenkins(基于Java开发的持续集成工具)都会收到通知,并且Jenkins会触发构建。 Maven 是一种用 Java 编写的开源项目管理工具,也是最常用的构建工具,它构建所有相关代码,包括 Docker 镜像。
Maven 将完成的镜像推送到私有注册表进行存储。
最后,Jenkins 触发 Docker 注册表拉取,将镜像下载到本地主机并自动启动应用程序容器。

k8s

K8s是一个容器集群管理系统,提供应用程序部署、维护和扩展机制。 Kubernetes 可以轻松管理跨机器运行的容器化应用程序。 架构图如下:

标签是用于区分 Pod、服务和复制控制器的键值对。

Master 包括一个复制控制器和一个 API 服务器

复制控制器:
Kubernete 确保■ 即使节点出现故障,集群中指定的Pod 副本也会继续运行。 通过更改复制控制器上的副本数量来水平扩展或收缩正在运行的 Pod。 通过一一替换 Pod 来滚动更新服务。 标签维度的多个发布轨道

API Server的主要声明(包括Pod注册中心、控制器注册中心、服务注册中心、端点注册中心、Minion注册中心、绑定注册中心、RESTStorage、客户端)

Minion 注册表负责跟踪系统中存在的 Minion(主机)数量。 Kubernetes 集群:可以创建、检索、列出和删除
pod 注册表跟踪 Kubernetes 集群中运行的 pod 数量以及这些 pod 和 minions 之间的映射关系,并且可以创建、检索和列出,执行更新。 ,一个 Pod 删除操作。
......
端点注册中心创建服务端点如name:"mysql",endpoint:["10.10.1.1:1909","10.10.2.2:8834"],负责收集。 、get、list、update、delete、monitor
注册表绑定 一个绑定的pod绑定到一个主机
调度器对当前Kubernetes集群中所有Minion节点的资源(内存、CPU)负载进行调度收集和分析。 ,根据 Kubernetes 集群中的可用节点分发新创建的 Pod。

Kubelet
是 Kubernetes 集群中每个 Minion 和 Master API 服务器的连接点。 Kubelet 在每个 Minion 上运行。 是主API服务器和Minions之间的桥梁,接收主API服务器分配的命令和工作,与持久键值存储etcd、文件、服务器和http交互,并提供配置信息读取。 Kubelet的主要工作是管理Pod和容器的生命周期,包括Docker客户端、根目录、Pod Worker、Etcd客户端、Cadvisor客户端和健康检查器组件。

Proxy
就是为了解决一个问题。 外部网络旨在访问跨机器集群中容器提供的应用服务。 从上面的图3-3可以看到,每个Minion上也运行着一个代理服务。 Proxy 为 TCP/UDP 套接字提供代理。 每当创建服务时,代理主要从 etcd 获取服务和端点配置信息。 或者您可以从文件中获取它。 然后根据配置信息在Minion上启动代理进程并监听相应的服务端口。 ,当外部请求发生时,代理根据负载均衡器将请求分发到后端相应的容器中进行处理。

互动:

http://tiewei.github.io/cloud...

企业云架构图:

容器

静态容器
固定可访问IP,无动态漂移,容器内无代码,快速扩展,轻量级虚拟机,共享支持卷/块设备、日志收集与物理机相同。

有状态容器
K8s的有状态容器是弹性扩展的,可动态漂移,可编码,可快速扩展,支持共享卷/块设备(使用云盘),支持固定IP。 适合需要程序数据持久化的服务。

无状态容器
k8s 部署模型已可供使用。 它可以动态漂移,快速扩展,具有优良的弹性伸缩性。 仅支持共享卷(ceph等网络分布式磁盘)和日志。 远程集合、容器名称和IP不固定,适合无状态微服务。 仅支持云平台变更(无直接在线系统),不挂载云盘

数据

小ceph,大物理机映射=>所有网络抖动都替换为本地盘(数据必须分条迁移,无论日志还是数据,两种方案都可以)

网络

Docker中有很多虚拟网络的原生和插件实现。 中,一般用原生overlay较多
SDN overlay网络不太稳定(IP不受限制,所以漂移不受限制)=>物理网络(IP是tor[IP只有Tor切换,扩容后资源不平衡)
流量到达LB后,如果使用SDN,流量到SDN中心节点,将虚拟IP映射到物理IP,并找到物理IP的宿主机。 ,宿主机通过overlay与docker通信
对于直接到docker的物理网络,docker的ip就是分配的物理ip。 Tor引起的漂移是指IP没有变化时的漂移。 IP变更导致日志记录等问题

物理网络
容器ip2直接发送到物理机(ip1,ip2=》mac1。物理机再发送到ip转发。

Docker虚拟网络原理
1.同主机IP模式:以bridge为例
同一个网卡,即使是不同的网卡,如果配置了IP路由,则使用iptable。 drop:如果网桥 docker0 正在监听,则先连接到 docker0。来自 172.17.0.0/16 网段的出站数据包将传递到 MASQUERADE 进行处理(iptable NAT)。 MASQUERADE的处理方法是将数据包的源地址替换为主机的地址并发送,即进行网络地址转换(NAT)
外部网络的逆序:ip:port(不同的虚拟)IP是不同的是(绑定到端口),docker-proxy 监听所有端口,更改 ip1 并将其发送到 docker0,然后 docker0 与 ip1

2 通信。 跨主机覆盖
Docerk覆盖网络需要一个键-值数据库来存储网络状态信息。 包括网络、端点、IP 等。 Consul、Etcd、ZooKeeper 都是 Docker 支持的重要软件。 这里我们使用Consul。
不同主机:基于VxLAN。 VxLAN可以发送封装在UDP中的二层数据。 VxLAN提供与VLAN相同的以太网二层服务,但具有更高的可扩展性和灵活性。

外部网络:为每个网络创建 eth1 以连接到外部网络。 这个过程和桥接器上的docker0访问外网是一样的
主机内部的br0仍然直接连接到端点,并且添加了vxlan设备来连接其他主机。

VXLAN原理
vxlan将vxlan头封装在第二层包中,通过UDP发送给VTEP设备进行解封装(头中包含24位ID(以及带有相同ID可以通信)

Linux vxlan创建UDP套接字。 默认侦听端口 8472。
一旦收到vxlan数据包,就会根据其中的vxlan ID解压缩并转发到vxlan接口,并通过附加的Linux网桥转发到虚拟机。
Linux vxlan 正在接收来自虚拟机的消息当收到数据包时,将其封装成组播UDP数据包并由网卡发送。

未经允许不得转载:主机频道 » docker/k8s/云

评论 抢沙发

评论前必须登录!