学习k8s(一)

一、安装及介绍

1、k8s架构

2、核心组件

 3、其他组件

 4、安装方式

yum安装:        1.5 最简单,版本低,适合学习
二进制安装:      最繁琐,可以用saltstack安装
kubeadm安装:    谷歌推荐的自动化安装工具,网络有要求
go源码编译安装:  最难,需要go环境
minikube:      单机版,只适合体验

5、环境介绍

主机

ip地址

cpu核数

内存

swap

host解析

软件版本

k8s-master

192.168.4.11

1+

2G+

关闭

需要

docker-1.12.6-71

k8s-node

192.168.4.12

1+

2G+

关闭

需要

kubernetes-1.5.2

# hostnamectl set-hostname k8s-master
# hostnamectl set-hostname k8s-node

192.168.4.11     k8s-master
192.168.4.12     k8s-node

# setenforce 0
# systemctl stop firewalld.service
# systemctl stop NetworkManager.service

6、配置yum源

# cat /etc/yum.repos.d/mnt.repo 
[old-os]
name=old
baseurl=https://mirrors.aliyun.com/centos/7/os/x86_64/
enabled=1
gpgcheck=0

[new-os]
name=os
baseurl=https://mirrors.aliyun.com/centos/7.7.1908/os/x86_64/
enabled=0
gpgcheck=0

[extras]
name=extras
baseurl=https://mirrors.aliyun.com/centos/7.7.1908/extras/x86_64/
enabled=0
gpgcheck=0

[epel]
name=epel
baseurl=https://mirrors.aliyun.com/epel/7Server/x86_64/
enabled=0
gpgcheck=0

[vault]
name=va
baseurl=http://vault.centos.org/7.4.1708/extras/x86_64
enabled=1
gpgcheck=0

7、安装配置k8s-master

1)安装配置etcd

1、安装etcd(数据库kv类型存储,原生支持做集群)
# yum install -y etcd

2、配置etcd
# grep '^[a-Z]' /etc/etcd/etcd.conf 
ETCD_DATA_DIR="/var/lib/etcd/default.etcd"
ETCD_LISTEN_CLIENT_URLS="http://0.0.0.0:2379"
ETCD_NAME="default"
ETCD_ADVERTISE_CLIENT_URLS="http://192.168.4.11:2379"

3、启动服务
# systemctl enable etcd
# systemctl start  etcd

4、取值检验
# etcdctl set   testdir/testkey test
# etcdctl get   testdir/testkey

5、健康状态检查
# etcdctl -C http://192.168.4.11:2379 cluster-health

6、netstat -lntp | grep etcd
# 2379:对外提供服务,k8s写入数据
# 2380:集群间数据同步

2)安装配置K8s-master

1、安装
# yum install kubernetes-master  -y

2、修改api配置文件
# grep '^[a-Z]' /etc/kubernetes/apiserver  8:KUBE_API_ADDRESS="--insecure-bind-address=0.0.0.0"
17:KUBE_ETCD_SERVERS="--etcd-servers=http://192.168.4.11:2379"
20:KUBE_SERVICE_ADDRESSES="--service-cluster-ip-range=10.254.0.0/16"
23:KUBE_ADMISSION_CONTROL="--admission-control=NamespaceLifecycle,NamespaceExists,LimitRanger,SecurityContextDeny,ResourceQuota"
26:KUBE_API_ARGS=""
#删除23行ServiceAccount 服务认证,会很坑。

3、修改config配置文件(公共配置文件)
# grep '^[a-Z]' /etc/kubernetes/config 13:KUBE_LOGTOSTDERR="--logtostderr=true"
16:KUBE_LOG_LEVEL="--v=0"
19:KUBE_ALLOW_PRIV="--allow-privileged=false"
22:KUBE_MASTER="--master=http://192.168.4.11:8080"
# 指定apiserver地址,给controller-manager和scheduler使用,日志默认在/var/log/messages,可修改。

4、启动服务
# systemctl enable kube-apiserver.service
# systemctl start  kube-apiserver.service
# systemctl enable kube-controller-manager.service
# systemctl start  kube-controller-manager.service
# systemctl enable kube-scheduler.service
# systemctl start  kube-scheduler.service

5、检查服务是否安装正常
# kubectl  get cs
NAME                 STATUS    MESSAGE             ERROR
scheduler            Healthy   ok                  
controller-manager   Healthy   ok                  
etcd-0               Healthy   {"health":"true"}   

组件作用
api-server:   接受并响应用户的请求
controller:   控制器管理,保证容器始终存活
scheduler:    调度器,选择启动容器的node节点

8、安装配置k8s-node

1、安装
# yum install kubernetes-node  -y

2、配置
# grep '^[a-Z]' /etc/kubernetes/config -n
13:KUBE_LOGTOSTDERR="--logtostderr=true"
22:KUBE_MASTER="--master=http://192.168.4.11:8080"

# grep '[^a-Z]'/etc/kubernetes/kubelet
5行:KUBELET_ADDRESS="--address=0.0.0.0"
8行:KUBELET_PORT="--port=10250"
11行:KUBELET_HOSTNAME="--hostname-override=192.168.4.12"
14行:KUBELET_API_SERVER="--api-servers=http://192.168.4.11:8080"

3、启动服务
# systemctl enable kubelet.service
# systemctl start kubelet.service
# systemctl enable kube-proxy.service
# systemctl start kube-proxy.service

4、在master节点检查
# kubectl get nodes
NAME           STATUS    AGE
192.168.4.12   Ready     4d

组件作用
kubelet: 调用docker,管理容器生命周期
kube-proxy: 提供容器的网络访问

8、所有节点安装flannel网络

flannel:不同宿主机之间容器的通信

1、安装
# yum install flannel -y
# yum install docker-1.12.6-71.git3e8e77d.el7.centos.x86_64(master节点要配置镜像仓库)

2、配置 # grep '^[a-Z]' /etc/sysconfig/flanneld -n 4:FLANNEL_ETCD_ENDPOINTS="http://192.168.4.11:2379" 8:FLANNEL_ETCD_PREFIX="/atomic.io/network" #也可以用sed替换 # sed -i s#127.0.0.1:2379#192.168.4.11:2379#g /etc/sysconfig/flanneld 3、master节点 # etcdctl mk /atomic.io/network/config '{"Network":"172.16.0.0/16"}' #docker网段 如果设置错了,删除重新设置 # etcdctl get /atomic.io/network/config # etcdctl rm /atomic.io/network/config 4、启动服务 # systemctl enable flanneld.service # systemctl restart flanneld.service # systemctl restart docker # systemctl enable docker master节点: # systemctl restart kube-apiserver.service # systemctl restart kube-controller-manager.service # systemctl restart kube-scheduler.service node节点: # systemctl restart kubelet.service # systemctl restart kube-proxy.service

5、检查服务
# ifconfig flannel0

docker1.13版本中的一个问题,需要修改iptables,否则容器之间不通
# vim /usr/lib/systemd/system/docker.service
ExecStartPost=/sbin/iptables -P FORWARD ACCEPT

容器网络互通测试

1、所有节点启动容器并获取容器ip地址
# docker run -it busybox /bin/sh   

2、网络互通性测试
# ping 172.16.30.2      ping自己
# ping 172.16.30.1      ping网关
# ping 172.16.20.2      ping容器

配置master为镜像仓库

