k8s系列01---docker的由来及基本原理

 

1、docker基础知识

 

1.1、docker崛起的原因

  1. docker镜像通过技术手段解决了PasS的根本性问题;
  2. docker容器同开发者之间有着与生俱来的紧密关系;
  3. PaaS概念已经深入人心的完美契机;

 

1.2、容器的概念

容器就是一种沙盒的技术。沙盒就是能够像一个集装箱一样,把你的应用“装”起来。这样应用与应用之间就有了边界而不至于相互干扰。装进集装箱的应用也可以被方便的搬来搬去。

 

1.3、创建docker容器

创建容器使用如下命令:

$ docker run -it busybox /bin/sh

/#

命令意思:请分配给我一个容器,容器执行bin/sh命令,并且需要分配一个命令行终端与容器交互。

命令解释:

1、it命令告诉docler容器创建后需要分配一个文本输入、输出环境;

2、bin/sh是我们在docker容器里面要运行的程序;

 

1.4、docker容器的原理

 

1.4.1、namespace概念

docker容器使用linux系统的namespace概念,将一个个容器隔离开来。也就是创建socker容器时制定一系列的namespace参数,指定这个容器能够看到的资源、文件、设备和配置等,对于宿主机其他的程序则完全看不到。

与虚拟机的区别:docker容器是调用了linux系统自带的namespace命令的各种参数,并没有真正的像虚拟机一样创建了真实的系统,也就是没有真实的docker容器存在。区别如下图:

k8s系列01---docker的由来及基本原理

 

虚拟机是在虚拟机软件里面的一个个系统;docker容器是在linux系统上的一个个由namespace参数进行隔离的程序。

优点:1、docker容器不需要单独的创建系统,使得容器化占用的额外资源可以忽略不计;2、容器化后的应用在宿主机上仍是一个普通的进程(么有经过像虚拟机一样的系统转化),所以由虚拟化带来的性能损耗是不存在的。因此docker容器具有敏捷和高性能的特性。

弊端:1、docker容器基于linux系统的namespace技术进行的隔离,隔离的不够彻底;2、linux系统的一些东西是不能通过namespace进行隔离的,比如时间。

 

1.4.2、Cgroups概念

由于由namespace创建的进程,不做限制的化可能会出现某个进程把linux系统的所有cpu和内存资源耗光的情况,所以为了限制单个docker容器能够使用的系统资源,docker容器使用了linux系统的Cgroups概念。

linux Cgeoups全称是Linux Control Group.它的主要作用就是限制一个进程组能够使用的资源上限,包括cpu、磁盘、带宽、内存等。

在linux系统中,Cgroups给用户爆露出来的接口是文件系统,即它以文件和目录的方式组织在操作系统的/sys/fs/cgroup路径下。除了cpu子系统外,Cgroups的每一项子系统都具有独立的资源限制能力,比如:

blkio: 为块设备设定i/o限制,一般用于磁盘设备;

cpuset:为进程分配单独的cpu核和对应的内存节点;

memory:为进程设定内存使用的限制。

 

1.4.3、mount namespace

mount namespace修改的是容器进程对文件系统‘挂载点’的认知。他对容器进程试图的改变一定是伴随着挂在操作(mount)才能生效。

mount namespace是linux操作系统中的第一个namespace.挂载在容器根目录上,用来为容器进程提供隔离后执行环境的文件系统,就是容器镜像。更为专业的名字叫做:rootfs(根文件系统)。

rootfs 只是一个操作系统所包含的文件、配置和目录,并不包括操作系 统内核。在 Linux 操作系统中,这两部分是分开存放的,操作系统只有在开机启动时才会加载 指定版本的内核镜像。同一台机器上的所有容器,都共享宿主机操作系统的内核。

 

1.4.4、总结

由上面可知,对一个docker镜像来说,其核心的执行原理就是为待创建的用户进程:1、启用linux namespace设置;2、设置指定的Cgroups参数;3、切换根目录rootfs.

 

1.5、镜像制作

Docker 在镜像的设计中,引入了层(layer)的概念。也就是说,用户制作镜像的 每一步操作,都会生成一个层,也就是一个增量 rootfs。

k8s系列01---docker的由来及基本原理

只读层:一个容器镜像的基础层,只能读取,不能修改。

可读写层:对当前容器镜像的操作都放在这一层,当根据当前容器制作新的镜像的时候,这个可读写层在新的镜像里就是只读层;

init层:存放一些基于当前容器的配置信息,比如hostname等。