文章详情

短信预约-IT技能 免费直播动态提醒

请输入下面的图形验证码

提交验证

短信预约提醒成功

如何在Kubernetes中使用Init Container

2024-11-30 05:50

关注

Init Container 是什么

Init Container 是一种特殊容器,顾名思义是用来做初始化工作的容器,可以是一个或者多个,如果有多个的话,这些容器会按定义的顺序依次执行,只有所有的Init Container执行完后,主容器才会被启动。

我们知道一个Pod里面的所有容器是共享数据卷和网络命名空间的,所以Init Container里面产生的数据可以被主容器使用到的。Init Container与应用容器本质上是一样的,除了以下两点:

如果 Pod 的 Init 容器失败,Kubernetes 会不断地重启该 Pod,直到 Init 容器成功为止。如果 Pod 对应的 restartPolicy 为 Never,它不会重新启动。

Pod 的生命周期:

从上面这张图我们可以直观的看到 Init Container 是独立于主容器之外的,但他们都属于Pod的生命周期。

应用场景

简单示例

应用容器定义在 Pod.Spec.Containers,是必填字段,而 init 是定义在 Pod.Spec.initContainers 中,是可选字段。

下面的例子定义了一个具有 2 个 Init 容器的简单 Pod。第一个等待 myservice 启动, 第二个等待 mydb 启动。一旦这两个 Init 容器都启动完成,Pod 将启动 spec 节中的应用容器。

myapp.yaml:

apiVersion: v1
kind: Pod
metadata:
  name: myapp-pod
  labels:
    app.kubernetes.io/name: MyApp
spec:
  containers:
  - name: myapp-container
    image: busybox:1.28
    command: ['sh', '-c', 'echo The app is running! && sleep 3600']
  initContainers:
  - name: init-myservice
    image: busybox:1.28
    command: ['sh', '-c', "until nslookup myservice.$(cat /var/run/secrets/kubernetes.io/serviceaccount/namespace).svc.cluster.local; do echo waiting for myservice; sleep 2; done"]
  - name: init-mydb
    image: busybox:1.28
    command: ['sh', '-c', "until nslookup mydb.$(cat /var/run/secrets/kubernetes.io/serviceaccount/namespace).svc.cluster.local; do echo waiting for mydb; sleep 2; done"]

创建:

[root@localhost ~]# kubectl apply -f myapp.yaml
pod/myapp-pod created

查看状态:

[root@localhost ~]# kubectl get -f myapp.yaml    
NAME        READY   STATUS     RESTARTS   AGE
myapp-pod   0/1     Init:0/2   0          8s

输出详细信息:

[root@localhost ~]# kubectl describe -f myapp.yaml  
Name:         myapp-pod
Namespace:    default
[...]
Labels:       app.kubernetes.io/name=MyApp
Annotations:  
Status:       Pending
[...]
Init Containers:
  init-myservice:
[...]
    State:          Running
[...]
  init-mydb:
[...]
    State:          Waiting
      Reason:       PodInitializing
    Ready:          False
[...]
Containers:
  myapp-container:
[...]
    State:          Waiting
      Reason:       PodInitializing
    Ready:          False
[...]
Events:
  Type    Reason     Age   From               Message
  ----    ------     ----  ----               -------
  Normal  Scheduled  20s   default-scheduler  Successfully assigned default/myapp-pod to localhost.localdomain
  Normal  Pulling    17s   kubelet            Pulling image "busybox:1.28"
  Normal  Pulled     8s    kubelet            Successfully pulled image "busybox:1.28" in 9.30472043s
  Normal  Created    7s    kubelet            Created container init-myservice
  Normal  Started    6s    kubelet            Started container init-myservice

查看 Pod 内 Init 容器的日志:

[root@localhost ~]# kubectl logs myapp-pod -c init-myservice   # 查看第一个 Init 容器
nslookup: can't resolve 'myservice.default.svc.cluster.local'
Server:    10.96.0.10
Address 1: 10.96.0.10 kube-dns.kube-system.svc.cluster.local
 
waiting for myservice
 
 
 
[root@localhost ~]# kubectl logs myapp-pod -c init-mydb     # 查看第二个 Init 容器
Error from server (BadRequest): container "init-mydb" in pod "myapp-pod" is waiting to start: PodInitializing

此时,init-mydb容器会等待 init-myservice 执行完成后再执行。如下为创建这些 Service 的配置文件:services.yaml:

---
apiVersion: v1
kind: Service
metadata:
  name: myservice