1、所有节点,配置镜像加速,以及私有仓库地址
1.13版本之前
# vim /etc/sysconfig/docker
OPTIONS='--selinux-enabled --log-driver=journald --signature-verification=false --registry-mirror=https://registry.docker-cn.com --insecure-registry=192.168.4.11:5000'
1.13版本之后
# vim /etc/docker/daemon.json  
{
  "registry-mirror": ["registry.docker-cn.com"],
  "insecure-registries":["192.168.4.11:5000"]
}
重启服务
# systemctl restart docker

2、启动私有仓库 # docker run -d -p 5000:5000 --restart=always --name registry -v /opt/registry:/var/lib/registry registry 3、推送镜像测试 master节点: # docker tag docker.io/busybox:latest 192.168.4.11:5000/busybox:latest # docker push 192.168.4.11:5000/busybox:latest node节点: # docker images
# docker pull 192.168.4.11:5000/busybox:latest

二、功能和基础架构

1、k8s有什么功能

k8s是一个docker集群的管理工具

k8s是容器的编排工具

2、k8s的核心功能

自愈: 重新启动失败的容器,在节点不可用时,替换和重新调度节点上的容器,对用户定义的健康检查不响应的容器会被中止,并且,在容器准备好服务之前不会把容器向客户端广播。

弹性伸缩: 通过监控容器的cpu的使用负载,如果这个容器评价高于80%,增加容器的数量,平均值低于10%,减少容器数量。

服务的自动发现和负载均衡: 不需要修改您的应用程序来使用不熟悉的服务发现机制,kubernetes为容器提供了自己的ip地址和一组容器的单个DNS名称,并可以在他们之间进行负载均衡。

滚动升级和一键回滚: kubernetes 逐渐部署对应用程序或者其配置的更改,同时监视应用程序运行状况,以确保它不会同时终止所有实例。如果出现问题,kubernetes会为你恢复更改,利用日益增长的部署,解决方案的生态系统。

私密配置文件管理: web容器里面,数据库的账户密码(测试库密码)

3、k8s的应用场景

最适合跑微服务项目!

微服务的好处

能承载更高的并发
业务健壮性,高可用
修改代码,重新编译时间短

持续集成,持续发布
jenkins代码自动上线

 

 三、k8s常用的资源

1、pod资源

pod是最小的资源单位

任何一个k8s资源都可以有yml清单文件来定义

k8s yaml的主要组成

apiVersion: v1  api版本
kind: pod       资源类型
metadata:       属性
spec:           详细

pod基本操作

创建
# kubectl create –f  ks8_pod.yaml

查询
# kubectl get pod  
# kubectl describe pod
# kubectl get pod -o wide  查看资源列表 删除 # kubectl delete pod nginx # kubectl delete
-f ks8_pod.yaml 更新 # Kubectl replace ks8_pod.yaml

一个最简单的pod

编辑k8s_pod.yml文件

apiVersion: v1  #版本
kind: Pod       #资源类型
metadata:       #元数据(属性)
  name: nginx   #pod名字
  labels:       #标签  键值对
    app: web
spec:           #详细
  containers:   #容器
    - name: nginx  #名字
      image: 192.168.4.11:5000/nginx:latest #镜像
      ports:
        - containerPort: 80         #端口

启动pod

# kubectl  create -f ks8_pod.yaml

获取pod详细信息kubectl describe(排错常用命令)

# kubectl describe pod nginx

构建成失败,此处有坑
错误是无法从registry.access.redhat.com仓库获取镜像

解决办法:
1、下载redhat-ca.crt证书
2、下载镜像文件,tag改名,上传到私有仓库

node节点
# vim /etc/kubernetes/kubelet
KUBELET_POD_INFRA_CONTAINER="--pod-infra-container image=192.168.4.11:5000/pod-infrastructure:latest"
重启服务
# systemctl restart kubelet.service

pod资源:至少由两个容器组成,pod基础容器和业务容器组成(最多1+4)

pod网络类型是container

Nginx没有IP地址

# docker ps -a
CONTAINER ID        IMAGE
b28f849335a7        192.168.4.11:5000/nginx:latest
2bed13c3afda        192.168.4.11:5000/pod-infrastructure:latest

# docker inspect b28f849335a7| tail -22
"NetworkSettings": {
            "Bridge": "",
            "SandboxID": "",
            "HairpinMode": false,
            "LinkLocalIPv6Address": "",
            "LinkLocalIPv6PrefixLen": 0,
            "Ports": null,
            "SandboxKey": "",
            "SecondaryIPAddresses": null,
            "SecondaryIPv6Addresses": null,
            "EndpointID": "",
            "Gateway": "",
            "GlobalIPv6Address": "",
            "GlobalIPv6PrefixLen": 0,
            "IPAddress": "",
            "IPPrefixLen": 0,
            "IPv6Gateway": "",
            "MacAddress": "",
            "Networks": {}
        }

访问的IP实际是pod-infrastructure容器的ip

# docker inspect 01549ff0cf31| tail -22
            "IPPrefixLen": 24,
            "IPv6Gateway": "",
            "MacAddress": "02:42:ac:10:0e:02",
            "Networks": {
                "bridge": {
                    "IPAMConfig": null,
                    "Links": null,
                    "Aliases": null,
                    "NetworkID": "91b2a8f0e6bc27e794c236206658ff980174af5af50f5c8960da2920d3936eca",
                    "EndpointID": "32d012474893339123e7ce707d89528831a50fd05374bb773fe5abab050b1e81",
                    "Gateway": "172.16.30.1",
                    "IPAddress": "172.16.30.2",
                    "IPPrefixLen": 24,
                    "IPv6Gateway": "",
                    "GlobalIPv6Address": "",
                    "GlobalIPv6PrefixLen": 0,
                    "MacAddress": "02:42:ac:10:0e:02"
                }
            }

原理:Nginx只提供web服务,pod-infrastructure的基础容器提供IP,实现k8s负载均衡、服务自愈等高级功能。

一个pod两个容器nginx+redis(端口不冲突即可)

1、编辑pod文件
# cat ks8_pod.yaml apiVersion: v1 kind: Pod metadata: name: test labels: app: web spec: containers:
- name: nginx image: nginx:latest ports: - containerPort: 80 - name: redis image: redis:latest
imagePullPolicy: IfNotPresent(使用本地镜像,不要pull) ports:
- containerPort: 6379 2、创建并验证 # kubectl create -f ks8_pod.yaml # kubectl get pods -o wide NAME READY STATUS RESTARTS AGE IP NODE po/test 2/2 Running 0 25s 172.16.30.2 192.168.4.12
访问Nginx和Redis,共用一个ip # curl -I 172.16.30.2 # telnet 172.16.30.2 6379
node1节点上有3个容器 Nginx+ Redis + pod # docker ps CONTAINER ID IMAGE COMMAND 922e73599020 redis:latest "docker-entrypoint..." 28690cdbc403 nginx:latest "nginx -g 'daemon off" c630ef8c2216 pod-infrastructure:latest "/pod"

k8s每启动一个容器,都需要先启动一个pod容器,启动的容器共用pod容器的ip地址

2、ReplicationController 资源

通过metadata标签,选择器selector管理pod
rc:保证指定数量的pod始终存活,确保pod数量,确保pod健康,弹性伸缩,滚动升级

创建yaml文件

# vim   myweb-rc.yml
apiVersion: v1
kind: ReplicationController       
metadata:
  name: myweb         #rc的名字
spec:
  replicas: 3         #副本数
  selector:
    app: myweb        #选择器,管理pod
  template:
    metadata:
      labels:
        app: myweb    #此为pod的标签
    spec:
      containers:
      - name: nginx
        image: 192.168.4.11:5000/nginx:latest
        ports:
        - containerPort: 80

