zoukankan      html  css  js  c++  java
  • kubernetes 容器编排系统

    前言

    docker解决了打包和隔离的问题,但是在docker集群中我们需要解决更多的问题,如调度(容器在哪运行)、生命周期及健康状况(确保容器在无错的情况下运行)、服务发现(容器所处位置,和容器通信)、监控(容器运行是否正常)、认证(谁能访问我的容器)、容器聚合(如何将多个关联的容器聚合一个工程),在集群中需要解决这么问题,但是docker并没有给出解决方案,kubenetes就是解决这些问题的。

    kubernetes概述及使用

    轻量级、简单,可以在公有云、私有云及混合云部署,模块化(mudular),可插拔化(pluggable)- 可以使第三方的用户很容易将自己的应用集成到kubenetesz中,可挂接(hookbale)-可以接收kubernetes产生的事件并做相应的处理,,可组合(composable)-你可以任意的选择kuberntes当中的一些功能,来组成一个完整的系统,自动恢复、自动重启、自动复制。

    1、使用与kubernetes进行交互的命令接口kubernetes-kubernetes CLI

    (1)在主节点查看所有的node节点

    [root@k8s-master ~]# kubectl get nodes
    NAME STATUS ROLES AGE VERSION
    k8s-master Ready master 6d5h v1.15.2
    k8s-node1 Ready <none> 6d5h v1.15.2
    k8s-node2 Ready <none> 6d5h v1.15.2

    (2) 获取kubernetes集群发生的事件

    kubectl get events

    image.png
    (3)Pods

    创建、调度、及管理的最小单元,共存的一组容器集合,容器共享PID-容器共享了PID命名空间,它使同一个Pods内的容器可以看到彼此的进程,网络-共享了网络命名空间,可以使同一个Pods内的容器使用相同的ip地址及其端口,通过localhost来相互访问,IPC-同一个Pods内的容器可以使用systemvip或porstem的消息队列的方式来进行通信,UTS命名空间-同一个Pods内的容器使用了相同的主机名,同时同一个Pods中的容器还可以共享存储卷-kubernetes的设计,为了更好的资源共享及容器间的通信便于管理,短暂存在-就像我们的容器一样,Pods是一个短暂存在的对象,Pods的生命周期主要分为以下几个状态:

    1、首先是一个pending的状态,它表示Pods已经被系统接受,但是一个或多个容器镜像还没有创建,这包括容器在被调度之前的时间以及下载镜像的时间
    2、running它表示Pods已经被部署到一个节点上,并且所有的容器镜像都被创建了
    3、successed表示Pods中的容器都被成功的停止了,并且不会被重启
    4、failed,它表示Pods中的所有容器都被停止了,并且至少有一个容器在停止的时候出现了错误

    2、k8s最佳实践

    1、创建一个基本的Pod,kubectl create –f pod.yaml
    apiVersion: v1
    kind: Pod  #表示yaml文件定义了一个pod对象,首字母需要大写
    metadata: #表示这个对象需要的一些属性值
       name: nginx
    spec:
       containers:
       - name: nginx
         image: nginx
         ports:
         - containerPort: 80
    
    
    
    2、获取集群的Pods,kubectl get pods
    [root@k8s-master opt]# kubectl get pods nginx
    NAME    READY   STATUS    RESTARTS   AGE
    nginx   1/1     Running   0          20s
    
    3、删除pod,kubectl delete pods podsName
    [root@k8s-master opt]# kubectl delete pods nginx
    pod "nginx" deleted
    
    4、上面演示了一个创建pod的案例,并在pod中运行一个nginx的容器,我们知道容器中的文件是短暂存在的,当容器crash的时候,数据将会丢失,下面使用Volumes进行pod数据持久化

    Volumes的作用及生命周期:

    1、数据持久化
    2、Pod中容器共享数据
    3、生命周期(Volumes的周期和Pod定义的生命周期是一样的),当一个Pods停止退出的时候Volumes也会停止退出,目前kubernetes支持的数据卷类型-emptyDir,hostpath,gcePersistentDisk,awsElasticBlockStore,nfs,iscsi,glusterfs,secrets

    存储卷创建的几种方式

    1、本地主机上创建的两种类型数据卷

    1、emptyDir:当Pods被调度到一个节点的时候生成,只要Pods运行到当前节点上便一直存在,其初始是一个空文件夹,Pods内的容器可以读取此文件夹中的文件,当此Pods从此节点删除的时候,数据卷也会被相应的删除,我们需要注意容器crash的时候,数据卷是不会被删除的
    2、hostpath:可以指明当前宿主机上的一个路径映射到我的Pods内

    2、云端存储

    gcePersistentDisk,awsElasticBlockStore

    3、网络存储

    nfs,iscsi,glusterfs

    4、加密存储secrets

    用于存储比较敏感的数据,如果用户密码

    创建一个包含Volumes的Pods,kubectl create -f volumes.yaml

    apiVersion: v1
    kind: Pod
    metadata:
       name: redis
    spec:
       containers:
       - name: redis
         image: redis
         volumeMounts:
         - name: redis-persistent-storage
           mountPath: /data/redis
       volumes:
       - name: redis-persistent-storage
         emptyDir: {}
    
    使用yaml格式查看redis Pod的详细信息,kubectl get pods redis -o yaml
    image.png


    Label的作用

    用以表示对象(如Pod)的key/value对,组织并选择对象子集,Labels使用户可以使用松耦合的方式来映射自己应用的组织结构,而不需要存储这些映射表,那么与命名和uid不同的是,Label不需要提供唯一性,反而我们希望多个对象使用相同的Label,通过Label选择器用户可以指定一些对象子集来进行分组合并。
    创建一个Labels的pod,kubectl create -f label.yaml
    apiVersion: v1
    kind: Pod
    metadata:
        name: nginx
        labels:
          app: nginx
    spec:
       containers:
       - name: nginx
         image: nginx
         ports: 
         - containerPort: 80
    
    查看带有label的Pod,kubectl get pods -l app=nginx-web
    image.png

    这个时候我们已经可以创建一个带labels并能够提供持久化的pod,但是当我们的节点出错或者需要维护的时候,我们如何确保我们的Pods能被调度到其他节点正常运行呢?在kubernets当中有一个replication controller的概念,我们简称它为RC

    RC的概述

    1、保证在任意时刻运行指定数量的Pod,比如说我要指定刚才创建的nginx在任意时候都要运行一个Pod,当我运行nginx的pod的节点出现错误时,那么我的这个RC确保这个Pod会被调度到另外可以工作正常的接点上,保证Pod正常运行
    2、容器重新调度,可以把它当做守护进程,与之不同的是RC监控的事多个节点的多个Pod
    3、规模调度,它使规模调度变得简单,你只需要修改指定Pod的数目,RC便会删除多余的容器和启动新的容器以达到指定的数目
    4、在线升级,同时RC可以通过一个接一个替换Pod的方法实现在线升级,你可以增加一个新版本的Pod,然后删除一个旧的Pod,之后当旧版本的Pod数目为0的时候,你可以删除旧的RC,需要注意的是我们使用新版本的Pod和旧版本Pod的RC需要至少有一处不同label以标记不同版本的RC
    5、多发布版本跟踪,在某一个时间段内运行多个版本的应用是可能的,这个多个版本的追踪也是可以通过设置不同的label,通过RC去实现
    创建一个rc,kubectl create -f rc.yaml
    apiVersion: v1
    kind: ReplicationController
    metadata:
      name: nginx
    spec:
      replicas: 3 #创建nginx pod实例的数量
      selector:
        app: nginx
      template:
        metadata:
          name: nginx
          labels:
            app: nginx
        spec:
          containers:
          - name: nginx
            image: nginx
            ports:
            - containerPort: 80
    
    
    查看rc的信息,kubectl get rc,并查看创建的Pod
    image.png
    尝试删除其中一个Pod,验证RC是否重新创建一个,kubectl delete pods podName,可以看到重新创建了一个Pod,rc控制器始终保证了Pod的运行数量
    image.png


    每个Pods都有自己的ip地址,并且这些地址并不是固定的,这带来一个问题,如果一些Pods是被另外一些Pods提供服务的,那么它如何被发现呢,kubernetes为此提供了service的抽象去解决这个问题

    Service的定义

    1、抽象一系列Pod并定义访问规则
    2、它为每一个服务提供了一个固定的虚拟的ip和dns域名
    3、我们可以通过环境变量和DNS的方式发现服务
    4、同时它还提供了非常简单的负载均衡
    5、它定义了我们Pod的访问方式,目前有三种,首先是一个ClusterIP(它只能在当前集群内访问),type是NodePort的时候,那么它是使用了ClusterIP,同时它还会在集群的每一个节点上暴露一个服务的端口,你可以通过这个集群的某一个工作节点的ip地址以及这个端口来访问这个服务,如果你的云服务商提供支持外部负载均衡的话,那么你可以使用LoadBalancer这个类型,通过service的访问你并不需要Pods的ip,service的ip是一个固定的ip,并且你可以通过kubernetes提供的DNS服务进行查询
    创建一个service,kubectl create -f service.yaml
    apiVersion: v1
    kind: Service
    metadata:
       name: nginx-service
    spec:
      ports:
      - port: 8000 # The port that this service should serve on the container on each pod to connect to,
                   #can be a name(eg,'www') or a number(eg,'80')
        targetPort: 80
        protocol: TCP
                   #            # Just like the selector in the replication controller,but this time it identifies the set of pods load balance traffic to.
      selector:
            app: nginx
    
    查看service的状态,kubectl get service
    image.png
    在节点上验证service暴露是否成功,cutrl http://ClusterIP:port
    image.png
  • 相关阅读:
    ng2-bootstrap的modal嵌套时无法滚动的情况
    oracle自动补0
    webservice 从客户端中检测到有潜在危险的 Request.Form 值
    树莓派花生壳
    ubuntu E: Could not get lock /var/lib/dpkg/lock
    树莓派配置静态ip
    解决PL/SQL查询结果乱码的问题
    批处理脚本命令行方式关闭Windows服务
    最简单的分享到微博代码
    Select的onchange事件
  • 原文地址:https://www.cnblogs.com/lcword/p/14540685.html
Copyright © 2011-2022 走看看