第190集:Service 与 Ingress

核心知识点讲解

1. Service基础

基本概念

Service是Kubernetes中用于暴露应用的抽象,它定义了一组Pod的访问策略,并为这些Pod提供稳定的IP地址和DNS名称。Service确保即使Pod发生变化,服务的访问方式保持不变。

Service的类型

  • ClusterIP:默认类型,仅在集群内部可访问
  • NodePort:在每个节点上开放一个端口,可从集群外部访问
  • LoadBalancer:使用云提供商的负载均衡器,外部可访问
  • ExternalName:将服务映射到外部DNS名称

Service的创建

# service.yaml
apiVersion: v1
kind: Service
metadata:
  name: my-service
spec:
  selector:
    app: my-app
  ports:
  - port: 80
    targetPort: 8080
    protocol: TCP
  type: ClusterIP
# 创建Service
kubectl apply -f service.yaml

# 查看Service
kubectl get services

# 查看Service详情
kubectl describe service my-service

# 删除Service
kubectl delete service my-service

2. Service配置详解

基本配置

  • selector:选择器,用于匹配Pod
  • ports:端口配置
  • type:Service类型
  • clusterIP:指定集群IP(可选)
  • sessionAffinity:会话亲和性
  • externalIPs:外部IP地址

端口配置

ports:
- name: http
  port: 80        # Service端口
  targetPort: 8080  # Pod端口
  protocol: TCP
- name: https
  port: 443
  targetPort: 8443
  protocol: TCP

会话亲和性

sessionAffinity: ClientIP

3. 服务发现

DNS服务发现

Kubernetes集群内部运行着DNS服务,为Service和Pod提供域名解析:

  • Service DNSservice-name.namespace.svc.cluster.local
  • Pod DNSpod-ip-address.namespace.pod.cluster.local

环境变量服务发现

当Pod启动时,Kubernetes会自动注入集群中其他Service的环境变量:

  • {SERVICE_NAME}_SERVICE_HOST
  • {SERVICE_NAME}_SERVICE_PORT

4. Ingress基础

基本概念

Ingress是Kubernetes中用于管理外部访问集群服务的API对象,它提供了HTTP和HTTPS路由、TLS终止、负载均衡等功能。Ingress需要Ingress控制器才能工作。

常见的Ingress控制器

  • NGINX Ingress Controller:最常用的Ingress控制器
  • Traefik:现代化的Ingress控制器,支持自动配置
  • HAProxy Ingress:基于HAProxy的Ingress控制器
  • AWS ALB Ingress Controller:AWS专用的Ingress控制器

Ingress的创建

# ingress.yaml
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: my-ingress
  annotations:
    nginx.ingress.kubernetes.io/rewrite-target: /
spec:
  rules:
  - host: example.com
    http:
      paths:
      - path: /app
        pathType: Prefix
        backend:
          service:
            name: my-service
            port:
              number: 80
# 创建Ingress
kubectl apply -f ingress.yaml

# 查看Ingress
kubectl get ingresses

# 查看Ingress详情
kubectl describe ingress my-ingress

# 删除Ingress
kubectl delete ingress my-ingress

5. Ingress配置详解

路由规则

rules:
- host: example.com
  http:
    paths:
    - path: /api
      pathType: Prefix
      backend:
        service:
          name: api-service
          port:
            number: 80
    - path: /web
      pathType: Prefix
      backend:
        service:
          name: web-service
          port:
            number: 80

TLS配置

tls:
- hosts:
  - example.com
  secretName: tls-secret

路径类型

  • Exact:精确匹配路径
  • Prefix:前缀匹配路径
  • ImplementationSpecific:由Ingress控制器决定

6. 高级配置

Ingress TLS

# 创建TLS密钥
openssl req -x509 -nodes -days 365 -newkey rsa:2048 \
  -keyout tls.key -out tls.crt \
  -subj "/CN=example.com"

# 创建Secret
kubectl create secret tls tls-secret \
  --key tls.key \
  --cert tls.crt

# 在Ingress中使用
# ...

负载均衡配置

metadata:
  annotations:
    kubernetes.io/ingress.class: "nginx"
    nginx.ingress.kubernetes.io/ssl-redirect: "true"
    nginx.ingress.kubernetes.io/affinity: "cookie"
    nginx.ingress.kubernetes.io/session-cookie-name: "route"
    nginx.ingress.kubernetes.io/session-cookie-expires: "172800"
    nginx.ingress.kubernetes.io/session-cookie-max-age: "172800"