故障自愈(多次删除自动新启动容器)

1、创建
# kubectl create -f myweb-rc.yaml 
2、查看 # kubectl get all -o wide
NAME DESIRED CURRENT READY AGE CONTAINER(S) IMAGE(S) SELECTOR rc
/myweb 3 3 3 21s nginx nginx:latest app=myweb NAME READY STATUS RESTARTS AGE IP NODE po/myweb-9gngt 1/1 Running 0 21s 172.16.30.4 192.168.4.12 po/myweb-blrwr 1/1 Running 0 21s 172.16.30.3 192.168.4.12 po/myweb-wk6gm 1/1 Running 0 21s 172.16.30.2 192.168.4.12 3、删除pod,rc会自动创建 # kubectl delete pod myweb-9gngt # kubectl delete pod myweb-wk6gm
# kubectl
get pods -o wide
NAME             READY     STATUS    RESTARTS   AGE       IP            NODE
po/myweb-blrwr   1/1       Running   0          51s       172.16.30.3   192.168.4.12
po/myweb-8dkee   1/1       Running   0          21s       172.16.30.5   192.168.4.12
po/myweb-7wsek   1/1       Running   0          21s       172.16.30.6   192.168.4.12

弹性伸缩—手动

方式一:kubectl scale rc 【rc-name】 --replicas=1

1、查看rc名字
# kubectl get rc  -o wide 

2、修改副本数
# kubectl scale rc myweb --replicas=5

3、查看结果
# kubectl  get pods -o wide --selector app=myweb

方式二 :手动编辑 

# kuberctl  edit rc myweb
设置 replicas

服务发现和负载均衡

1、查看当前rc和pod
# kubectl  get all  -o wide  --show-labels
NAME       DESIRED   CURRENT   READY     AGE       CONTAINER(S)   IMAGE(S)       SELECTOR    LABELS
rc/myweb   3         3         3         21s       nginx          nginx:latest   app=myweb   app=myweb NAME             READY     STATUS    RESTARTS   AGE       IP            NODE           LABELS
po/myweb-blrwr   1/1       Running   0          51s       172.16.30.3   192.168.4.12   app=myweb
po/myweb-8dkee   1/1       Running   0          21s       172.16.30.5   192.168.4.12 app=myweb po/myweb-7wsek   1/1       Running   0          21s       172.16.30.6   192.168.4.12 app=myweb
po/test    1/1       Running   0          56s       172.16.30.2   192.168.4.12 app=web
2、修改test标签:app=myweb
# kubectl edit pod test app: myweb kubectl
get pod NAME READY STATUS RESTARTS AGE po/myweb-blrwr 1/1 Running 0 8m po/myweb-8dkee 1/1 Running 0 8m po/test 1/1 Running 0 1h

3、小结
1)因为rc控制器设置最少保持3个副本
2)rc控制器是根据Labels 标签来区分的
3)test的标签和myweb控制器的标签一样,所以就删除了存活时间最短的容器(rc认为pod存活久的比较稳定,默认删除新的pod)

rc滚动的升级和回滚

1、创建nginx两个版本yaml文件
# cat nginx-1.13-rc.yaml 
kind: ReplicationController apiVersion: v1 metadata: name: nginx spec: replicas:
1 selector: app: nginx template: metadata: labels: app: nginx spec: containers: - name: nginx image: nginx:1.13 ports: - containerPort: 80 # cat nginx-1.15-rc.yaml kind: ReplicationController apiVersion: v1 metadata: name: nginx spec: replicas: 1 selector: app: nginx template: metadata: labels: app: nginx spec: containers: - name: nginx image: nginx:1.15 ports: - containerPort: 80 2、滚动升级 # kubectl create -f nginx-1.13-rc.yaml 创建旧版本nginx # kubectl rolling-update nginx -f nginx-1.15-rc.yaml --update-period=20s # curl -I 172.16.30.2 检查版本
3、一键回滚 # kubectl rolling-update nginx -f nginx-1.13-rc.yaml --update-period=10s # curl -I 172.16.30.2 检查版本

3、deployment资源

rc在滚动升级之后,会造成服务访问中断,于是k8s引入了deployment资源

对比rc的好处:

升级服务不中断
不依赖yaml文件
rc标签选择器不支持模糊匹配,rs标签选择器支持模糊匹配

通过文件创建deployment

1、创建yaml文件
# cat nginx-dep.yaml 
apiVersion: extensions/v1beta1
kind: Deployment
metadata:
  name: nginx-dep
spec:
  replicas: 3
  template:
    metadata:
      labels:
        app: nginx
    spec:
      containers:
      - name: nginx
        image: 192.168.4.11:5000/nginx:1.13
        ports:
        - containerPort: 80
2、启动
# kubectl create -f nginx-dep.yaml 

3、查看
# kubectl get deploy

DESIRED :   Pod副本数量的期望值,即Deployment里定义的Replica。
CURRENT:   当前实际的Replica数量,当这个值不断增加,达到DESIRED时表明部署完成。
UP-TO-DATE:最新版本的Pod副本数量,用于指示在滚动升级过程中有多少Pod副本已经成功升级。
AVAILABLE:  当前集群中可用的Pod副本数量(当前存活的Pod数量)

自动加载deployment配置

deployment编辑配置之后可以自动加载,不想rc还需要删除再启动。
1、修改副本数
# kubectl edit deployment nginx-dep
 replicas: 2

2、查看
# kubectl get all -o wide

通过命令行创建deployment

1、命令创建
# kubectl run nginx-dep2 --image=192.168.4.11:5000/nginx:1.15 --replicas=1 --record

2、查看
# kubectl get all

手动扩容缩容

# kubectl scale deployment nginx-dep2  --replicas=2
# kubectl get all

升级pod镜像版本

1、查看pod镜像版本及名字
# kubectl get rs -o wide

2、升级镜像
# kubectl
set image deploy nginx-dep2 nginx-dep2=192.168.4.11:5000/nginx:1.15 nginx-dep2=192.168.4.11:5000/nginx:1.15 的名字
3、查看升级结果 # kubectl get rs -o wide 4、查看升级状态 # kubectl rollout status deployment nginx-dep2 5、查看升级历史 # kubectl rollout history deployment nginx-dep2 6、查看历史版本详情 # kubectl rollout history deployment nginx-dep2 --revision=2

回滚pod镜像版本

1、查看历史版本
# kubectl rollout history deployment nginx-dep2

2、执行回滚指定版本
# kubectl rollout undo deployment nginx-dep2 --to-revision=1

3、检查回滚结果
# kubectl get pods -o wide 
# curl -I 172.16.30.2

生产建议--record

--record参数: 记录执行的操作步骤和相关信息,生产建议采用这种方式创建deployment

rc和deployment的升级区别

rc:
# kubectl rolling-update nginx -f nginx-1.15-rc.yaml  --update-period=20s  升级
# kubectl rolling-update nginx -f nginx-1.13-rc.yaml  --update-period=20s  回滚

deploy:
# kubectl create   -f nginx-dep.yaml  --record                             文件创建
# kubectl set image deploy nginx-dep nginx=192.168.4.11:5000/nginx:1.15    升级或回滚

# kubectl run nginx-dep2 --image=192.168.4.11:5000/nginx:1.15 --replicas=1 --record
# kubectl set image deploy nginx-dep2 nginx-dep2=192.168.4.11:5000/nginx:1.15

