k8s之Service资源

1.Service概述

  service是kubernetes中最核心的资源对象之一,service和pod之间是通过Label串起来,相同的Service的pod的Label是一样的.同一个service下的所有pod是通过kube-proxy实现负载均衡.而每个service都会分配一个全局唯一的虚拟ip,也就cluster ip.

在该service整个生命周期内,cluster ip保持不变,而在kubernetes中还有一个dns服务,它会把service的name解析为cluster ip.

service工作模式:userspace(1.1版本之前)、iptables(1.10版本之前)和ipvs(1.11版本之后)

类型:ExternalName(集群内部pod想要访问外部服务),ClusterIP,NodePort,

LoadBalancer:k8s如果部署在公有云上,且公有云支持LBAAS,k8s的CloudControllor会调用IAAS的api,创建service时会按需创建,删除时会按需删除,这种类型称为负载均衡器类型.

资源记录:SVC_NAME.NS_NAME.DOMAIN.LTD.

svc.cluster.local. 例如:redis.default.svc.cluster.local.

2.ClusterIP

vim redis-svc.yaml
apiVersion: v1
kind: Service
metadata:
  name: redis
  namespace: default
spec:
  selector:
    app: redis
    role: logstor
  clusterIP: 10.97.97.97 # 可以不指定,将会自动分配
  type: ClusterIP
  ports:
  - port: 6379
    targetPort: 6379

port:service的端口
targetPort:pod的端口
nodePort:宿主机的端口

3.NodePort

将物理机的端口映射到service的端口,外部可通过宿主机IP+port的方式访问

client->NodeIP:NodePort->ClusterIP:ServicePort->PodIP:targetPort

vim myapp-svc.yaml
apiVersion: v1
kind: Service
metadata:
  name: myapp
  namespace: default
spec:
  selector:
    app: myapp
    role: canary
  clusterIP: 10.99.99.99
  type: NodePort
  ports:
  - port: 80
    targetPort: 80
    nodePort: 30080 # 可以不指定,将会自动分配

kubectl apply -f myapp-svc.yaml
# 打补丁:session绑定,第一次访问的是哪台pod,之后访问时就会一直是这台pod
# 用sessionAffinity将同一个客户端会话请求粘滞到一个固定的pod上
# 这样就不会出现负载均衡现象,相当于nginx的ip_hash功能
kubectl patch svc myapp -p '{"spec":{"sessionAffinity":"ClientIP"}}'

# 也可以直接用edit方法编辑,再改回负载均衡模式
kubectl patch svc myapp -p '{"spec":{"sessionAffinity":"None"}}'

无头service--不指定ClusterIP:

无头service是指service name直接解析为后面的pod ip,无头就是没有cluster ip牵头

vim myapp-svc-headless.yaml
apiVersion: v1
kind: Service
metadata:
  name: myapp-svc
  namespace: default
spec:
  selector:
    app: myapp
    release: canary
  clusterIP: "None"
  ports:
  - port: 80
    targetPort: 80

kubectl apply -f myapp-svc-headless.yaml
kubectl get svc
NAME         TYPE        CLUSTER-IP   EXTERNAL-IP   PORT(S)   AGE
kubernetes   ClusterIP   10.96.0.1    <none>        443/TCP   13d
myapp-svc    ClusterIP   None         <none>        80/TCP    6s

# 直接解析为后端pod ip
dig -t A myapp-svc.default.svc.cluster.local. @10.96.0.10
myapp-svc.default.svc.cluster.local. 5 IN A	10.244.2.8
myapp-svc.default.svc.cluster.local. 5 IN A	10.244.1.10

kubectl get pods -o wide
NAME                            READY   STATUS    AGE     IP            NODE     
myapp-deploy-65df64765c-6vrjq   1/1     Running   9s      10.244.2.8    k8s-node2
myapp-deploy-65df64765c-88h9d   1/1     Running   9s      10.244.1.10   k8s-node1

  ExternalName类型的服务适用于外部服务使用域名的方式,缺点是不能指定端口,要实现集群内访问集群外服务的这个需求,也可以实现,因为集群内的Pod会继承Node上的DNS解析规则.因此只要Node可以访问的服务,Pod中也可以访问到.

参考博客:http://blog.itpub.net/28916011/viewspace-2214745/

原文地址:https://www.cnblogs.com/fawaikuangtu123/p/11030977.html