• k8s中初始化容器(init container)的作用及其使用方法


    概述

    在容器的部署过程中,有的时候需要在容器运行之前进行一些预配置的工作,比如下载配置,判断某些服务是否启动,修改配置等一些准备的工作,想要实现这些功能,在k8s中可以使用初始化容器,在应用容器运行之前进行一些预处理的工作。

    本文档介绍在k8s中初始化容器的使用方法。

    使用方法

    以下的例子使用初始化容器,在nginx容器启动之前下载一个index.html文件

    kubectl apply -f - <<EOF
    apiVersion: v1
    kind: Pod
    metadata:
      name: initnginx
    spec:
      initContainers:
      - name: install
        image: busybox
        command:
        - wget
        - "-O"
        - "/var/index.html"
        - "https://www.baidu.com"
      containers:
      - name: nginx
        image: 172.20.45.174:81/base/nginx:1.15-alpine
        ports:
        - containerPort: 80
      dnsPolicy: Default
    EOF

    查看pod的状态

    [root@nccztsjb-node-11 ~]# kubectl get pod
    NAME                          READY   STATUS     RESTARTS   AGE
    cm-test-app                   1/1     Running    0          20h
    cm-test-nginx                 1/1     Running    0          175m
    cm-test-pod                   1/1     Running    0          20h
    initnginx                     0/1     Init:0/1   0          16s  #在初始化阶段
    nginx-test-5c7f8fc697-lrvpm   1/1     Running    0          32d
    nginx-test-5c7f8fc697-whx4g   1/1     Running    0          32d
    web-0                         1/1     Running    0          32d
    web-1                         1/1     Running    0          32d
    web-2                         1/1     Running    0          32d
    
    # 初始化容器运行完成后,pod状态变为Running
    
    [root@nccztsjb-node-11 ~]# kubectl get pod
    NAME                          READY   STATUS    RESTARTS   AGE
    cm-test-app                   1/1     Running   0          20h
    cm-test-nginx                 1/1     Running   0          178m
    cm-test-pod                   1/1     Running   0          20h
    initnginx                     1/1     Running   0          9s
    nginx-test-5c7f8fc697-lrvpm   1/1     Running   0          32d
    nginx-test-5c7f8fc697-whx4g   1/1     Running   0          32d
    web-0                         1/1     Running   0          32d
    web-1                         1/1     Running   0          32d
    web-2                         1/1     Running   0          32d
    [root@nccztsjb-node-11 ~]# 

    查看初始化容器的日志

    [root@nccztsjb-node-11 ~]# kubectl logs initnginx -c install
    Connecting to www.baidu.com (103.235.46.39:443)
    wget: note: TLS certificate validation not implemented
    saving to '/var/index.html'
    index.html           100% |********************************|  2443  0:00:00 ETA
    '/var/index.html' saved
    [root@nccztsjb-node-11 ~]#

    说明执行命令是成功的。

    进入容器中,查看是否存在该文件

    [root@nccztsjb-node-11 ~]# kubectl exec -it initnginx -- bash
    [initnginx root:~]# cd /var/
    [initnginx root:/var]# ls
    cache  empty  git  lib  local  lock  log  opt  run  spool  tmp
    [initnginx root:/var]# 

    发现并没有该文件!

    问题在于install容器和nginx容器不是同一个容器所以,下载的/var/index.html只是在install容器的/var目录下。

    为了实现nginx可以访问初始化容器中的内容,可以挂载一个数据卷进行2个容器的共享,修改pod定义如下:

    kubectl apply -f - <<EOF
    apiVersion: v1
    kind: Pod
    metadata:
      name: initnginx
    spec:
      initContainers:
      - name: install
        image: busybox
        command:
        - wget
        - "-O"
        - "/work-dir/index.html"
        - "https://www.baidu.com"
        volumeMounts:
        - name: workdir
          mountPath: /work-dir
      containers:
      - name: nginx
        image: 172.20.45.174:81/base/nginx:1.15-alpine
        ports:
        - containerPort: 80
        volumeMounts:
        - name: workdir
          mountPath: /usr/share/nginx/html
      dnsPolicy: Default
      volumes:
      - name: workdir
        emptyDir: {}
    EOF

    这样的化,2个容器中就都挂载了workdir这个数据卷,初始化容器中下载的文件,就可以被nginx应用容器来使用了。

    创建pod后查看nginx容器中的文件

    [root@nccztsjb-node-11 ~]# kubectl exec -it initnginx -- bash
    [initnginx root:~]# cd /usr/share/nginx/
    [initnginx root:/usr/share/nginx]# ls
    html
    [initnginx root:/usr/share/nginx]# cd html/
    [initnginx root:/usr/share/nginx/html]# ls
    index.html
    [initnginx root:/usr/share/nginx/html]# cat index.html 
    <!DOCTYPE html>
    <!--STATUS OK--><html> <head><meta http-equiv=content-type content=text/html;charset=utf-8><meta http-equiv=X-UA-Compatible content=IE=Edge><meta content=always name=referrer><link rel=stylesheet type=text/css href=https://ss1.bdstatic.com/5eN1bjq8AAUYm2zgoY3K/r/www/cache/bdorz/baidu.min.css><title>百度一下,你就知道</title></head> <body link=#0000cc> <div id=wrapper> <div id=head> <div class=head_wrapper> <div class=s_form> <div class=s_form_wrapper> <div id=lg> <img hidefocus=true src=//www.baidu.com/img/bd_logo1.png width=270 height=129> </div> <form id=form name=f action=//www.baidu.com/s class=fm> <input type=hidden name=bdorz_come value=1> <input type=hidden name=ie value=utf-8> <input type=hidden name=f value=8> <input type=hidden name=rsv_bp value=1> <input type=hidden name=rsv_idx value=1> <input type=hidden name=tn value=baidu><span class="bg s_ipt_wr"><input id=kw name=wd class=s_ipt value maxlength=255 autocomplete=off autofocus=autofocus></span><span class="bg s_btn_wr"><input type=submit id=su value=百度一下 class="bg s_btn" autofocus></span> </form> </div> </div> <div id=u1> <a href=http://news.baidu.com name=tj_trnews class=mnav>新闻</a> <a href=https://www.hao123.com name=tj_trhao123 class=mnav>hao123</a> <a href=http://map.baidu.com name=tj_trmap class=mnav>地图</a> <a href=http://v.baidu.com name=tj_trvideo class=mnav>视频</a> <a href=http://tieba.baidu.com name=tj_trtieba class=mnav>贴吧</a> <noscript> <a href=http://www.baidu.com/bdorz/login.gif?login&amp;tpl=mn&amp;u=http%3A%2F%2Fwww.baidu.com%2f%3fbdorz_come%3d1 name=tj_login class=lb>登录</a> </noscript> <script>document.write('<a href="http://www.baidu.com/bdorz/login.gif?login&tpl=mn&u='+ encodeURIComponent(window.location.href+ (window.location.search === "" ? "?" : "&")+ "bdorz_come=1")+ '" name="tj_login" class="lb">登录</a>');
                    </script> <a href=//www.baidu.com/more/ name=tj_briicon class=bri style="display: block;">更多产品</a> </div> </div> </div> <div id=ftCon> <div id=ftConw> <p id=lh> <a href=http://home.baidu.com>关于百度</a> <a href=http://ir.baidu.com>About Baidu</a> </p> <p id=cp>&copy;2017&nbsp;Baidu&nbsp;<a href=http://www.baidu.com/duty/>使用百度前必读</a>&nbsp; <a href=http://jianyi.baidu.com/ class=cp-feedback>意见反馈</a>&nbsp;京ICP证030173号&nbsp; <img src=//www.baidu.com/img/gs.gif> </p> </div> </div> </div> </body> </html>
    [initnginx root:/usr/share/nginx/html]# 

    发现index.html文件已经生成了,就是在初始化容器中创建的文件被挂载到nginx中来使用。

    查看初始化容器的日志

    [root@nccztsjb-node-11 ~]# kubectl logs initnginx -c install
    Connecting to www.baidu.com (103.235.46.39:443)
    wget: note: TLS certificate validation not implemented
    saving to '/work-dir/index.html'
    index.html           100% |********************************|  2443  0:00:00 ETA
    '/work-dir/index.html' saved
    [root@nccztsjb-node-11 ~]# 

    OK,通过日志发现是向/work-dir/目录中写了index.html文件。

    以上就是初始化容器的基本的用法。

    查看pod的事件也可以看到pod中容器运行的顺序

    [root@nccztsjb-node-11 ~]# kubectl describe pod  initnginx
    Name:         initnginx
    Namespace:    default
    Priority:     0
    Node:         172.20.59.57/172.20.59.57
    Start Time:   Tue, 11 Jan 2022 13:49:57 +0800
    Labels:       <none>
    Annotations:  cni.projectcalico.org/podIP: 172.23.29.31/32
                  cni.projectcalico.org/podIPs: 172.23.29.31/32
    Status:       Running
    IP:           172.23.29.31
    IPs:
      IP:  172.23.29.31
    Init Containers:
      install:
        Container ID:  docker://9d2aec37255a02a2b13abced64717057eb100dd329bc6b6529211e30595f1c93
        Image:         busybox
        Image ID:      docker-pullable://busybox@sha256:5acba83a746c7608ed544dc1533b87c737a0b0fb730301639a0179f9344b1678
        Port:          <none>
        Host Port:     <none>
        Command:
          wget
          -O
          /work-dir/index.html
          https://www.baidu.com
        State:          Terminated
          Reason:       Completed
          Exit Code:    0
          Started:      Tue, 11 Jan 2022 13:50:05 +0800
          Finished:     Tue, 11 Jan 2022 13:50:08 +0800
        Ready:          True
        Restart Count:  0
        Environment:    <none>
        Mounts:
          /var/run/secrets/kubernetes.io/serviceaccount from default-token-8ss8s (ro)
          /work-dir from workdir (rw)
    Containers:
      nginx:
        Container ID:   docker://9f088e80c72e6691ea48bf3a9edf3983ccf8e8d32dd17e27425916efdfec4ff4
        Image:          172.20.45.174:81/base/nginx:1.15-alpine
        Image ID:       docker-pullable://172.20.45.174:81/base/nginx@sha256:478a73bcec93acc3e814ddd6fb2f95c6f6b4b0d0f168a4feaa039513d260a5d9
        Port:           80/TCP
        Host Port:      0/TCP
        State:          Running
          Started:      Tue, 11 Jan 2022 13:50:08 +0800
        Ready:          True
        Restart Count:  0
        Environment:    <none>
        Mounts:
          /usr/share/nginx/html from workdir (rw)
          /var/run/secrets/kubernetes.io/serviceaccount from default-token-8ss8s (ro)
    Conditions:
      Type              Status
      Initialized       True 
      Ready             True 
      ContainersReady   True 
      PodScheduled      True 
    Volumes:
      workdir:
        Type:       EmptyDir (a temporary directory that shares a pod's lifetime)
        Medium:     
        SizeLimit:  <unset>
      default-token-8ss8s:
        Type:        Secret (a volume populated by a Secret)
        SecretName:  default-token-8ss8s
        Optional:    false
    QoS Class:       BestEffort
    Node-Selectors:  <none>
    Tolerations:     node.kubernetes.io/not-ready:NoExecute op=Exists for 300s
                     node.kubernetes.io/unreachable:NoExecute op=Exists for 300s
    Events:
      Type    Reason     Age    From               Message
      ----    ------     ----   ----               -------
      Normal  Scheduled  6m27s  default-scheduler  Successfully assigned default/initnginx to 172.20.59.57
      Normal  Pulling    6m26s  kubelet            Pulling image "busybox"
      Normal  Pulled     6m20s  kubelet            Successfully pulled image "busybox" in 6.378365555s
      Normal  Created    6m20s  kubelet            Created container install
      Normal  Started    6m19s  kubelet            Started container install
      Normal  Pulled     6m16s  kubelet            Container image "172.20.45.174:81/base/nginx:1.15-alpine" already present on machine
      Normal  Created    6m16s  kubelet            Created container nginx
      Normal  Started    6m16s  kubelet            Started container nginx
    [root@nccztsjb-node-11 ~]# 

    即先创建初始化容器,运行结束后,才是运行nginx这个应用容器。

    初始化容器使用的说明

    关于初始化容器的使用,有几点说明

    • 在pod中可以有一个或者多个初始化容器
    • 初始化容器执行成功后,应用的容器才能被执行
    • 初始化容器是仅运行一次的任务
    ★★★★★如果您在查看博文时,有任何的疑问都可以加我的微信。13240133388. 希望可以帮助到您~★★★★
  • 相关阅读:
    java线程——三种创建线程的方式
    java线程——详解Callable、Future和FutureTask
    商品详情页系统的Servlet3异步化实践
    关于servlet3.0中的异步servlet
    Spring中线程池的应用
    Spring中@Async注解实现“方法”的异步调用
    高性能的关键:Spring MVC的异步模式
    SpringBoot+springmvc异步处理请求
    指定Qt程序运行的style,比如fusion(以前没见过QStyleFactory)
    Linux下获取arm的交叉编译工具链
  • 原文地址:https://www.cnblogs.com/chuanzhang053/p/15788006.html
Copyright © 2020-2023  润新知