# kubectl rollout history deployment nginx-dep2                            查看历史版本
# kubectl rollout undo deployment nginx-dep2 --to-revision=1               回滚指定版本

rc修改(edit)配置文件,需要启动新容器才生效
deploy修改配置文件,立即生效

4、service资源

介绍

Pod挂掉后ip地址会改变,外部不能访问容器内的服务,service是提供了一个固定IP,cluster ip(vip),通过该固定的IP来进行通信
service的作用:帮助外界用户访问k8s内的服务,并且提供负载均衡 service默认使用iptables来实现负载均衡, k8s
1.8新版本中推荐使用lvs(四层负载均衡 传输层tcp,udp)
Service同RC一样,都是通过Label来关联Pod的。在Service的yaml文件中定义了selector中的label为app:my
-web,那么这个Service会将Pod-->metadata-->labeks中label为app:my-web的Pod作为分发请求的后端。当Pod发生变化时(增加、减少、重建等),Service会及时更新。这样一来,Service就可以作为Pod的访问入口,起到代理服务器的作用,而对于访问者来说,通过Service进行访问,无需直接感知Pod。 需要注意的是,Kubernetes分配给Service的固定IP是一个虚拟IP,并不是一个真实的IP,在外部是无法寻址的。真实的系统实现上,Kubernetes是通过Kube-proxy组件来实现的虚拟IP路由及转发。所以在之前集群部署的环节上,我们在每个Node上均部署了Proxy这个组件,从而实现了Kubernetes层级的虚拟转发网络。

kubernetes中的三种IP

Node IP:    Node节点IP地址
Cluster IP: Service的IP地址
Pod IP:     Pod的IP地址

Service负载均衡

1、创建
# kubectl create -f myweb-svc.yaml 
# cat myweb-svc.yaml 
apiVersion: v1
kind: Service
metadata:
  name: nginx
spec:
  type: NodePort        #转发方式
  ports:
    - port: 80          #clusterIP(vip)端口
      nodePort: 30001   #node端口
      targetPort: 80    #pod 端口
  selector:         
    run: nginx-dep2     #标签选择器(选择rc的pod资源)

2、查看service状态
# kubectl describe svc nginx                             
Name:                   nginx
Namespace:              default
Labels:                 <none>
Selector:               run=nginx-deployment2    #搜索标签
Type:                   NodePort                 #转发方式
IP:                     10.254.18.231            #虚拟IP
Port:                   <unset> 80/TCP
NodePort:               <unset> 30001/TCP        #node暴露端口
Endpoints:              172.16.30.2:80,172.16.30.3:80,172.16.30.5:80 + 2 more... #pod
Session Affinity:       None

3、访问测试
是由kuber-proxy服务提供的
# curl   192.168.4.11:30000
# curl   192.168.4.12:30000

修改Service的nodePort范围

默认分配30000-32767
1、修改默认端口
# vim /etc/kubernetes/apiserver
KUBE_API_ARGS="--service-node-port-range=10000-50000"

2、启动服务
# systemctl restart kube-apiserver.service

命令行创建service资源

# kubectl expose rc  nginx --type=NodePort --port=80
# kubectl expose 资源类型  资源名称  端口类型  暴漏端口

其他

1、非交互式修改副本数量
# kubectl scale rc nginx --replicas=2 调度 名称 副本数 2、进入容器
# kubectl exec
-it nginx-ld22v /bin/bash

3、网站curl 不通 排错思路:
内核转发参数,iptables规则
重启服务flanneld,docker , kubelet ,kube-proxy

四、项目实践

1、简单web应用tomcat+mysql

准备镜像

1、下载
# docker pull kubeguide/tomcat-app:v2
# docker pull mysql:5.7

2、改名并上传
# docker tag docker.io/kubeguide/tomcat-app:v1  192.168.4.11:5000/tomcat-app:v1
# docker tag docker.io/mysql:5.7    192.168.4.11:5000/mysql:5.7
# docker push  192.168.4.11:5000/tomcat-app:v1
# docker push  192.168.4.11:5000/mysql:5.7

部署mysql 服务

1、创建yaml文件
# vim mysql-dep.yaml
apiVersion: extensions/v1beta1
kind: Deployment                       
metadata:  
  name: mysql                          #Deployment的名称,全局唯一
spec:
  replicas: 1                          #Pod副本的数量
  selector:
    matchLabels:                       #定义RS的标签
      app: mysql                       #符合目标的Pod拥有此标签
  template:                            #根据此模版创建Pod的副本(实例)
    metadata:
       labels:
         app: mysql                    #Pod拥有的标签,对应Deployment的selector
    spec:
       containers:                     #Pod内,定义容器
       - name: mysql                   #容器名称
         image: 192.168.0.136:5000/mysql:5.7             
         ports:
         - containerPort: 3306         #容器应用监听的端口
         env:                          #环境变量
         - name: MYSQL_ROOT_PASSWORD   #设置root初始密码
           value: "123456"

# vim mysql-rc.yaml
apiVersion: v1
kind: ReplicationController            #副本控制器RC
metadata:  
  name: mysql                          #RC的名称,全局唯一
spec:
  replicas: 1                          #Pod副本的数量
  selector:
    app: mysql                         #符合目标的Pod拥有此标签
  template:                            #根据此模版创建Pod的副本(实例)
    metadata:
       labels:
         app: mysql                    #Pod副本拥有的标签,对应RC的selector
    spec:
       containers:                     #Pod内,定义容器
       - name: mysql                   #容器名称
         image: 192.168.0.136:5000/mysql:5.7             
         ports:
         - containerPort: 3306         #容器应用监听的端口
         env:                          #环境变量
         - name: MYSQL_ROOT_PASSWORD   #设置root初始密码
           value: "123456"

2、创建mysql-deployment
# kubectl create -f mysql-dep.yaml

3、创建mysql serveice文件
# vim mysql-svc.yaml
apiVersion: v1
kind: Service
metadata:
  name: mysql
spec:
  type: NodePort
  ports:
  - port: 3306
    nodePort: 30001
  selector:
    app: mysql

4、创建MySQL svc
# kubectl create -f mysql-svc.yaml

部署web服务

1、创建yaml文件
# vim   tomcat-app-dep.yaml
apiVersion: extensions/v1beta1
kind: Deployment
metadata:
  name: tomcat-app
spec:
  replicas: 3
  template:
    metadata:
      labels:
        app: tomcat-app
    spec:
      containers:
      - name: tomcat-app
        image: 192.168.0.136:5000/tomcat-app:v1
        ports:
        - containerPort: 8080
        env:
        - name: MYSQL_SERVICE_HOST
          value: 'mysql'                  #这是一个坑,最好写mysql服务的Cluster IP
        - name: MYSQL_SERVICE_PORT
          value: '3306'

# vim  tomcat-app-rc.yaml 
apiVersion: v1
kind: ReplicationController
metadata:
  name: myweb
spec:
  replicas: 1
  selector:
    app: myweb
  template:
    metadata:
      labels:
        app: myweb
    spec:
      containers:
        - name: myweb
          image: kubeguide/tomcat-app:v2
          ports:
          - containerPort: 8080
          env:
          - name: MYSQL_SERVICE_HOST
            value: 'mysql'               mysql为域名要解析
          - name: MYSQL_SERVICE_PORT
            value: '3306'

2、创建tomcat-app-deployment
# kubectl create -f tomcat-app-dep.yaml 

3、创建tomcat-app service文件
# vim tomcat-app-svc.yaml 
apiVersion: v1
kind: Service
metadata:
  name: tomcat-app
