起因

在遥远的时代,在GitHub上看到了一个好玩的项目,那必须是韩了,但苦于本人的知识储备,只能看作者是否提供了Releases,没有那就换一个啊。但是作者贴心的提供了部署文档,我直接clone,在我的小破笔记本上配置好环境,运行!报错了,没有关系有问题就去解决问题,花费了半天时间终于在本地运行好后,我满怀欣喜的把项目打包丢到服务器上时,又报错了,跑起来后又出现了奇奇怪怪的错误。后来我看见一些部署文档上提供了docker部署的方式,这是个什么东西?

哦,原来是这么一个东西!本文就记录了我对docker的学习的过程,和我对docker技术的一些理解,望能做到温故而知新。

Docker是什么

映入眼帘的是docker的Log,一头鲸鱼驮着很多集装箱游弋广袤的大海,我个人对docker的理解是,docker是这头鲸鱼,大海就像宿主机,鲸鱼要吃小鱼小虾来维持生活,这就像宿主机提供的资源,这样鲸鱼就可以驮着集装箱(container)到处跑了。

这样你的程序可以在任何环境都会有一致的表现,这里程序运行的依赖也就是容器就好比集装箱,容器所处的操作系统环境就好大鲸鱼的背上,程序的表现只和集装箱有关系(容器),和集装箱放在哪头鲸鱼的背上(操作系统)没有关系。

docker中有这样几个概念:

  • Dockerfile:定义了如何构建image的指令文件。

  • Image:类似于可执行程序,是由Dockerfile生成的。

  • Container:运行中的image,即实际的应用程序实例。

实际上你可以简单的把image理解为可执行程序,container就是运行起来的进程。

那么写程序需要源代码,那么“写”image就需要dockerfile,dockerfile就是image的源代码,docker就是"编译器"。

因此我们只需要在dockerfile中指定需要哪些程序、依赖什么样的配置,之后把dockerfile交给“编译器”docker进行“编译”,也就是docker build命令,生成的可执行程序就是image,之后就可以运行这个image了,这就是docker run命令,image运行起来后就是docker container。

具体的使用方法就不再这里赘述了,可以参考docker的官方文档,那里有详细的讲解。

Docker是如何工作的

实际上docker使用了常见的C/S架构,也就是client-server模式,docker client负责处理用户输入的各种命令,比如docker build、docker run,真正工作的其实是server,也就是docker demon,值得注意的是,docker client和docker demon可以运行在同一台机器上。

可以用几条命令来快速理解docker的工作过程:

docker build:

当我们写完dockerfile交给docker“编译”时使用这个命令,那么client在接收到请求后转发给docker daemon,接着docker daemon根据dockerfile创建出“可执行程序”image。

docker run:

有了“可执行程序”image后就可以运行程序了,接下来使用命令docker run,docker daemon接收到该命令后找到具体的image,然后加载到内存开始执行,image执行起来就是所谓的container。

docker pull:

那么docker pull是什么意思呢?

我们之前说过,docker中image的概念就类似于“可执行程序”,我们可以从哪里下载到别人写好的应用程序呢?很简单,那就是应用商店。与之类似,既然image也是一种“可执行程序”,那么有没有"Docker Image Store"呢?答案是肯定的,这就是Docker Hub,docker官方的“应用商店”,你可以在这里下载到别人编写好的image,这样你就不用自己编写dockerfile了。

docker registry 可以用来存放各种image,公共的可以供任何人下载image的仓库就是docker Hub。那么该怎么从Docker Hub中下载image呢,就是这里的docker pull命令了。

由此看来,这个命令的实现也很简单,那就是用户通过docker client发送命令,docker daemon接收到命令后向docker registry发送image下载请求,下载后存放在本地,这样我们就可以使用image了。

docker的底层实现

docker基于Linux内核提供这样几项功能实现的:

  • NameSpace
    我们知道Linux中的PID、IPC、网络等资源是全局的,而NameSpace机制是一种资源隔离方案,在该机制下这些资源就不再是全局的了,而是属于某个特定的NameSpace,各个NameSpace下的资源互不干扰,这就使得每个NameSpace看上去就像一个独立的操作系统一样,但是只有NameSpace是不够。

  • Control groups
    虽然有了NameSpace技术可以实现资源隔离,但进程还是可以不受控的访问系统资源,比如CPU、内存、磁盘、网络等,为了控制容器中进程对资源的访问,Docker采用control groups技术(也就是cgroup),有了cgroup就可以控制容器中进程对系统资源的消耗了,比如你可以限制某个容器使用内存的上限、可以在哪些CPU上运行等等。

有了这两项技术,容器看起来就真的像是独立的操作系统

———引自博客园

总结

本文从实际项目部署的需求出发,介绍了Docker的概念、工作原理及其核心组件。Docker通过Namespace和Control Groups技术,实现了资源的隔离与控制,使得容器看起来像独立的操作系统,希望本文能对大家理解docker有所帮助。

一个懒人