Kubernetes(k8s)容器编排Service

本文涉及的产品
云数据库 RDS MySQL Serverless,0.5-2RCU 50GB
云数据库 RDS MySQL Serverless,价值2615元额度,1个月
简介: Kubernetes(k8s)容器编排Service

1 Service概述

Kubernetes service 定义了这样一种抽象:一个 Pod 的逻辑分组,一种可以访问它们的策略 —— 通常称为微服务,这一组 pod 能够被 Service 访问到,通常是通过 Label selector

Service能够提供负载均衡的能力,但是在使用上有以下限制:

  • 只提供4层负载均衡能力,而没有7层功能,但有时我们可能需要更多的匹配规则来转发请求,这点上4层负载均衡是不支持的

Kubernetes Service 从逻辑上代理了一组 Pod,具体是哪些 Pod 则是由 label 来挑选,Service 有自己 IP,而且这个 IP 是不变的。

  • 客户端只需要访问 Service 的 IP,Kubernetes 则负责建立和维护 Service 与 Pod 的映射关系。
  • 无论后端 Pod 如何变化,对客户端不会有任何影响,因为 Service 没有变

1.1 为什么要有Service

当Pod宕机后重新生成时,其IP等状态信息可能会变动,Service会根据Pod的Label对这些状态信息进行监控和变更,保证上游服务不受Pod的变动而影响。

Kubernetes Pods 是有生命周期的,他们可以被创建,而且销毁不会再启动, 如果您使用Deployment来运行您的应用程序,则它可以动态创建和销毁 Pod。


一个Kubernetes的Service是一种抽象,它定义了一组Pods的逻辑集合和一个用于访问它们的策略 - 有的时候被称之为微服务,一个Service的目标Pod集合通常是由Label Selector 来决定的。


如下图所示,当Nginx Pod作为客户端访问Tomcat Pod中的应用时,IP的变动或应用规模的缩减会导致客户端访问错误。而Pod规模的扩容又会使得客户端无法有效的使用新增的Pod对象,从而影响达成规模扩展之目的。为此,Kubernetes特地设计了Service资源来解决此类问题。

cee5a89ca80f49e894d70e343bb55c43.png

1.2 Service实现原理

Service资源基于标签选择器将一组Pod定义成一个逻辑组合,并通过自己的IP地址和端口调度代理请求至组内的Pod对象之上,如下图所示,它向客户端隐藏了真实的、处理用户请求的Pod资源,使得客户端的请求看上去就像是由Service直接处理并响应一样。

Service对象的IP地址也称为Cluster IP,它位于Kubernetes集群配置指定专用IP地址的范围之内,是一种虚拟IP地址,它在Service对象创建后既保持不变,并且能够被同一集群中的Pod资源所访问。Service端口用于接收客户端请求并将其转发至其后端的Pod中的相应端口之上,因此,这种代理机构也称为“端口代理”(port proxy)或四层代理,工作于TCP/IP协议栈的传输层。


Service资源会通过API Server持续监视着(watch)标签选择器匹配到的后端Pod对象,并实时跟踪各对象的变动,例如,IP地址变动、对象增加或减少等。Service并不直接链接至Pod对象,它们之间还有一个中间层——Endpoints资源对象,它是一个由IP地址和端口组成的列表,这些IP地址和端口则来自由Service的标签选择器匹配到的Pod资源。当创建service对象时,其关联的Endpoints对象会自动创建。

2 Service 的类型

Service 在 K8s 中有以下四种类型

  • Clusterlp:默认类型,自动分配一个仅 Cluster 内部可以访问的虚拟 IP

NodePort:在 ClusterIP 基础上为 Service 在每台机器上绑定一个端口,这样就可以通过:NodePort 来访问该服务

LoadBalancer:在 NodePort 的基础上,借助 cloud provider 创建一个外部负载均衡器,并将请求转发到:NodePort

  • ExternalName:把集群外部的服务引入到集群内部来,在集群内部直接使用。没有任何类型代理被创建,这只有kubernetes 1.7或更高版本的 kube-dns 才支持

3 Service示例

3.1 准备工作

3.1.1 创建deployment

vi nginx-deployment.yml
apiVersion: apps/v1
kind: Deployment
metadata:
  name: nginx-deployment
spec:
  replicas: 1 # 只有一个副本
  selector:
    matchLabels:
        app: nginx
  template:
    metadata:
      labels:
        app: nginx
    spec:
      volumes:    #定义存储卷
      - name: html # 定义存储名称
        hostPath:  # 定义存储类型
          path: /tmp/k8s/data/volumn1 # 宿主机存储路径
          type: DirectoryOrCreate     # 不存在路径创建路径
      containers:
      - name: nginx
        image: nginx:1.20
        volumeMounts:    #在容器中定义挂载存储卷的名和路径
        - name: html
          mountPath: /usr/share/nginx/html
        ports:
        - containerPort: 80