spec:
  type: NodePort
  ports:
    - port: 8080
      name: myweb-svc
      nodePort: 30002
  selector:
    app: tomcat-app

4、创建tomcat-app service
# kubectl create -f tomcat-app-svc.yaml 

测试

1、查看所有svc、pod的状态及端口
# kubectl get all -o wide 

2、测试pod
# curl    172.16.30.2:8080 -I
# telnet  172.16.30.3 3306

3、测试svc
# curl    10.254.102.27:8080 -I
# telnet  10.254.217.119 3306

4、测试node
# curl 192.168.4.12:30008 -I
http://192.168.4.11:30008
http://192.168.4.11:30008/demo
插入一条数据

5、主要
# cat tomcat-app-dep.yaml
env:
        - name: MYSQL_SERVICE_HOST
          value:  '10.254.217.119'
tomcat-app-dep.yaml 文件mysql是域名要解析,没有dns,只能写cluster IP MySQL没有持久化,pod的数据是临时的,如果删除pod或者重启deployment,数据会丢失

 2、持久化存储

 数据持久化方式:

1、Volume
Docker数据持久化方案

2、k8s支持的数据卷类型
1)本地数据卷
EmptyDir:Pod配置了EmpyDir数据卷,只要Pod 存在,数据卷就会存在,Pod被删除,数据卷也会被删除,并且永久丢失,适合实现Pod中容器的文件共享。
HostPath:数据卷将容器宿主机上的文件系统挂载到Pod中。

2)网络共享数据卷
网络数据卷包含以下几种:NFS、iSCISI、GlusterFS、RBD(Ceph Block Device)、Flocker、AWS Elastic Block Store、GCE Persistent Disk

3)PV和PVC
PV(Persistent Volume):由管理员添加的的一个存储的描述,是一个全局资源,包含存储的类型,存储的大小和访问模式等。它的生命周期独立,例如当使用它的Pod销毁时对PV没有影响。
PVC(Persistent Volume Claim):是Namespace里的资源,描述对PV的一个请求。请求信息包含存储大小,访问模式等。

4)信息数据卷
信息数据卷:主要用来给容器传递配置信息,如Secret(处理敏感配置信息,密码、Token等)、Downward API(通过环境变量的方式告诉容器Pod的信息)、Git Repo(将Git仓库下载到Pod中),都是将Pod的信息以文件形式保存,然后以数据卷方式挂载到容器中,容器通过读取文件获取相应的信息

通过NFS实现持久化存储

配置NFS存储服务

1、环境
k8s-master  nfs-server
k8s-node    nfs-client

2、配置nfs
master:
# yum install -y nfs-utils      安装
# mkdir -p /data/tomcat         创建共享目录
# cat /etc/exports              创建共享配置文件
/data 192.168.4.0/24(rw,no_root_squash,no_all_squash,sync)
# systemctl start nfs           启动服务
node:
# yum install -y nfs-utils      安装客户端

创建PV-持久卷

1、创建pv文件
# cat  pv_nfs.yaml
apiVersion: v1
kind: PersistentVolume                     #资源类型
metadata:
  name: mysql-tomcat
  labels:
    type: mysql-tomcat-nfs
spec:
  capacity:
    storage: 5Gi 
  accessModes:
    - ReadWriteMany                       #访问模式,多个客户端读写
  persistentVolumeReclaimPolicy: Recycle  #回收策略-可以回收
  nfs:
    path: "/data/tomcat"
    server: 192.168.4.11                  #k8s-nfs matser
    readOnly: false                       #只读

2、创建pv
# kubectl create  -f pv_nfs.yaml 

3、查看PV信息
# kubectl describe pv

创建PVC-持久卷

1、创建PVC文件
# cat pvc_nfs.yaml 
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  name: mysql-tomcat-pvc
spec:
  accessModes:
  - ReadWriteMany      
  resources:
     requests:
       storage: 1Gi

2、创建pvc
# kubectl create  -f pv_nfs.yaml 

3、查看pvc
# kubectl get pvc

MySQL挂载共享存储

1、重新修改mysql的yaml文件
# cat mysql-dep.yaml 
apiVersion: extensions/v1beta1
kind: Deployment                       #控制器Deployment
metadata:  
  name: mysql                          #Deployment的名称,全局唯一
spec:
  replicas: 1                          #Pod副本的数量
  template:                            #根据此模版创建Pod的副本(实例)
    metadata:
       labels:
         app: mysql                    #Pod副本拥有的标签,对应Deployment的selector
    spec:
       containers:                     #Pod内,定义容器
       - name: mysql                   #容器名称
         image: 192.168.0.136:5000/mysql:5.7          
         ports:
         - containerPort: 3306         #容器监听的端口
         
         volumeMounts:
         - name: mysql-data-pvc        #容器内挂载点名称
           mountPath: /var/lib/mysql   #容器内挂载目录
         env:                          #注入容器内的环境变量
         - name: MYSQL_ROOT_PASSWORD   #这里设置root初始密码
           value: "123456"
       volumes:  
       - name: mysql-data-pvc           #数据卷名称,要和容器内挂载点名称一致
         persistentVolumeClaim:
           claimName: mysql-tomcat-pvc  #pvc名称

2、更新yaml文件
# kubectl apply -f mysql-dep.yaml

3、检查
# ls /data/tomcat/
# df -h
http:
//192.168.4.12:30008/demo 插入一条数据
进入数据库,查看插入的数据 删除pod,自动新建pod,再次查看数据 # kubectl delete pod mysql-1215028969-3d366 http://192.168.4.12:30008/demo 查看数据是否存在

不创建pv和pvc,使用nfs实现持久化存储

1、创建mysql的Deployment定义文件
# vim  mysql-dep.yaml
apiVersion: extensions/v1beta1                  #apiserver的版本
kind: Deployment                                #副本控制器deployment,管理pod和RS
metadata:
  name: mysql                                   #deployment的名称,全局唯一
spec:
  replicas: 1                                   #Pod副本期待数量
  selector:
    matchLabels:                                #定义RS的标签
      app: mysql                                #符合目标的Pod拥有此标签
  strategy:                                     #定义升级的策略
    type: RollingUpdate                         #滚动升级,逐步替换的策略
  template:                                     #根据此模板创建Pod的副本(实例)
    metadata:
      labels:
        app: mysql                              #Pod副本的标签,对应RS的Selector
    spec:
      containers:                               #Pod里容器的定义部分
      - name: mysql                             #容器的名称
        image: mysql:5.7                        #容器对应的docker镜像
        volumeMounts:                           #容器内挂载点的定义部分       
- name: mysql-data #容器内挂载点名称 mountPath: /var/lib/mysql #容器内挂载路径,mysql的数据目录 ports: - containerPort: 3306 #容器暴露的端口号 env: #写入到容器内的环境容量 - name: MYSQL_ROOT_PASSWORD #定义了一个mysql的root密码的变量 value: "123456" volumes: #本地需要挂载到容器里的数据卷定义部分
- name: mysql-data #数据卷名称,需要与容器内挂载点名称一致 nfs:
server: 192.168.4.11
path: "/data/tomcat"
2、创建deployment、RS、Pod和容器 # kubectl create -f mysql-dep.yaml 3、创建mysql的service定义文件 # vim mysql-svc.yaml apiVersion: v1 kind: Service #表示Kubernetes Service metadata: name: mysql #Service的名称 spec: ports: - port: 3306 #Service提供服务的端口号 selector: app: mysql #Service对应的Pod的标签 4、创建Service # kubectl create -f mysql-svc.yaml 5、测试
http://192.168.4.12:30008/demo   插入一条数据
进入数据库,查看插入的数据
删除pod,自动新建pod,再次查看数据
# kubectl  delete pod mysql-761066058-bgh3r
http://192.168.4.12:30008/demo   查看数据是否存在