自定义Ingress控制器

对于复杂的场景,可以自定义Ingress控制器的配置:

  • ConfigMap:配置Ingress控制器的全局设置
  • Annotations:配置单个Ingress的特定设置

7. 最佳实践

Service设计

  • 使用标签选择器:为Service使用有意义的标签选择器
  • 合理设置端口:使用标准端口,便于理解和维护
  • 选择合适的Service类型:根据访问需求选择合适的类型
  • 使用命名端口:为端口指定名称,提高可读性

Ingress设计

  • 使用IngressClass:为不同的Ingress配置不同的控制器
  • 合理组织路由:将相关的路由规则组织在一起
  • 配置TLS:为生产环境配置TLS
  • 使用健康检查:确保流量只发送到健康的后端
  • 监控Ingress:监控Ingress的性能和错误率

实用案例分析

案例1:暴露多服务应用

场景描述:部署一个包含前端和后端服务的应用,需要从外部访问。

解决方案

# frontend-deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
  name: frontend
spec:
  replicas: 2
  selector:
    matchLabels:
      app: frontend
  template:
    metadata:
      labels:
        app: frontend
    spec:
      containers:
      - name: frontend
        image: frontend:latest
        ports:
        - containerPort: 80

---
# backend-deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
  name: backend
spec:
  replicas: 3
  selector:
    matchLabels:
      app: backend
  template:
    metadata:
      labels:
        app: backend
    spec:
      containers:
      - name: backend
        image: backend:latest
        ports:
        - containerPort: 8080

---
# frontend-service.yaml
apiVersion: v1
kind: Service
metadata:
  name: frontend-service
spec:
  selector:
    app: frontend
  ports:
  - port: 80
    targetPort: 80

---
# backend-service.yaml
apiVersion: v1
kind: Service
metadata:
  name: backend-service
spec:
  selector:
    app: backend
  ports:
  - port: 8080
    targetPort: 8080

---
# ingress.yaml
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: app-ingress
  annotations:
    nginx.ingress.kubernetes.io/rewrite-target: /
spec:
  rules:
  - host: app.example.com
    http:
      paths:
      - path: /
        pathType: Prefix
        backend:
          service:
            name: frontend-service
            port:
              number: 80
      - path: /api
        pathType: Prefix
        backend:
          service:
            name: backend-service
            port:
              number: 8080

实施效果

  • 前端和后端服务分别部署,通过Service暴露
  • Ingress提供统一的访问入口
  • 外部用户可以通过app.example.com访问应用
  • 流量根据路径自动路由到前端或后端服务

案例2:配置HTTPS服务

场景描述:为应用配置HTTPS,确保通信安全。

解决方案

# tls-secret.yaml
apiVersion: v1
kind: Secret
metadata:
  name: app-tls
type: kubernetes.io/tls
data:
  tls.crt: <base64-encoded-cert>
  tls.key: <base64-encoded-key>

---
# ingress-tls.yaml
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: app-ingress-tls
  annotations:
    kubernetes.io/ingress.class: "nginx"
    nginx.ingress.kubernetes.io/ssl-redirect: "true"
spec:
  tls:
  - hosts:
    - secure.example.com
    secretName: app-tls
  rules:
  - host: secure.example.com
    http:
      paths:
      - path: /
        pathType: Prefix
        backend:
          service:
            name: web-service
            port:
              number: 80

实施效果

  • 应用通过HTTPS暴露
  • 自动将HTTP请求重定向到HTTPS
  • 客户端与Ingress之间的通信加密
  • 提供安全的应用访问方式

课后练习

  1. 创建一个ClusterIP类型的Service
  2. 创建一个NodePort类型的Service并从外部访问
  3. 为Service配置会话亲和性
  4. 创建一个包含多个路径的Ingress
  5. 为Ingress配置TLS
  6. 测试服务发现功能
  7. 配置Ingress的负载均衡策略
  8. 监控Service和Ingress的性能

总结

Service和Ingress是Kubernetes中用于暴露和管理应用访问的核心组件。Service为应用提供稳定的内部访问方式,而Ingress则提供了更高级的外部访问管理功能。通过本集的学习,我们了解了Service和Ingress的基本概念、配置方法和最佳实践。在实际应用中,我们应该根据具体的访问需求选择合适的Service类型,并利用Ingress提供的高级功能来管理外部流量。掌握这些技能对于构建可靠、安全、可访问的Kubernetes应用至关重要。

« 上一篇 Pod 与 Deployment 下一篇 » Service 与 Ingress