3.1.2 启动deployment

kubectl apply -f nginx-deployment.yml
kubectl get pods -o wide

3.1.3 访问测试

curl 10.244.2.54

3.2 ClusterlP类型

类型为ClusterIP的service,这个service有一个Cluster-IP,其实就一个VIP,具体实现原理依靠kubeproxy组件,通过iptables或是ipvs实现。

注意:这种类型的service 只能在集群内访问

3.2.1 编辑资源清单

vi cluster-iP-service.yml
apiVersion: v1
kind: Service
metadata:
  name: nginx-service
  namespace: default
  labels:
    app: nginx-service
spec:
  type: ClusterIP
  ports:
  - port: 8000      # Service 暴漏端口
    targetPort: 80  # 代理的对象的端口
  selector:
    app: nginx # 绑定标签是nginx的对象

3.2.2 应用Service

kubectl apply -f cluster-iP-service.yml
kubectl get service -o wide

3.2.3 访问测试

curl 10.1.206.66:8000

3.2.4 删除Pod

删除pod让Pod的节点漂移再次访问Service节点

kubectl delete pod nginx-deployment-6897679c4b-2hqmk

3.2.5 访问测试

我们发现虽然pod的IP以及节点变化了但是Service访问IP没有任何变化

curl 10.1.206.66:8000

3.3 NodePort

当我们需要集群外业务访问,那么ClusterIP就满足不了了,NodePort当然是其中的一种实现方案

3.3.1 编辑资源清单

vi node-port-service.yml
apiVersion: v1
kind: Service
metadata:
  name: nginx-node-port-service
  namespace: default
  labels:
    app: nginx-service
spec:
  type: NodePort
  ports:
  - port: 8000      # Service 暴漏端口
    targetPort: 80  # 代理的对象的端口
  selector:
    app: nginx # 绑定标签是nginx的对象

3.3.2 应用Service

kubectl apply -f node-port-service.yml
kubectl get service -o wide

3.3.3 访问测试

curl 10.1.137.200:8000

3.3.4 删除Pod

删除pod让Pod的节点漂移再次访问Service节点

kubectl delete pod nginx-deployment-6897679c4b-2hqmk

3.3.5 访问测试

我们发现虽然pod的IP以及节点变化了但是Service访问IP没有任何变化

curl 10.1.137.200:8000

3.3.6 外网访问

NodePort的最主要功能是进行外网访问,我们是不能通过访问8000端口访问的,他是内网端口,外网访问需要访问映射出来的端口8000:31337/TCP这里映射出来的nodeport31337,还可以通过指定nodePort来指定端口,要求端口必须大于30000

curl 192.168.64.160:31337

通过浏览器访问

4 端口号区分

k8s 中 portnodePorttargetPort有什么区别呢

4.1 应用位置不同

  • port:是service的的端口
  • targetport:是pod也就是容器的端口
  • nodeport:是容器所在宿主机的端口(实质上也是通过service暴露给了宿主机,而port却没有)

4.1 port

k8s集群内部服务之间访问service的入口,即clusterIP:port是service暴露在clusterIP上的端口

主要作用是集群内其他pod访问本pod的时候,需要的一个port,如nginx的pod访问mysql的pod,那么mysql的pod的service可以如下定义,由此可以这样理解,port是service的port,nginx访问service的33306

apiVersion: v1
 kind: Service
 metadata:
  name: mysql-service
 spec:
  ports:
  - port: 33306
    targetPort: 3306
  selector:
   name: mysql-pod

4.2 targetport

容器的端口(最终的流量端口)。targetPort是pod上的端口,从port和nodePort上来的流量,经过kube-proxy流入到后端pod的targetPort上,最后进入容器。

看上面的targetport,targetport说过是pod暴露出来的port端口,当nginx的一个请求到达service的33306端口时,service就会将此请求根据selector中的name,将请求转发到mysql-pod这个pod的3306端口上


4.3 nodeport

nodeport就很好理解了,它是集群外的客户访问,集群内的服务时,所访问的port,比如客户访问下面的集群中的nginx,就是这样的方式,ip:30001


外部流量访问k8s集群中service入口的一种方式(另一种方式是LoadBalancer),即nodeIP:nodePort是提供给外部流量访问k8s集群中service的入口


比如外部用户要访问k8s集群中的一个Web应用,那么我们可以配置对应service的type=NodePort,nodePort=30001。其他用户就可以通过浏览器http://node:30001访问到该web服务。而数据库等服务可能不需要被外界访问,只需被内部服务访问即可,那么我们就不必设置service的NodePort。