emptyDir类型

删除容器后数据会保存,但是删除pod后数据丢失
# cat mysql-rc.yml 
apiVersion: v1
kind: ReplicationController
metadata:
  name: mysql
  namespace: tomcat
spec:
  replicas: 1
  selector:
    app: mysql
  template:
    metadata:
      labels:
        app: mysql
    spec:
      volumes:        *
      - name: mysql   *
        emptyDir: {}  *
      containers:
        - name: mysql
          image: 192.168.4.11:5000/mysql:5.7
          volumeMounts:                  *
          - name: mysql                  *
            mountPath: /var/lib/mysql    *
          ports:
          - containerPort: 3306
          env:
          - name: MYSQL_ROOT_PASSWORD
            value: '123456'

HostPath类型

删除容器与删除pod,数据都会保存
# cat mysql-rc.yml 
apiVersion: v1
kind: ReplicationController
metadata:
  name: mysql
  namespace: tomcat
spec:
  replicas: 1
  selector:
    app: mysql
  template:
    metadata:
      labels:
        app: mysql
    spec:
      nodeName: 10.0.0.13  
      volumes:
      - name: mysql
        hostPath:            *
          path: /data/mysql  *
      containers:
        - name: mysql
          image: 10.0.0.11:5000/mysql:5.7
          volumeMounts:      *
          - name: mysql      *
            mountPath: /var/lib/mysql  *
          ports:
          - containerPort: 3306
          env:
          - name: MYSQL_ROOT_PASSWORD
            value: '123456'

五、HPA水平自动伸缩

HPA简介

Horizontal Pod Autoscaling,简称HPA,是Kubernetes中实现POD水平自动伸缩的功能。
自动扩展主要分为两种: 水平扩展(scale
out),针对于实例数目的增减 垂直扩展(scal up),即单个实例可以使用的资源的增减, 比如增加cpu和增大内存

自动伸缩

1、创建测试yaml文件
# vim k8s_deploy.yaml
apiVersion: extensions/v1beta1
kind: Deployment
metadata:
  name: nginx-deployment
spec:
  replicas: 3
  template:
    metadata:
      labels:
        app: nginx
    spec:
      containers:
      - name: nginx
        image: 10.0.0.11:5000/nginx:1.13
        ports:
        - containerPort: 80
        resources:    # 资源限制
          limits:    # 最大资源是多少
            cpu: 100m
          requests:    # 最小需要多少资源
            cpu: 100m

2、命令行创建一个svc资源
# kubectl expose deployment nginx-deployment --port=80 --target-port=80 --type=NodePort

3、命令行方式创建弹性伸缩规则
# kubectl autoscale deployment nginx-deployment --max=10 --min=2 --cpu-percent=10
# cpu生产建议设为60。能有一个40的缓冲

4、查看dpa描述
# kubectl describe hpa
Name:                nginx-deployment
Namespace:            default
Labels:                <none>
Annotations:            <none>
CreationTimestamp:        Tue, 24 Dec 2019 05:06:45 +0800
Reference:            Deployment/nginx-deployment
Target CPU utilization:        10%
Current CPU utilization:    0%
Min replicas:            2
Max replicas:            10

5、修改副本数为1
# kubectl edit deployment nginx-deployment
# kubectl get all    查看pod数量

6、开始压测
# ab -n 400000 -c 50 http://192.168.4.11:30008

调用原理

1、创建pod和service
# kubectl run php-apache --image=gcr.io/google_containers/hpa-example --requests=cpu=200m --expose --port=80

2、创建autoscaler
# kubectl autoscale deployment php-apache --cpu-percent=50 --min=1 --max=10

3、增加负载
# kubectl run -i --tty load-generator --image=busybox /bin/sh
$ while true; do wget -q -O- http://php-apache.default.svc.cluster.local; done

4、查看负载及pod
# kubectl get hpa
# kubectl get deployment
pod增加到7个
5、删除创建的负载
pod数量自动降回1个 # kubectl
get hpa # kubectl get deployment

小结
1、首先最底层的资源永远都是pod
2、比pod高级一点的资源叫rc副本控制器
3、在pod上面有一个高级的rs
4、那谁来管理rs呢?是deployment
5、HPA自动管理deployment,deployment设置为1,HPA最低设置为3,deployment这就会被自动设计为3个
HPA-yaml文件
# vim nginx-hpa.yaml apiVersion: autoscaling
/v1 kind: HorizontalPodAutoscaler metadata: name: nginx # 名称 namespace: default #k8s命名空间 spec: maxReplicas: 10 # 最大副本数 minReplicas: 3 # 最小副本数 scaleTargetRef: apiVersion: apps/v1beta1 kind: Deployment name: nginx # 监控名为nginx的Deployment targetCPUUtilizationPercentage: 80 # cpu 阈值

六、其他项目

1、安装部署Dashboard

1、 获取kubernetes-dashboard.yaml文件
去官网,github上下载对应版本的源码包文件。
https://github.com/kubernetes/kubernetes/blob/master/CHANGELOG-1.5.md#downloads-for-v152

# wget https://dl.k8s.io/v1.5.2/kubernetes.tar.gz
# cd kubernetes/cluster/addons/dashboard/
# cp dashboard-controller.yaml  /root/dashboard-dep.yaml
# cp dashboard-service.yaml     /root/dashboard-svc.yaml

2、修改yaml文件 # vim dashboard-dep.yaml image: gcr.io/google_containers/kubernetes-dashboard-amd64:v1.5.0 arg: - --apiserver-host=http://192.168.4.11:8080 3、启动 # kubectl create -f dashboard-dep.yaml # kubectl create -f dashboard-svc.yaml 4、查看 # kubectl get -n kube-system all http://192.168.4.11:8080/ui

 dashboard-dep.yaml文件内容

apiVersion: extensions/v1beta1
kind: Deployment
metadata:
# Keep the name in sync with image version and
# gce/coreos/kube-manifests/addons/dashboard counterparts
  name: kubernetes-dashboard-latest
  namespace: kube-system
spec:
  replicas: 1
  template:
    metadata:
      labels:
        k8s-app: kubernetes-dashboard
        version: latest
        kubernetes.io/cluster-service: "true"
    spec:
      nodeName: k8s-node2
      containers:
      - name: kubernetes-dashboard
        image: index.tenxcloud.com/google_containers/kubernetes-dashboard-amd64:v1.4.1
        imagePullPolicy: IfNotPresent
        resources:
          # keep request = limit to keep this container in guaranteed class
          limits:
            cpu: 100m
            memory: 50Mi
          requests:
            cpu: 100m
            memory: 50Mi
        ports:
        - containerPort: 9090
        args:
         -  --apiserver-host=http://192.168.4.11:8080
        livenessProbe:
          httpGet:
            path: /
            port: 9090
          initialDelaySeconds: 30
          timeoutSeconds: 30

dashboard-svc.yaml文件内容

apiVersion: v1
kind: Service
metadata:
  name: kubernetes-dashboard
  namespace: kube-system
  labels:
    k8s-app: kubernetes-dashboard
    kubernetes.io/cluster-service: "true"
spec:
  selector:
    k8s-app: kubernetes-dashboard
  ports:
  - port: 80
    targetPort: 9090
