容器运行时硬核技术内幕 (5) 侉界之王Sidecar

2022-08-04 15:10:03 浏览数 (1)

在上一期,我们提到了,容器运行时引擎需要符合CRI规范。

CRI规范中,有三类接口:

1、获取对方的CRI版本;

2、RuntimeService类型的调用,用于创建、停止、列出运行时对象——sandbox或container。

3、ImageService类型的调用,可以列出、拉取、查看状态、移除容器镜像。

我们注意到,运行时对象有两种——一种叫container,另一种叫sandbox。它们之间有什么区别呢?

实际上,我们很好理解container是什么。前文中提到的,利用docker run命令运行的容器,实际上就是一个container。

而sandbox,对外的名称叫pod,字面意思是“豆荚”。

顾名思义,pod是豆荚,豆荚中可以有多个豆子。每个豆子实际上就是一个容器。

我们知道,Kubernetes是一个使用了面向对象思想设计的系统,每种资源在Kubernetes中都以对象的方式存在。

对象是有生命周期的。Pod对象的生命周期如下图所示:

我们会发现,在一个pod的生命历程中,除了提供服务的main container外,还有init container。

当然,我们可以在yaml文件中描述init container:

代码语言:javascript复制
apiVersion: v1
kind: Pod

metadata: 
  name: myapp-pod
  labels: 
    app: myapp


spec:
  containers:
  - name: myapp-container
    image: ikubernetes/myapp:v1
  initContainers:
  -name: init-foobar
    image: busybox
    command: ['sh', '-c', 'sleep 10']

注意到这个范例中,initcontainers的描述,它启动了一个busybox,并且运行了一条命令,休眠10秒。在init container运行完毕后,kubelet会启动main container。

如main container的字面意义,pod中的这个容器运行着主要功能,如果pod中还有其他容器,只是为它提供支持服务的“边斗”(sidecar)。

图上就是具备了sidecar的侉界之王——长江750摩托车。它加装了边斗以后,可以装备7.62mm机枪或40mm火箭筒,大大增强了战斗力,成为高机动性的战车。

同样地,Kubernetes可以为container装备sidecar,形成一个pod,也可以实现非侵入式的微服务架构等。微服务架构的话题我们将在其他专题里面详解。

我们梳理一下kubelet启动pod的过程,如果pod中有1个init container,1个main container,1个sidecar。它会调用几次CRI接口呢?

这个问题比较简单,我们不留到下期了,就在这里解答吧:

  1. 首先创建pod:调用RunPodSandbox;
  2. 启动init container: 调用CreateContainer和RunContainer;
  3. init container执行完毕后,调用RemoveContainer移除init container;
  4. 调用CreateContainer和RunContainer启动main container和sidecar;

当然,在main container和sidecar运行期间,kubelet还可以通过ContainerStatus等调用,监控Pod内各个container的运行状态。

我们还注意到,在main container的生命周期中,有两个新的概念:post start hook和pre stop hook。它们的作用是什么呢?

原来,这两个概念指的是函数钩子。post start hook可以在容器初始化时调用,而pre stop hook会在停止容器运行前操作,并阻塞容器删除调用,也就是说,pre stop hook的调用完成之前,是不会进入容器删除流程的。

今天遗留了一个小问题:kubelet是如何探测容器的工作状态呢?

下一期中,我们将揭开谜底。

0 人点赞