spec:
  ports:
  - protocol: TCP
    port: 80
    targetPort: 9376
---
apiVersion: v1
kind: Service
metadata:
  name: mydb
spec:
  ports:
  - protocol: TCP
    port: 80
    targetPort: 9377

创建:

[root@localhost ~]# kubectl apply -f services.yaml
service/myservice created
service/mydb created

再次查看状态:变成 了 Running:

[root@localhost ~]# kubectl get pod
NAME        READY   STATUS    RESTARTS   AGE
myapp-pod   1/1     Running   0          2m35s

此时再次查看详细信息,发现两个 init-myservice 和 init-mydb 已经 Terminated 了:

Init Containers:
  init-myservice:
[...]
    State:          Terminated
      Reason:       Completed
      Exit Code:    0
[...]
  init-mydb:
[...]
    State:          Terminated
      Reason:       Completed
    Exit Code:    0

Sidecar 新特性

随着Kubernetes发布了1.28,支持了不少重磅特性,其中最令人感慨的莫过于新的Sidecar,目前是alpha版本。之前Sidecar的称谓只是一种多容器的设计模式,在K8s看来和普通容器没什么不一样。但由于其生命周期与业务容器并不一致,对于Sidecar的生命周期管理一直是个问题。

新版本的Sidecar是放置在initContainers中,指定restartPolicy为Always便开启Sidecar,其生命周期以及重启管理与普通容器也是一样的,此特性也可用于运行 Job 。

下面是一个带有Sidecar的Deployment示例,log Sidecar容器用来输出日志到终端,main容器模拟写入日志: sidecar.yaml:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: myapp
  labels:
    app: myapp
spec:
  replicas: 1
  selector:
    matchLabels:
      app: myapp
  template:
    metadata:
      labels:
        app: myapp
    spec:
      containers:
        - name: myapp
          image: alpine:latest
          command: ['sh', '-c', 'while true; do echo "logging" >> /opt/logs.txt; sleep 1; done']
          volumeMounts:
            - name: data
              mountPath: /opt
      initContainers:
        - name: logshipper # sidecar 容器
          image: alpine:latest
          restartPolicy: Always # 必须指定restartPolicy为Always才能开启sidecar
          command: ['sh', '-c', 'tail -f /opt/logs.txt']
          volumeMounts:
            - name: data
              mountPath: /opt
      volumes:
        - name: data
          emptyDir: {}

部署到K8s集群中,可以看到initContainers[*].restartPolicy字段:

[root@localhost ~]# kubectl create -f sidecar.yaml
deployment.apps/myapp created
 
[root@localhost ~]# kubectl get po -l app=myapp -ojsonpath='{.items[0].spec.initContainers[0].restartPolicy}'
Always
 
[root@localhost ~]# kubectl get po  -l app=myapp 
NAME                    READY   STATUS    RESTARTS   AGE
myapp-215h3248d-p4z6   2/2     Running   0          1m5s

myapp Pod中两个容器都是Ready(2/2),查看日志可以看到log Sidecar一直在输出日志。

[root@localhost ~]# kubectl logs -l app=myapp -c logshipper -f
logging
logging
来源:云原生运维圈内容投诉

免责声明:

① 本站未注明“稿件来源”的信息均来自网络整理。其文字、图片和音视频稿件的所属权归原作者所有。本站收集整理出于非商业性的教育和科研之目的,并不意味着本站赞同其观点或证实其内容的真实性。仅作为临时的测试数据,供内部测试之用。本站并未授权任何人以任何方式主动获取本站任何信息。

② 本站未注明“稿件来源”的临时测试数据将在测试完成后最终做删除处理。有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341

软考中级精品资料免费领

  • 2024年上半年信息系统项目管理师第二批次真题及答案解析(完整版)

    难度     813人已做
    查看
  • 【考后总结】2024年5月26日信息系统项目管理师第2批次考情分析

    难度     354人已做
    查看
  • 【考后总结】2024年5月25日信息系统项目管理师第1批次考情分析

    难度     318人已做
    查看
  • 2024年上半年软考高项第一、二批次真题考点汇总(完整版)

    难度     435人已做
    查看
  • 2024年上半年系统架构设计师考试综合知识真题

    难度     224人已做
    查看

相关文章

发现更多好内容

猜你喜欢

AI推送时光机
位置:首页-资讯-后端开发
咦!没有更多了?去看看其它编程学习网 内容吧
首页课程
资料下载
问答资讯