没用nodeport,不做端口映射

 Pod控制器

Kubernetes中内建了很多controller(控制器),分为有状态应用和无状态应用
Pod控制器有多种类型:
Deployment:工作在ReplicaSet之上,用于管理无状态应用,目前来说最好的控制器。支持滚动更新和回滚功能,还提供声明式配置。
DaemonSet:确保集群中的每一个节点只运行特定的pod副本,通常用于实现系统级后台任务。比如ELK,要求:服务是无状态的;服务必须是守护进程
Job:只要完成就立即退出,不需要重启或重建。
Cronjob:周期性任务控制,不需要持续后台运行,
StatefulSet:管理有状态应用,如mysql,redis等。
ReplicaSet: 代用户创建指定数量的pod副本数量,确保pod副本数量符合预期状态,并且支持滚动式自动扩容和缩容功能。

DaemonSet:一个node节点只能启动一个,监控pod、日志收集pod
pet sets: 有状态,适合数据库之类的

namespace

1、介绍
Namespace(命名空间):在很多情况下用于实现多租户的资源隔离。
同一个namespace下面不允许出现两个service叫mysql
生产环境中把不同的应用放到不同的namespace中。

2、namespace管理命令
创建namespace
# kubectl create namespace nginx
 
查看namespace
# kubectl get namespace 
 
删除namespace
# kubectl delete namespace qiangge
注:特别危险!会删除namespace下所有的k8s资源

3、yaml文件
# vim nginx-rc.yaml 
apiVersion: v1
kind: ReplicationController
metadata:
  name: myweb
  namespace: nginx-nm
spec:
  replicas: 2
  selector:
    app: myweb
  template:
    metadata:
      labels:
        app: myweb
    spec:
      containers:
      - name: myweb
        image: 10.0.0.11:5000/nginx:1.13
        ports:
        - containerPort: 80

# vim nginx-svc.yaml
apiVersion: v1
kind: Service
metadata:
  name: myweb
  namespace: nginx-nm
spec:
  type: ClusterIP
  ports:
    - port: 80
      targetPort: 80
  selector:
    app: myweb

通过apiservice反向代理访问service

访问k8s中应用,在svc中配置
第一种:NodePort类型 
  type: NodePort
  ports:
    - port: 80
      targetPort: 80
      nodePort: 30008

第二种:ClusterIP类型
  type: ClusterIP
  ports:
    - port: 80
      targetPort: 80
      
http://192.168.4.11:8080/api/v1/proxy/namespaces/命令空间/services/service的名字/

2、部署dns组件

dns服务的作用:将svc的名字解析成VIP地址
1、获取yaml文件
去官网,github上下载对应版本的源码包文件。
https://github.com/kubernetes/kubernetes/blob/master/CHANGELOG-1.5.md#downloads-for-v152
# wget https://dl.k8s.io/v1.5.2/kubernetes.tar.gz
# cd kubernetes/cluster/gce/coreos/kube-manifests/addons/dns/
# cp skydns-rc.yamll    /root/skydns-rc.yaml
# cp skydns-svc.yaml    /root/skydns-svc.yaml

2、修改yaml文件
     image: myhub.fdccloud.com/library/kubedns-amd64:1.9
     - --domain=cluster.local.
     - --kube-master-url=http://192.168.4.11:8080
     image: myhub.fdccloud.com/library/kube-dnsmasq-amd64:1.4
     image: myhub.fdccloud.com/library/dnsmasq-metrics-amd64:1.0
     image: myhub.fdccloud.com/library/exechealthz-amd64:1.2
     - --cmd=nslookup kubernetes.default.svc.cluster.local 127.0.0.1 >/dev/null
     - --cmd=nslookup kubernetes.default.svc.cluster.local 127.0.0.1:10053 >/dev/null

3、启动dns
# kubectl create -f skydns-rc.yaml
# kubectl create -f skydns-svc.yaml

4、修改node节点kubelet配置文件并重启服务
# cat /etc/kubernetes/kubelet
KUBELET_ARGS="--cluster_dns=10.254.230.254 --cluster_domain=cluster.local"
# systemctl restart kubelet

5、测试
# cat  test_dns_pod.yaml
apiVersion: v1
kind: Pod
metadata:
  labels:
    name: busybox
    role: master
  name: busybox2
spec:
  containers:
  - name: busybox
    image: docker.io/busybox:latest
    imagePullPolicy: IfNotPresent
    command:
    - sleep
    - "3600"

# kubectl exec -it busybox sh
# cat /etc/resolv.conf 
测试
# nslookup kubernetes
# nslookup kubernetes.default.cluster.local
# nslookup kubernetes.default.svc.cluster.local

skydns-rc.yaml的内容

apiVersion: extensions/v1beta1
kind: Deployment
metadata:
  name: kube-dns
  namespace: kube-system
  labels:
    k8s-app: kube-dns
    kubernetes.io/cluster-service: "true"
spec:
  # replicas: not specified here:
  # 1. In order to make Addon Manager do not reconcile this replicas parameter.
  # 2. Default is 1.
  # 3. Will be tuned in real time if DNS horizontal auto-scaling is turned on.
  strategy:
    rollingUpdate:
      maxSurge: 10%
      maxUnavailable: 0
  selector:
    matchLabels:
      k8s-app: kube-dns
  template:
    metadata:
      labels:
        k8s-app: kube-dns
      annotations:
        scheduler.alpha.kubernetes.io/critical-pod: ''
        scheduler.alpha.kubernetes.io/tolerations: '[{"key":"CriticalAddonsOnly", "operator":"Exists"}]'
    spec:
      containers:
      - name: kubedns
        image: myhub.fdccloud.com/library/kubedns-amd64:1.9
        resources:
          # TODO: Set memory limits when we've profiled the container for large
          # clusters, then set request = limit to keep this container in
          # guaranteed class. Currently, this container falls into the
          # "burstable" category so the kubelet doesn't backoff from restarting it.
          limits:
            memory: 200Mi
          requests:
            cpu: 100m
            memory: 100Mi
        livenessProbe:
          httpGet:
            path: /healthz-kubedns
            port: 8080
            scheme: HTTP
          initialDelaySeconds: 60
          timeoutSeconds: 5
          successThreshold: 1
          failureThreshold: 5
        readinessProbe:
          httpGet:
            path: /readiness
            port: 8081
            scheme: HTTP
          # we poll on pod startup for the Kubernetes master service and
          # only setup the /readiness HTTP server once that's available.
          initialDelaySeconds: 3
          timeoutSeconds: 5
        args:
        # command = "/kube-dns"
        - --domain=cluster.local.
        - --dns-port=10053
        - --config-map=kube-dns
        - --kube-master-url=http://192.168.4.11:8080
        env:
          - name: PROMETHEUS_PORT
            value: "10055"
        ports:
        - containerPort: 10053
          name: dns-local
          protocol: UDP
        - containerPort: 10053
          name: dns-tcp-local
          protocol: TCP
        - containerPort: 10055
          name: metrics
          protocol: TCP
      - name: dnsmasq
        image: myhub.fdccloud.com/library/kube-dnsmasq-amd64:1.4
        livenessProbe:
          httpGet:
            path: /healthz-dnsmasq
            port: 8080
            scheme: HTTP
          initialDelaySeconds: 60
          timeoutSeconds: 5
          successThreshold: 1
          failureThreshold: 5
        args:
        - --cache-size=1000
        - --no-resolv
        - --server=127.0.0.1#10053
        - --log-facility=-
        ports:
        - containerPort: 53
          name: dns
          protocol: UDP
        - containerPort: 53
          name: dns-tcp
          protocol: TCP
      - name: dnsmasq-metrics
        image: myhub.fdccloud.com/library/dnsmasq-metrics-amd64:1.0
        livenessProbe:
          httpGet:
            path: /metrics
            port: 10054
            scheme: HTTP
          initialDelaySeconds: 60
          timeoutSeconds: 5
          successThreshold: 1
          failureThreshold: 5
        args:
        - --v=2
        - --logtostderr
        ports:
        - containerPort: 10054
          name: metrics
          protocol: TCP
        resources:
          requests:
            memory: 10Mi
      - name: healthz
        image: myhub.fdccloud.com/library/exechealthz-amd64:1.2
        resources:
          limits:
            memory: 50Mi
          requests:
            cpu: 10m
            # Note that this container shouldn't really need 50Mi of memory. The
            # limits are set higher than expected pending investigation on #29688.
            # The extra memory was stolen from the kubedns container to keep the
            # net memory requested by the pod constant.
            memory: 50Mi
        args:
        - --cmd=nslookup kubernetes.default.svc.cluster.local 127.0.0.1 >/dev/null
        - --url=/healthz-dnsmasq
        - --cmd=nslookup kubernetes.default.svc.cluster.local 127.0.0.1:10053 >/dev/null
        - --url=/healthz-kubedns
        - --port=8080
        - --quiet
        ports:
        - containerPort: 8080
          protocol: TCP
      dnsPolicy: Default  # Don't use cluster DNS.