apiVersion: v1 
kind: Service 
metadata: 
    name: nginx-service 
spec: 
    type: NodePort # 有配置NodePort,外部流量可访问k8s中的服务 
    ports: 
    - port: 30080 # 服务访问端口 
      targetPort: 80 # 容器端口 
      nodePort: 30001 # NodePort 
    selector: name: nginx-pod 

4.4 小结

nodeport是集群外流量访问集群内服务的端口类型,比如客户访问nginx,apache,port是集群内的pod互相通信用的端口类型,比如nginx访问mysql,而mysql是不需要让客户访问到的,最后targetport,顾名思义,目标端口,也就是最终端口,也就是pod的端口。

相关实践学习
容器服务Serverless版ACK Serverless 快速入门:在线魔方应用部署和监控
通过本实验,您将了解到容器服务Serverless版ACK Serverless 的基本产品能力,即可以实现快速部署一个在线魔方应用,并借助阿里云容器服务成熟的产品生态,实现在线应用的企业级监控,提升应用稳定性。
云原生实践公开课
课程大纲 开篇:如何学习并实践云原生技术 基础篇: 5 步上手 Kubernetes 进阶篇:生产环境下的 K8s 实践 相关的阿里云产品:容器服务 ACK 容器服务 Kubernetes 版(简称 ACK)提供高性能可伸缩的容器应用管理能力,支持企业级容器化应用的全生命周期管理。整合阿里云虚拟化、存储、网络和安全能力,打造云端最佳容器化应用运行环境。 了解产品详情: https://www.aliyun.com/product/kubernetes
目录
相关文章
|
6天前
|
存储 运维 Kubernetes
Docker+Kubernetes/K8s+Jenkins视频资料【干货分享】
Docker+Kubernetes/K8s+Jenkins视频资料【干货分享】
Docker+Kubernetes/K8s+Jenkins视频资料【干货分享】
|
4天前
|
存储 Kubernetes C++
【专栏】Kubernetes VS Docker Swarm:哪个容器编排工具更适合你?
【4月更文挑战第27天】对比Kubernetes和Docker Swarm:K8s在可扩展性和自动化方面出色,有强大社区支持;Swarm以简易用著称,适合初学者。选择取决于项目需求、团队技能和预期收益。高度复杂项目推荐Kubernetes,快速上手小项目则选Docker Swarm。了解两者特点,助力选取合适容器编排工具。
|
1天前
|
Kubernetes API 调度
|
6天前
|
运维 Kubernetes Linux
10分钟搭建Kubernetes容器集群平台(kubeadm)
10分钟搭建Kubernetes容器集群平台(kubeadm)
|
6天前
|
存储 Kubernetes Docker
Kubernetes(K8S)集群管理Docker容器(概念篇)
Kubernetes(K8S)集群管理Docker容器(概念篇)
|
7天前
|
Kubernetes Ubuntu Docker
Kubernetes(K8S v1.1版本) 集群管理Docker容器之部署篇
Kubernetes(K8S v1.1版本) 集群管理Docker容器之部署篇
|
16天前
|
存储 运维 Kubernetes
构建高效稳定的容器化运维环境:Docker与Kubernetes的协同
【4月更文挑战第14天】 在当今快速发展的云计算时代,容器技术以其轻量级、快速部署和易于管理的优势,成为现代应用交付的标准。本文将深入探讨如何通过Docker和Kubernetes的整合使用来构建一个高效且稳定的容器化运维环境。我们将分析Docker容器的基本概念,探索Kubernetes在容器编排方面的强大能力,以及两者结合所带来的益处。文章还将讨论在实际部署中可能遇到的挑战,并提出相应的解决方案。
|
18天前
|
JSON Kubernetes Go
无缝集成:在IntelliJ IDEA中利用Kubernetes插件轻松管理容器化应用
无缝集成:在IntelliJ IDEA中利用Kubernetes插件轻松管理容器化应用
28 0
无缝集成:在IntelliJ IDEA中利用Kubernetes插件轻松管理容器化应用
|
18天前
|
Kubernetes 应用服务中间件 nginx
Kubernetes容器探针
Kubernetes容器探针
30 0
|
4天前
|
存储 监控 安全
【专栏】Docker Compose:轻松实现容器编排的利器
【4月更文挑战第27天】Docker Compose是款轻量级容器编排工具,通过YAML文件统一管理多容器应用。本文分三部分深入讨论其核心概念(服务、网络、卷和配置)、使用方法及最佳实践。从快速入门到高级特性,包括环境隔离、CI/CD集成、资源管理和安全措施。通过案例分析展示如何构建多服务应用,助力高效容器编排与管理。

推荐镜像

更多