跳转至

通过 Ingress 访问K8S内部的应用


2020-03-10 by dongnan

开始之前

IngressKubernetes 的一种 API对象,将集群内部的 Service 通过 HTTP/HTTPS 方式暴露到集群外部,并通过规则定义 HTTP/HTTPS 的路由。

  • 集群外部可访问的 URL
  • 负载均衡
  • SSL Termination
  • 按域名(路径)进行路由

目标

部署 Ingress 控制器,并通过 monitor.io 访问 K8S集群内部的应用(Service/Pod)。

数据流大致是这样的:

Client -> SLB (L7 TCP:443) -> ECS ->  IngressController(SVC:TCP 32002:443) 
                                    -> IngressRule(Host: monitor.io) -> App(SVC:TCP 80:80)

环境描述

测试的k8s集群由一个Master管理节点、两个Worker计算节点组成。

主机: AliYun ecs.g6.large 2c/8G
OS: Ubuntu Server 18.04
Docker: docker-ce:18.09.9
Kubernetes: v1.17.x
网络: 使用相同的 VPC 与 安全组
角色: 
    master: 
        主机名: host0
        IP: 10.0.20.20
    worker: 
        主机名: host1
        IP: 10.0.20.21
        主机名: host2
        IP: 10.0.20.22

k8s 部署请参考这篇文章

操作步骤

需要使用到的文件

tree  k8s/ingress/
k8s/ingress/
├── controller
│   ├── ingress-svc.yaml
│   └── mandatory.yaml
└── default
    ├── ds.yaml
    ├── ing.yaml
    └── svc.yaml

2 directories, 5 files

部署 ingress 控制器

使用 kubectl 命令完成部署

kubectl apply -f k8s/ingress/controller/

将自动创建 NameSpaceServiceDeploymentPod 等资源:

# namespaces
kubectl get ns ingress-nginx 
NAME            STATUS   AGE
ingress-nginx   Active   101d

# service
kubectl -n ingress-nginx get svc
NAME            TYPE       CLUSTER-IP       EXTERNAL-IP   PORT(S)                      AGE
ingress-nginx   NodePort   172.19.xxx.223   <none>        80:32001/TCP,443:32002/TCP   101d

# deployment
kubectl -n ingress-nginx get deploy
NAME                       READY   UP-TO-DATE   AVAILABLE   AGE
nginx-ingress-controller   2/2     2            2           101d

# pod
kubectl -n ingress-nginx get pod
NAME                                        READY   STATUS    RESTARTS   AGE
nginx-ingress-controller-5b454769bd-8bqqk   1/1     Running   0          101d
nginx-ingress-controller-5b454769bd-ftp7j   1/1     Running   0          101d

需要注意的是,Service使用的是 NodePort方式,这将暴露ECS的端口给SLB负载均衡器使用。

创建 ingress 规则

当拥有 ingress 控制器后,就可以创建具体的 ingress 规则了,例如希望访问 monitor.io/check.html 时代理到后端的 nginx 服务。

首先看下 ingress 规则,在这个 yaml 文件定义了 hostpath

cat ing.yaml

apiVersion: networking.k8s.io/v1beta1
kind: Ingress
metadata:
  name: monitor.io
  annotations:
    nginx.ingress.kubernetes.io/enable-access-log: "false"  # 关闭日志
spec:
  rules:
  - host: monitor.io
    http:
      paths:
      - path: /check.html
        backend:
          serviceName: default-svc      # 注意
          servicePort: 80

创建 Ingress

kubectl apply -f k8s/ingress/default/ing.yaml

查看 Ingress

kubectl get ingresses.
NAME         HOSTS        ADDRESS          PORTS   AGE
monitor.io   monitor.io   172.19.xxx.223   80      101d

但是只有 ingress 规则只是第一步,还需要 ServicePod 资源才能提供完整的服务,可以看到在规则中指定了 Servicedefault-svc

创建 Service

Service 在这个 yaml 文件中则定义了 协议、端口和集群类型等,并指定后端Pod必须带有 app: default-nginx 这个标签。

cat svc.yaml 

apiVersion: v1
kind: Service
metadata:
  name: default-svc
  labels:
    app: default-svc
spec:
  selector:
    app: default-nginx     # 注意
  ports:
  - name: default-svc-port
    protocol: TCP
    port: 80
    targetPort: 80
  type: ClusterIP # ClusterIP/NodePort/LoaderBalancer
# sessionAffinity: ClientIP

创建 Service

kubectl apply -f k8s/ingress/default/svc.yaml

查看 Service

kubectl get svc default-svc 
NAME          TYPE        CLUSTER-IP       EXTERNAL-IP   PORT(S)   AGE
default-svc   ClusterIP   172.19.xxx.151   <none>        80/TCP    101d

创建 Pod

这里的 Pod是使用 DaemonSet 进行管理维护,与 Deployment 不同的是 DaemonSet 将在K8s集群每个Worker节点都会上运行此Pod

在这个 yaml 文件定义了标签 app: default-nginx ,也就与 Service selector 所对应的标签。

cat default/ds.yaml 

apiVersion: apps/v1
kind: DaemonSet
metadata:
  name: default-nginx
  labels:
    app: default-nginx
spec:
  selector:
    matchLabels:
      app: default-nginx
  template:
    metadata:
      labels:
        app: default-nginx      # 注意
    spec:
      containers:
      - name: nginx
        image: hub.xyc.com/library/nginx-health:0.0.3

创建 Pod

kubectl apply -f k8s/ingress/default/ds.yaml

查看 Pod

kubectl get pod
NAME                  READY   STATUS    RESTARTS   AGE
default-nginx-k8p2q   1/1     Running   2          101d
default-nginx-kmhkc   1/1     Running   1          101d

验证

K8s集群外部通过浏览器访问返回ok 表示 ingress 可以正常使用。

# 这里使用 curl 模拟浏览器访问
curl -H "Host:monitor.io" -k https://Your-Server-IP/check.html
ok

小结

  • Ingress 控制器是非常重要的,可以将它理解为一个智能的Nginx代理服务器。
  • Ingress 规则 与 ServicePod 共同描述了这个Web应用集群的细节。

参考

回到页面顶部