skydns-svc.yaml 的内容

apiVersion: v1
kind: Service
metadata:
  name: kube-dns
  namespace: kube-system
  labels:
    k8s-app: kube-dns
    kubernetes.io/cluster-service: "true"
    kubernetes.io/name: "KubeDNS"
spec:
  selector:
    k8s-app: kube-dns
  clusterIP: 10.254.230.254 
  ports:
  - name: dns
    port: 53
    protocol: UDP
  - name: dns-tcp
    port: 53
    protocol: TCP

 3、部署heapster监控

 介绍

Heapster是kubernetes集群监控工具。在kubernetes中,cAdvisor被集成到kubelet中。通过netstat可以查看到kubelet新开了一个4194的端口,这就是cAdvisor监听的端口,现在我们然后可以通过http://<node-ip>:4194的方式访问到cAdvisor。Heapster就是通过每个node上的kubelet,也就是实际的cAdvisor上收集数据并汇总,保存到后端存储中。
Heapster支持多种后端存储,包括influxDB,Elasticsearch,Kafka等,我们使用influxDB作为后端存储来展示heapster的相关配置。需要说明的是,heapster依赖kubernetes dns配置

部署

1、 获取yaml文件
去官网,github上下载对应版本的源码包文件。
https://github.com/kubernetes/kubernetes/blob/master/CHANGELOG-1.5.md#downloads-for-v152
# wget https://dl.k8s.io/v1.5.2/kubernetes.tar.gz
# cd kubernetes/cluster/addons/cluster-monitoring/influxdb/
# mkdir  -p  /data/yaml
# cp *.yaml  /data/yaml

2、修改yaml文件
查看image地址,添加本地查找
# grep 'image' heapster-controller.yaml 
        - image: gcr.io/google_containers/heapster:v1.2.0
          imagePullPolicy: IfNotPresent    #本地找镜像
        - image: gcr.io/google_containers/heapster:v1.2.0
          imagePullPolicy: IfNotPresent
        - image: gcr.io/google_containers/addon-resizer:1.6
           imagePullPolicy: IfNotPresent
        - image: gcr.io/google_containers/addon-resizer:1.6
           imagePullPolicy: IfNotPresent
# grep 'image' influxdb-grafana-controller.yaml 
        - image: gcr.io/google_containers/heapster_influxdb:v0.7
          imagePullPolicy: IfNotPresent
        - image: gcr.io/google_containers/heapster_grafana:v3.1.1
          imagePullPolicy: IfNotPresent
3、下载镜像文件并修改
# docker search heapster:v1.2.0
# docker pull   heapster:v1.2.0
# docker tag  heapster:v1.2.0   gcr.io/google_containers/heapster:v1.2.0

4、启动
# kubectl create -f /data/yaml  批量创建

5、报错处理
修改heapster-controller.yaml
command:
        - /heapster
        - --source=kubernetes:http://192.168.4.11:8080?inClusterConfig=false   数据源在从哪里,apiserver拿数据
        - --sink=influxdb:http://monitoring-influxdb:8086                      数据存储到哪里,influxdb存数据
heapster依赖kubernetes dns

heapster-controller.yaml 文件内容

apiVersion: v1
kind: ReplicationController
metadata:
  labels:
    k8s-app: heapster
    name: heapster
    version: v6
  name: heapster
  namespace: kube-system
spec:
  replicas: 1
  selector:
    k8s-app: heapster
    version: v6
  template:
    metadata:
      labels:
        k8s-app: heapster
        version: v6
    spec:
      nodeSelector:
         kubernetes.io/hostname: k8s-master
      containers:
      - name: heapster
        image: kubernetes/heapster:canary
        imagePullPolicy: IfNotPresent
        command:
        - /heapster
        - --source=kubernetes:http://192.168.4.11:8080?inClusterConfig=false
        - --sink=influxdb:http://monitoring-influxdb:8086

influxdb-grafana-controller.yaml 文件内容

apiVersion: v1
kind: ReplicationController
metadata:
  labels:
    name: influxGrafana
  name: influxdb-grafana
  namespace: kube-system
spec:
  replicas: 1
  selector:
    name: influxGrafana
  template:
    metadata:
      labels:
        name: influxGrafana
    spec:
      containers:
      - name: influxdb
        image: kubernetes/heapster_influxdb:v0.5
        imagePullPolicy: IfNotPresent
        volumeMounts:
        - mountPath: /data
          name: influxdb-storage
      - name: grafana
        imagePullPolicy: IfNotPresent
        image: kubernetes/heapster_grafana:v2.6.0
        env:
          - name: INFLUXDB_SERVICE_URL
            value: http://monitoring-influxdb:8086- name: GF_AUTH_BASIC_ENABLED
            value: "false"
          - name: GF_AUTH_ANONYMOUS_ENABLED
            value: "true"
          - name: GF_AUTH_ANONYMOUS_ORG_ROLE
            value: Admin
          - name: GF_SERVER_ROOT_URL
            value: /api/v1/proxy/namespaces/kube-system/services/monitoring-grafana/
        volumeMounts:
        - mountPath: /var
          name: grafana-storage
      nodeSelector:
         kubernetes.io/hostname: k8s-master
      volumes:
      - name: influxdb-storage
        emptyDir: {}
      - name: grafana-storage
        emptyDir: {}

 原理

heapster读取kubelet中cadvisor(http://192.168.4.12:4194/containers/)的数据,存到influxdb中,再由grafana读取出图,最后由dashboard呈现
监控数据获得,是从cadvisor获得的,现在cadvisor集成到了kubelete中,访问cadvisor,可以修改kubelet配置文件,添加--cadvisor参数

# cat /etc/kubernetes/kubelet 
KUBELET_ARGS="--cluster_dns=10.254.230.254 --cluster_domain=cluster.local --cadvisor-port=8080"
重启
systemctl restart kubelet.service 
原文地址:https://www.cnblogs.com/wuhg/p/12162583.html