zoukankan      html  css  js  c++  java
  • 1. Docker容器技术基础入门

    容器

    容器是一种基础工具;泛指任何可以用于容纳其他物品的工具,可以部分或完全封闭,被用于容纳、储存、运输物品;物体可以被放置在容器中,而容器则可以保护内容物。

    LXC

    全称:LinuX Container

    虚拟化和容器之间的关系

    虚拟化常用实现形式有两种:

    • 主机级虚拟机化(虚拟化整个完整的物理硬件平台,如:VMware Workstation ):
      • Type-I:直接硬件基础上安装一个虚拟机管理器Hypervisor,在这之上在安装虚拟机;
      • Type-II:在物理机上装一个宿主机操作系统,在宿主机的基础上装一个VMM虚拟机管理器,然后再创建虚拟机,例如:VMware Workstation、VirtBox、KVM
    • 容器级虚拟化

    主机级虚拟化的实现机制是,首先得有硬件平台,而后有 VMM,用户需要在虚拟机之上部署一个完整的操作系统,包括内核、用户空间,而后在用户空间跑应用程序进程。而运行内核不是主要的目的,内核核心作用在于资源分配和管理。在用户空间跑的应用进程才是真正实现生产力的。 所以说,真正能产生生产力的是用户空间的应用进程,而不是出于通用目的而设计的资源管理平台系统内核,而在虚拟化中,内核又是不可获取的存在。原因在于在一组硬件平台上使用软件程序,软件程序基本都是针对内核的系统调用和库调用研发的,如果不安装内核、不安装库、不安装运行环境,是没办法运行应用程序的,所以内核必不可少。更何况,一旦有用户空间以后,要运行很多进程,这些进程为了协调,也必须要由内核来实现。

    假设创建一个虚拟机的目的就为了运行一个单一的Web服务,为此却不得不安装内核安装用户空间,然后跑Web服务,这样的代价就比较大。而且更主要的是,一个进程为了运行,需要实现两级调度和分派,虚拟机有自己的内核,此内核就已经实现了,资源分派,IO调度,而虚拟机的本身也是被宿主机内核管理的一个抽象层而已,因此还需要被宿主机内核或者是 Hypervisor 再需要调度和管理一次,这之间的调度和开销就不言而喻了。 这种传统的主机虚拟化技术确实能够在一组硬件之上实现所谓的跨系统环境的隔离和调试各种需求,但带来的资源开销也是不容忽视的,而很多时候创建虚拟机的目的仅仅是为了运行有限的一个或几个富有生产的进程而已,而为此付出的代价有点大了,既然如此,减少中间层、减少中间环节是有效提高效率的方式。比如说,现在需要提升效率的话,能不能把虚拟机中间的内核抽掉,只保留进程,但是使用虚拟机是目的之一也是为了环境的隔离。比如同时运行nginx,都监听80端口,一台主机是做不到的。有了虚拟机之后,开两台虚拟机在同一个宿主机上运行两个nginx是完全没问题的,这是一种需求。 所以创建虚拟机的目的,假如只是为了运行进程为什么不直接放在宿主机上运行,而非要放在虚拟机中,目标是为了资源的隔离使用,就算 tomcat 在虚拟机中吃掉了所有的CPU和内存资源,都不会影响到其他虚拟机系统进程,最多损坏的只是那一个虚拟机,所以隔离才是追求的目标。所以抽掉一层内核,但又不能让进程直接跑在同一个用户空间,而是需要让每一个进程或每一组进程彼此之间是相互隔离的,就像类似运行两个虚拟机的进程互相不可达一样,互不干扰,而共享同一组底层硬件资源而已。

    如图,在虚拟隔离环境管理器之上创建出一个个隔离环境,让需要隔离出来运行的进程跑在每个隔离环境中,进程是跑在用户空间的,所以这里的隔离是在隔离用户空间。通常来讲,用户空间是只有一组的,现在期望实现的是将这个用户空间隔离成多组,彼此之间互相不干扰,一个用户空间内只运行一个进程或部分进程。但无论怎么隔离,这其中必定有一个特权空间,一般是第一个。通过这个特权空间来管理其他隔离空间。这些众多的隔离空间能够共享同一个内核,大家都被同一个内核管理,但是这些隔离空间运行时能够看到的边界却是自己所属用户空间的边界。这种隔离显然没有主机级虚拟化隔离的彻底。这些隔离空间拿来放进程的,给进程提供运行环境并且还能够保护其内部的进程不受其他进程的干扰,所以这就是容器。 这就是在 Linux 中经常提到的 容器技术。

    容器技术最早出现在 FreeBSD上,当年叫 Jail ,其实目的只是为了运行一进程不受其他的干扰。就算这个进程出现bug故障也不会对其他系统造成干扰。这种隔离带来的是安全运行的初衷。 后来 Jail 这种技术就拿到Linux中叫:vserver,类似与 chroot

    一个隔离空间主要实现的目标是隔离,任何进程运行在这个隔离空间中都认为自己是唯一运行在当前这个内核之上用户空间的进程,所能看到的其他进程也都是。

    一个系统运行起来可以看作两棵树:

    1. 文件系统树
    2. 进程树

    在Linux 进程管理界,从来都是白发人送黑发人,子进程由它的父进程创建,而子进程终止并回收也是由父进程来实现的。如果 init 结束了, 它就会把所属它的所有子进程全部终止。

    一个隔离用户空间应该看到的以下组件:

    1. UTS - 主机名和域名
    2. 根文件系统
    3. IPC(进程间通信专用通道)在同一个隔离空间内是可以通信的,跨隔离空间是无法通信的。
    4. PID 需要为每个隔离空间伪装一个PID为1的进程。
    5. User、Group 需要单独做隔离
    6. Network

    Linux 开始在内核级把这些资源作为可以切分为多个相互隔离的空间,就称为:名称空间。

    意味着在同一个内核之上,创建出多个名称空间,在这些名称空间之上把 UTS 资源让每个名称空间和其他名称空间隔离。

    为了支撑容器机制的实现,Linux内核级对以上 6种名称空间的切分原生支持,叫做 namespaces ,直接通过系统调用向外输出。整个 Linux 领域的容器化技术就是靠内核级的 6 个 namespaceschroot 来实现的。

    在容器级虚拟化中,隔离的名称空间是工作在同一内核之上的,如果隔离空间故障占用大量系统资源,会对其他隔离空间造成影响。因此,内核级还必须实现一个功能来限制每一个用户空间中的进程的所有可用资源总量。比如:按CPU来分配。而这个功能在内核叫:CGroups

    • Cgroups
    • namespaces
    • chroot

    有了 Cgroupsnamespaces 就可以愉快的使用容器了, 实际上容器的隔离能力相比主机级虚拟化来说,差很多。毕竟多个容器同属于一个内核,只是在内核空间强行设置了边界,而不像主机级虚拟化,大家原本就不属于同一个内核,容器的隔离远不如主机级虚拟化好。因此为了避免这种问题,实用了类似 selinux 等这样的机制来加强容器的边界管理。

    为了容器更加的易用,将所有的容器实现的工具打包称为了: LXC(LinuX Container)

    LXC 是最早将容器技术用一组简易实用的工具和模板来极大的简化了容器技术使用的一种方案。LXC 在容器技术的推广上功不可没,但依然存在很多门槛。

    1. 理解LXC各种工具
    2. 需要定制模板
    3. 每一个用户空间都是安装生成的,生成数据文件持久存储的问题
    4. 批量创建用户空间

    Docker

    LXC 虽然极大的简化了容器的使用,但是比起虚拟机来讲,复杂程度并没有多大降低的,更何况隔离性也没有虚拟机那么好。好处在于,能让每个用户空间的进程使用宿主机的性能,中间没有额外的开销。资源方面的节约。于是就出现了 dockerdocker 只是 LXC 的增强版。

    docker 是如何简化的?

    LXC 大规模创建容器很难,docker 早起的版本核心就是 LXC ,利用 LXC 做容器管理引擎,在创建容器时,不再是现场安装模板,而是通过镜像技术,整体打包成一个文件,这个文件就是镜像文件。这个镜像文件是放在一个集中统一的仓库中的。

    使用 docker create 创建一个容器时,不会激活模板让用户去安装,而是自动连接到镜像仓库服务器去下载一个匹配创建容器所需要的镜像,并基于镜像来启动容器。所以 docker 极大的简化了容器的使用难度。

    以后使用docker 启动一个容器,直接使用命令:docker create 结束。

    docker容器的原则是一个容器只运行一个进程。LXC 是把一个容器当一个用户空间来使用,可以运行N个进程。

    docker 容器编排工具:

    • machine + swarm + compose
    • mesos + marathon
    • kubernetes -> k8s
  • 相关阅读:
    FZU Monthly-201906 tutorial
    FZU Monthly-201906 获奖名单
    FZU Monthly-201905 tutorial
    BZOJ1009 GT考试
    BZOJ2428 均分数据
    模拟退火
    BZOJ3680 吊打XXX
    BZOJ4818 序列计数
    BZOJ4103 异或运算
    BZOJ3512 DZY Loves Math IV
  • 原文地址:https://www.cnblogs.com/hukey/p/14055907.html
Copyright © 2011-2022 走看看