0
点赞
收藏
分享

微信扫一扫

(八)Kubernetes Ingress资源

前言


​Kubernetes​​​提供了两种内建的云端负载均衡机制(​​cloud load balancing​​​)用于发布公共应用,一种是工作于传输层的​​Service​​​资源,它实现的是​​“TCP负载均衡器”​​​,另一种是​​Ingress​​​资源,它实现的是​​“HTTP(S)负载均衡器”​​。

  • TCP负载均衡器
  • 无论是​​iptables​​还是​​ipvs​​模型的​​Service​​资源都配置于​​Linux​​内核中的​​Netfilter​​之上进行四层调度,是一种类型更为通用的调度器,支持调度​​HTTP​​、​​MySQL​​等应用层服务。不过,也正是由于工作于传输层从而使得它无法做到类似卸载​​HTTPS​​中的​​SSL​​会话等一类操作,也不支持基于​​URL​​的请求调度机制,而且,​​Kubernetes​​也不支持为此类负载均衡器配置任何类型的健康状态检查机制。

  • HTTP(S)负载均衡器
  • ​HTTP(S)​​负载均衡器是应用层负载均衡机制的一种,支持根据环境做出更好的调度决策。与传输层调度器相比,它提供了诸如可自定义​​URL​​映射和​​TLS​​卸载等功能,并支持多种类型的后端服务器健康状态检查机制。


Ingress概述

什么是Ingress?


通常情况下,​​service​​​和​​pod​​​仅可在集群内部网络中通过​​IP​​地址访问。所有到达边界路由器的流量或被丢弃或被转发到其他地方。从概念上讲,可能像下面这样:

internet
|
------------
[ Services ]



Ingress是授权入站连接到达集群服务的规则集合。

internet
|
[ Ingress ]
--|-----|--
[ Services ]



你可以给​​Ingress​​​配置提供外部可访问的​​URL​​​、负载均衡、​​SSL​​​、基于名称的虚拟主机等。用户通过​​POST Ingress​​​资源到​​API Server​​​的方式来请求​​Ingress​​​。​​Ingress controller​​​负责实现​​Ingress​​​,通常使用负载平衡器,它还可以配置边界路由和其他前端,这有助于以​​HA​​方式处理流量。


Ingress和Ingress Controller


​Ingress​​​是​​Kubernetes API​​​的标准资源类型之一,它其实就是一组基于​​DNS​​​名称(​​host​​​)或​​URL​​​路径把请求转发至指定的​​Service​​​资源的规则,用于将集群外部的请求流量转发至集群内部完成服务发布。然而,​​Ingress​​​资源自身并不能进行“流量穿透”,它仅是一组路由规则的集合,这些规则要想真正发挥作用还需要其他功能的辅助,如监听某套接字,然后根据这些规则的匹配机制路由请求流量。这种能够为​​Ingress​​​资源监听套接字并转发流量的组件称为​​Ingress​​​控制器(​​Ingress Controller​​)。



​Ingress​​​控制器并不直接运行为​​kube-controller-manager​​​的一部分,它是​​Kubernetes​​​集群的一个重要组件,类似​​CoreDNS​​,需要在集群上单独部署。


Ingress工作流程

如下图所示,流量到达外部负载均衡器(​​externalLB​​​)后,首先转发至​​Service​​​资源​​Ingres-nginx​​​上,然后通过​​Ingress​​​控制器基于​​Ingress​​​资源定义的规则将客户端请求流量直接转发至与​​Service​​​对应的后端​​Pod​​​资源之上。这种转发机制会绕过​​Service​​​资源(​​app Service​​​;​​api Service​​​),从而省去了由​​kube-proxy​​​实现的端口代理开销。​​Ingress​​​规则需要由一个​​Service​​​资源对象辅助识别相关的所有​​Pod​​​资源。如下​​Ingress​​​通过​​app service​​​资源去匹配后端的​​pod1​​​和​​pod2​​​;这个​​app service​​只是起到一个辅助识别功能。

(八)Kubernetes Ingress资源_nginx

先决条件


在使用​​Ingress resource​​​之前,必须先了解下面几件事情。​​Ingress​​​是​​beta​​​版本的​​resource​​​,在​​kubernetes1.1​​​之前还没有。你需要一个​​Ingress Controller​​​来实现​​Ingress​​​,单纯的创建一个​​Ingress​​没有任何意义。

​GCE/GKE​​​会在​​master​​​节点上部署一个​​Ingress Controller​​​。你可以在一个​​Pod​​​中部署任意个自定义的​​Ingress Controller​​​。你必须正确的​​annotate​​​每个​​Ingress​​​,比如运行多个​​Ingress Controller​​​和关闭​​glbc​​。


Ingress清单文件几个字段说明


​Ingress​​​资源是基于​​HTTP​​​虚拟主机或​​URL​​​的转发规则,​​spec​​​字段中嵌套了​​rules​​​、​​backend​​​、​​tls​​​等字段进行定义。下面这个示例中,它包含了一个转发规则,把发往​​www.ilinux.io​​​的请求代理给名为​​myapp-svc​​​的​​Service​​资源。


apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: ingress-demo
namespace: default
annotations:
kubernetes.io/ingress.class: "nginx"
spec:
rules:
- host: www.ilinux.io
http:
paths:
- backend:
serviceName: myapp-svc
servicePort: 80

#说明:上面资源清单文件中的annotations用于识别其所属的Ingress控制器的类别,这一点在集群上部署多个Ingress控制器时尤为重要。


​Ingress Spec​​​(​​# kubectl explain ingress.spec​​​)中的字段是定义​​Ingress​​资源的核心组成部分,主要嵌套如下三个字段:

  • rules <[]Object>:用于定义当前​​Ingress​​资源的转发规则列表;未由​​rules​​定义规则,或者没有匹配到任何规则时,所有流量都会转发到由​​backend​​定义的默认后端。
  • backend <Object>:默认的后端用于服务那些没有匹配到任何规则的请求;定义​​Ingress​​资源时,至少应该定义​​backend​​或​​rules​​两者之一;此字段用于让负载均衡器指定一个全局默认的后端。
  • tls <[]Object>:​TLS​​配置,目前仅支持通过默认端口​​443​​提供服务;如果要配置指定的列表成员指向了不同的主机,则必须通过​​SNI TLS​​扩展机制来支持此功能。

​ingress.spec.rules.http.paths.backend​​​对象的定义由两个必须的内嵌字段组成:​​serviceName​​​和​​servicePort​​​,分别用于指定流量转发的后端目标​​Service​​资源的名称和端口。


部署Ingress Controller(Nginx)

描述


​Ingress​​​ 控制器自身是运行于​​Pod​​​中的容器应用,一般是​​Nginx​​​或​​Envoy​​​一类的具有代理及负载均衡功能的守护进程,它监视着来自​​API Server​​​的​​Ingress​​对象状态,并根据规则生成相应的应用程序专有格式的配置文件并通过重载或重启守护进程而使新配置生效。

​Ingress​​​控制器其实就是托管于​​Kubernetes​​​系统之上的用于实现在应用层发布服务的​​Pod​​​资源,跟踪​​Ingress​​资源并实时生成配置规则。


运行为​​Pod​​​资源的​​Ingress​​控制器进程通过下面两种方式接入外部请求流量:

1、以​​Deployment​​​控制器管理​​Ingress​​​控制器的​​Pod​​​资源,通过​​NodePort​​​或​​LoadBalancer​​​类型的​​Service​​​对象为其接入集群外部的请求流量,这就意味着,定义一个​​Ingress​​​控制器时,必须在其前端定义一个专用的​​Service​​资源。

(八)Kubernetes Ingress资源_nginx_02

2、借助于​​DaemonSet​​​控制器,将​​Ingress​​​控制器的​​Pod​​​资源各自以单一实例的方式运行于集群的所有或部分工作节点之上,并配置这类​​Pod​​​对象以​​HostPort​​​(如下图中的a)或​​HostNetwork​​(如下图中的b)的方式在当前节点接入外部流量。

(八)Kubernetes Ingress资源_tomcat_03

部署

​​Ingress-nginx官网​​

​​Ingress-nginx GitHub仓库地址​​

​​Ingress安装文档​​

1)在​​github​​​上下载配置清单​​yaml​​文件,并创建部署

[root@k8s-master ~]# mkdir ingress-nginx   #这里创建一个目录专门用于ingress-nginx(可省略)
[root@k8s-master ~]# cd ingress-nginx/
[root@k8s-master ingress-nginx]# wget https://raw.githubusercontent.com/kubernetes/ingress-nginx/master/deploy/static/mandatory.yaml #下载配置清单yaml文件
[root@k8s-master ingress-nginx]# ls #查看下载的文件
mandatory.yaml

[root@k8s-master ingress-nginx]# kubectl apply -f mandatory.yaml #创建Ingress
namespace/ingress-nginx created
configmap/nginx-configuration created
configmap/tcp-services created
configmap/udp-services created
serviceaccount/nginx-ingress-serviceaccount created
clusterrole.rbac.authorization.k8s.io/nginx-ingress-clusterrole created
role.rbac.authorization.k8s.io/nginx-ingress-role created
rolebinding.rbac.authorization.k8s.io/nginx-ingress-role-nisa-binding created
clusterrolebinding.rbac.authorization.k8s.io/nginx-ingress-clusterrole-nisa-binding created
deployment.apps/nginx-ingress-controller created

2)验证

[root@k8s-master ingress-nginx]# kubectl get pods -n ingress-nginx    #查看生成的pod,注意这里在ingress-nginx名称空间
NAME READY STATUS RESTARTS AGE
nginx-ingress-controller-79f6884cf6-5fb6v 1/1 Running 0 18m
[root@k8s-master ingress-nginx]# kubectl describe pod nginx-ingress-controller-79f6884cf6-5fb6v -n ingress-nginx 查看该pod的详细信息
Name: nginx-ingress-controller-79f6884cf6-5fb6v
Namespace: ingress-nginx
Priority: 0
Node: k8s-node2/192.168.1.33
Start Time: Fri, 27 Sep 2019 17:53:07 +0800
Labels: app.kubernetes.io/name=ingress-nginx
app.kubernetes.io/part-of=ingress-nginx
pod-template-hash=79f6884cf6
Annotations: prometheus.io/port: 10254
prometheus.io/scrape: true
Status: Running
IP: 10.244.2.73
......

3)如果是裸机部署,还需要安装​​service​​​。(比如​​VMware​​虚拟机、硬件服务器等)

---同样去官网下载配置清单文件,也可以自定义创建。
[root@k8s-master ingress-nginx]# wget https://raw.githubusercontent.com/kubernetes/ingress-nginx/master/deploy/static/provider/baremetal/service-nodeport.yaml
[root@k8s-master ingress-nginx]# kubectl apply -f service-nodeport.yaml #创建service资源
service/ingress-nginx created
[root@k8s-master ingress-nginx]# kubectl get svc -n ingress-nginx #查看service资源
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
ingress-nginx NodePort 10.107.40.182 <none> 80:32699/TCP,443:30842/TCP 9s
[root@k8s-master ingress-nginx]# kubectl describe svc/ingress-nginx -n ingress-nginx #查看该service的详细信息
Name: ingress-nginx
Namespace: ingress-nginx
Labels: app.kubernetes.io/name=ingress-nginx
app.kubernetes.io/part-of=ingress-nginx
Annotations: kubectl.kubernetes.io/last-applied-configuration:
{"apiVersion":"v1","kind":"Service","metadata":{"annotations":{},"labels":{"app.kubernetes.io/name":"ingress-nginx","app.kubernetes.io/par...
Selector: app.kubernetes.io/name=ingress-nginx,app.kubernetes.io/part-of=ingress-nginx
Type: NodePort
IP: 10.107.40.182
Port: http 80/TCP
TargetPort: 80/TCP
NodePort: http 32699/TCP
Endpoints: 10.244.2.73:80
Port: https 443/TCP
TargetPort: 443/TCP
NodePort: https 30842/TCP
Endpoints: 10.244.2.73:443
Session Affinity: None
External Traffic Policy: Cluster
Events: <none>

通过上面创建的​​service​​​资源对象可以看出,随机分配的​​http​​​的​​NodePort​​​为​​32668​​​,​​https​​​的​​NodePort​​​的为​​30606​​​。该端口也可以自定义,在前面的​​service​​章节说过。单一般不建议自定义。

示例1:使用Ingress发布Nginx

该示例中创建的所有资源都位于新建的​​testing​​名称空间中。与其他的资源在逻辑上进行隔离,以方便管理。

(八)Kubernetes Ingress资源_Kubernetes_04

首先创建一个单独的目录为了方便管理

[root@k8s-master ~]# mkdir ingress-nginx/ingress
[root@k8s-master ~]# cd ingress-nginx/ingress/

(1)、创建​​testing​​​名称空间(也可以使用命令直接创建​​# kubectl create namespace my-namespace​​,不过这里使用资源清单格式创建)

[root@k8s-master ingress]# vim namespace-testing.yaml    #编写namespace清单文件
apiVersion: v1
kind: Namespace
metadata:
name: testing
labels:
env: testing
[root@k8s-master ingress]#
[root@k8s-master ingress]# kubectl apply -f namespace-testing.yaml #创建namespace
namespace/testing created
[root@k8s-master ingress]#
[root@k8s-master ingress]# kubectl get namespace testing #验证
NAME STATUS AGE
testing Active 12s

(2)、部署​​nginx​​​实例,这里使用​​Deployment​​​控制器于​​testing​​​中部署​​nginx​​​相关的​​Pod​​对象。

[root@k8s-master ingress]# vim deployment-nginx.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name: deploy-nginx
namespace: testing
spec:
replicas: 3
selector:
matchLabels:
app: nginx
template:
metadata:
labels:
app: nginx
spec:
containers:
- name: nginx
image: nginx:1.12
ports:
- name: http
containerPort: 80
[root@k8s-master ingress]#
[root@k8s-master ingress]# kubectl apply -f deployment-nginx.yaml
deployment.apps/deploy-nginx created
[root@k8s-master ingress]#
[root@k8s-master ingress]# kubectl get deploy -n testing
NAME READY UP-TO-DATE AVAILABLE AGE
deploy-nginx 3/3 3 3 5s
[root@k8s-master ingress]#
[root@k8s-master ingress]# kubectl get pods -n testing
NAME READY STATUS RESTARTS AGE
deploy-nginx-686bddcb56-9g7pq 1/1 Running 0 6s
deploy-nginx-686bddcb56-gqpm2 1/1 Running 0 6s
deploy-nginx-686bddcb56-vtwkq 1/1 Running 0 6s

(3)、创建​​Service​​​资源,关联后端的​​Pod​​​资源。这里通过​​service​​​资源​​svc-nginx​​​的​​80​​​端口去暴露容器的​​80​​端口。

[root@k8s-master ingress]# vim service-nginx.yaml
apiVersion: v1
kind: Service
metadata:
name: svc-nginx
namespace: testing
labels:
app: svc-nginx
spec:
selector:
app: nginx
ports:
- name: http
port: 80
targetPort: 80
protocol: TCP
[root@k8s-master ingress]#
[root@k8s-master ingress]# kubectl apply -f service-nginx.yaml
service/svc-nginx created
[root@k8s-master ingress]#
[root@k8s-master ingress]# kubectl get svc -n testing
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
svc-nginx ClusterIP 10.99.233.90 <none> 80/TCP 6s
[root@k8s-master ingress]#
[root@k8s-master ingress]# kubectl describe svc/svc-nginx -n testing
Name: svc-nginx
Namespace: testing
Labels: app=svc-nginx
Annotations: kubectl.kubernetes.io/last-applied-configuration:
{"apiVersion":"v1","kind":"Service","metadata":{"annotations":{},"labels":{"app":"svc-nginx"},"name":"svc-nginx","namespace":"testing"},"s...
Selector: app=nginx
Type: ClusterIP
IP: 10.99.233.90
Port: http 80/TCP
TargetPort: 80/TCP
Endpoints: 10.244.1.76:80,10.244.1.77:80,10.244.2.74:80
Session Affinity: None
Events: <none>

(4)、创建​​Ingress​​​资源,匹配​​Service​​​资源​​svc-nginx​​​,并将​​svc-nginx​​的80端口暴露。

[root@k8s-master ingress]# vim ingress-nginx.yaml
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: nginx
namespace: testing
annotations:
kubernetes.io/ingress.class: "nginx"
spec:
rules:
- host: nginx.ilinux.io
http:
paths:
- path:
backend:
serviceName: svc-nginx
servicePort: 80
[root@k8s-master ingress]#
[root@k8s-master ingress]# kubectl apply -f ingress-nginx.yaml
ingress.extensions/nginx created
[root@k8s-master ingress]#
[root@k8s-master ingress]# kubectl get ingress -n testing
NAME HOSTS ADDRESS PORTS AGE
nginx nginx.ilinux.io 80 16s
[root@k8s-master ingress]#
[root@k8s-master ingress]# kubectl describe ingress -n testing
Name: nginx
Namespace: testing
Address:
Default backend: default-http-backend:80 (<none>)
Rules:
Host Path Backends
---- ---- --------
tomcat.ilinux.io
svc-nginx:80 (10.244.1.76:80,10.244.1.77:80,10.244.2.74:80)
Annotations:
kubectl.kubernetes.io/last-applied-configuration: {"apiVersion":"extensions/v1beta1","kind":"Ingress","metadata":{"annotations":{"kubernetes.io/ingress.class":"nginx"},"name":"nginx","namespace":"testing"},"spec":{"rules":[{"host":"nginx.ilinux.io","http":{"paths":[{"backend":{"serviceName":"svc-nginx","servicePort":80},"path":null}]}}]}}

kubernetes.io/ingress.class: nginx
Events: <none>

(5)、测试,通过​​Ingress​​​控制器的前端的​​Service​​​资源的​​NodePort​​来访问此服务,

#首先查看前面部署Ingress控制器的前端的Service资源的映射端口
[root@k8s-master ingress-nginx]# kubectl get svc -n ingress-nginx
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
ingress-nginx NodePort 10.107.40.182 <none> 80:32699/TCP,443:30842/TCP 3m59s

#终端测试,添加hosts
[root@k8s-master ~]# cat /etc/hosts
192.168.1.31 k8s-master nginx.ilinux.io
192.168.1.32 k8s-node1 nginx.ilinux.io
192.168.1.33 k8s-node2 nginx.ilinux.io
#访问测试
[root@k8s-master ~]# curl nginx.ilinux.io:32699
<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>
<style>
......

(八)Kubernetes Ingress资源_Kubernetes_05

验证是否调度到后端的​​Pod​​资源,查看日志

[root@k8s-master ~]# kubectl get pods -n testing
NAME READY STATUS RESTARTS AGE
deploy-nginx-686bddcb56-9g7pq 1/1 Running 0 56m
deploy-nginx-686bddcb56-gqpm2 1/1 Running 0 56m
deploy-nginx-686bddcb56-vtwkq 1/1 Running 0 56m
[root@k8s-master ~]# kubectl logs deploy-nginx-686bddcb56-9g7pq -n testing
10.244.2.75 - - [28/Sep/2019:02:33:45 +0000] "GET / HTTP/1.1" 200 612 "-" "curl/7.29.0" "10.244.0.0"
10.244.2.75 - - [28/Sep/2019:02:44:02 +0000] "GET / HTTP/1.1" 200 612 "-" "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/76.0.3809.100 Safari/537.36" "10.244.0.0"

(6)、配置​​TLS Ingress​​资源(这里使用自签证书)

1)生成key
[root@k8s-master ingress]# openssl genrsa -out tls.key 2048
2)生成证书
[root@k8s-master ingress]# openssl req -new -x509 -key tls.key -out tls.crt -subj /C=CN/ST=ShenZhen/L=ShenZhen/O=DevOps/CN=nginx.ilinux.io -days 3650

3)创建secret资源
[root@k8s-master ingress]# kubectl create secret tls nginx-ingress-secret --cert=tls.crt --key=tls.key -n testing
secret/nginx-ingress-secret created
[root@k8s-master ingress]# kubectl get secret -n testing
NAME TYPE DATA AGE
default-token-lfzrt kubernetes.io/service-account-token 3 116m
nginx-ingress-secret kubernetes.io/tls 2 16s

4)编写Ingress资源清单文件
[root@k8s-master ingress]# vim ingress-nginx-https.yaml
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: nginx-ingress-tls
namespace: testing
annotations:
kubernetes.io/ingress.class: "nginx"
spec:
tls:
- hosts:
- nginx.ilinux.io
secretName: nginx-ingress-secret
rules:
- host: nginx.ilinux.io
http:
paths:
- path: /
backend:
serviceName: svc-nginx
servicePort: 80

5)查看Ingress资源信息
[root@k8s-master ingress]# kubectl get ingress -n testing
NAME HOSTS ADDRESS PORTS AGE
nginx nginx.ilinux.io 80 66m
nginx-ingress-tls nginx.ilinux.io 80, 443 15s
[root@k8s-master ingress]# kubectl describe ingress/nginx-ingress-tls -n testing
Name: nginx-ingress-tls
Namespace: testing
Address:
Default backend: default-http-backend:80 (<none>)
TLS:
nginx-ingress-secret terminates nginx.ilinux.io
Rules:
Host Path Backends
---- ---- --------
nginx.ilinux.io
/ svc-nginx:80 (10.244.1.76:80,10.244.1.77:80,10.244.2.74:80)
Annotations:
kubectl.kubernetes.io/last-applied-configuration: {"apiVersion":"extensions/v1beta1","kind":"Ingress","metadata":{"annotations":{"kubernetes.io/ingress.class":"nginx"},"name":"nginx-ingress-tls","namespace":"testing"},"spec":{"rules":[{"host":"nginx.ilinux.io","http":{"paths":[{"backend":{"serviceName":"svc-nginx","servicePort":80},"path":"/"}]}}],"tls":[{"hosts":["nginx.ilinux.io"],"secretName":"nginx-ingress-secret"}]}}

kubernetes.io/ingress.class: nginx
Events:
Type Reason Age From Message
---- ------ ---- ---- -------
Normal CREATE 64s nginx-ingress-controller Ingress testing/nginx-ingress-tls

(7)、测试​​https​​(这里由于是自签,所以上面提示不安全)

#首先查看前面部署Ingress控制器的前端的Service资源的映射端口
[root@k8s-master ingress-nginx]# kubectl get svc -n ingress-nginx
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
ingress-nginx NodePort 10.107.40.182 <none> 80:32699/TCP,443:30842/TCP 3m59s

(八)Kubernetes Ingress资源_linux_06

示例2:使用Ingress发布多个服务

将不同的服务映射不同的主机上

(八)Kubernetes Ingress资源_tomcat_07

准备工作:这里创建一个目录保存本示例的所有资源配置清单

[root@k8s-master ~]# mkdir ingress-nginx/multi_svc
[root@k8s-master ~]# cd !$

创建名称空间

创建一个名称空间保存本示例的所有对象(方便管理)

[root@k8s-master multi_svc]# vim namespace-ms.yaml    #编写配置清单文件
apiVersion: v1
kind: Namespace
metadata:
name: multisvc
labels:
env: multisvc

[root@k8s-master multi_svc]# kubectl apply -f namespace-ms.yaml #创建上面定义的名称空间
namespace/multisvc created

[root@k8s-master multi_svc]# kubectl get namespace multisvc #查看名称空间
NAME STATUS AGE
multisvc Active 9s

创建后端应用和Service

这里后端应用创建为一组​​nginx​​​应用和一组​​tomcat​​应用

1)编写资源清单文件,这里将​​service​​​资源对象和​​deployment​​控制器写在这一个文件里

[root@k8s-master multi_svc]# vim deploy_service-ms.yaml
#tomcat应用的Deployment控制器
apiVersion: apps/v1
kind: Deployment
metadata:
name: tomcat-deploy
namespace: multisvc
spec:
replicas: 3
selector:
matchLabels:
app: tomcat
template:
metadata:
labels:
app: tomcat
spec:
containers:
- name: tomcat
image: tomcat:jdk8
imagePullPolicy: IfNotPresent
ports:
- name: httpport
containerPort: 8080
- name: ajpport
containerPort: 8009
---
#tomcat应用的Service资源
apiVersion: v1
kind: Service
metadata:
name: tomcat-svc
namespace: multisvc
labels:
app: tomcat-svc
spec:
selector:
app: tomcat
ports:
- name: httpport
port: 8080
targetPort: 8080
protocol: TCP
- name: ajpport
port: 8009
targetPort: 8009
protocol: TCP

---
#nginx应用的Deployment控制器
apiVersion: apps/v1
kind: Deployment
metadata:
name: nginx-deploy
namespace: multisvc
spec:
replicas: 3
selector:
matchLabels:
app: nginx
template:
metadata:
labels:
app: nginx
spec:
containers:
- name: nginx
image: nginx:1.12
imagePullPolicy: IfNotPresent
ports:
- name: http
containerPort: 80
---
#nginx应用的Service资源
apiVersion: v1
kind: Service
metadata:
name: nginx-svc
namespace: multisvc
labels:
app: nginx-svc
spec:
selector:
app: nginx
ports:
- name: http
port: 80
targetPort: 80
protocol: TCP

2)创建上面定义资源对象并查看验证

[root@k8s-master multi_svc]# kubectl apply -f deploy_service-ms.yaml 
deployment.apps/tomcat-deploy created
service/tomcat-svc created
deployment.apps/nginx-deploy created
service/nginx-svc created
[root@k8s-master multi_svc]# kubectl get pods -n multisvc -o wide #查看pod资源
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
nginx-deploy-86c667ff66-hl6rx 1/1 Running 0 13s 10.244.2.78 k8s-node2 <none> <none>
nginx-deploy-86c667ff66-hx4j8 1/1 Running 0 13s 10.244.2.77 k8s-node2 <none> <none>
nginx-deploy-86c667ff66-tl9mm 1/1 Running 0 13s 10.244.1.79 k8s-node1 <none> <none>
tomcat-deploy-6484688ddc-n25hn 1/1 Running 0 13s 10.244.1.78 k8s-node1 <none> <none>
tomcat-deploy-6484688ddc-s8dts 1/1 Running 0 13s 10.244.1.80 k8s-node1 <none> <none>
tomcat-deploy-6484688ddc-snszk 1/1 Running 0 13s 10.244.2.76 k8s-node2 <none> <none>
[root@k8s-master multi_svc]# kubectl get svc -n multisvc #查看service资源对象
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
nginx-svc ClusterIP 10.104.213.237 <none> 80/TCP 26s
tomcat-svc ClusterIP 10.103.75.161 <none> 8080/TCP,8009/TCP 26s

[root@k8s-master multi_svc]# kubectl describe svc/nginx-svc -n multisvc #查看service对象nginx-svc的详细信息
Name: nginx-svc
Namespace: multisvc
Labels: app=nginx-svc
Annotations: kubectl.kubernetes.io/last-applied-configuration:
{"apiVersion":"v1","kind":"Service","metadata":{"annotations":{},"labels":{"app":"nginx-svc"},"name":"nginx-svc","namespace":"multisvc"},"...
Selector: app=nginx
Type: ClusterIP
IP: 10.104.213.237
Port: http 80/TCP
TargetPort: 80/TCP
Endpoints: 10.244.1.79:80,10.244.2.77:80,10.244.2.78:80
Session Affinity: None
Events: <none>

[root@k8s-master multi_svc]# kubectl describe svc/tomcat-svc -n multisvc #查看service对象tomcat-svc的详细信息
Name: tomcat-svc
Namespace: multisvc
Labels: app=tomcat-svc
Annotations: kubectl.kubernetes.io/last-applied-configuration:
{"apiVersion":"v1","kind":"Service","metadata":{"annotations":{},"labels":{"app":"tomcat-svc"},"name":"tomcat-svc","namespace":"multisvc"}...
Selector: app=tomcat
Type: ClusterIP
IP: 10.103.75.161
Port: httpport 8080/TCP
TargetPort: 8080/TCP
Endpoints: 10.244.1.78:8080,10.244.1.80:8080,10.244.2.76:8080
Port: ajpport 8009/TCP
TargetPort: 8009/TCP
Endpoints: 10.244.1.78:8009,10.244.1.80:8009,10.244.2.76:8009
Session Affinity: None
Events: <none>

创建Ingress资源对象

1)编写资源清单文件

[root@k8s-master multi_svc]# vim ingress_host-ms.yaml
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: multi-ingress
namespace: multisvc
spec:
rules:
- host: nginx.imyapp.com
http:
paths:
- path: /
backend:
serviceName: nginx-svc
servicePort: 80
- host: tomcat.imyapp.com
http:
paths:
- path: /
backend:
serviceName: tomcat-svc
servicePort: 8080

2)创建上面定义资源对象并查看验证

[root@k8s-master multi_svc]# kubectl apply -f ingress_host-ms.yaml 
ingress.extensions/multi-ingress created
[root@k8s-master multi_svc]# kubectl get ingress -n multisvc #查看ingress资源对象
NAME HOSTS ADDRESS PORTS AGE
multi-ingress nginx.imyapp.com,tomcat.imyapp.com 80 18s

[root@k8s-master multi_svc]# kubectl describe ingress/multi-ingress -n multisvc #查看ingress资源multi-ingrsss的详细信息
Name: multi-ingress
Namespace: multisvc
Address:
Default backend: default-http-backend:80 (<none>)
Rules:
Host Path Backends
---- ---- --------
nginx.imyapp.com
/ nginx-svc:80 (10.244.1.79:80,10.244.2.77:80,10.244.2.78:80)
tomcat.imyapp.com
/ tomcat-svc:8080 (10.244.1.78:8080,10.244.1.80:8080,10.244.2.76:8080)
Annotations:
kubectl.kubernetes.io/last-applied-configuration: {"apiVersion":"extensions/v1beta1","kind":"Ingress","metadata":{"annotations":{},"name":"multi-ingress","namespace":"multisvc"},"spec":{"rules":[{"host":"nginx.imyapp.com","http":{"paths":[{"backend":{"serviceName":"nginx-svc","servicePort":80},"path":"/"}]}},{"host":"tomcat.imyapp.com","http":{"paths":[{"backend":{"serviceName":"tomcat-svc","servicePort":8080},"path":"/"}]}}]}}

Events:
Type Reason Age From Message
---- ------ ---- ---- -------
Normal CREATE 39s nginx-ingress-controller Ingress multisvc/multi-ingress

测试访问

这是测试自定义的域名,故需要配置​​host​

192.168.1.31     nginx.imyapp.com tomcat.imyapp.com
192.168.1.32 nginx.imyapp.com tomcat.imyapp.com
192.168.1.33 nginx.imyapp.com tomcat.imyapp.com

查看部署的​​Ingress​​​的​​Service​​对象的端口

[root@k8s-master multi_svc]# kubectl get svc -n ingress-nginx
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
ingress-nginx NodePort 10.107.40.182 <none> 80:32699/TCP,443:30842/TCP 6h39m

访问​​nginx.imyapp.com:32699​

(八)Kubernetes Ingress资源_linux_08

访问​​tomcat.imyapp.com:32699​

(八)Kubernetes Ingress资源_nginx_09

配置Ingress处理TLS传输

这里使用自签证书,通过​​OpenSSL​​进行创建

1)创建证书

#创建nginx.imyapp.com域名的证书
[root@k8s-master multi_svc]# openssl genrsa -out nginx.imyapp.com.key 2048
[root@k8s-master multi_svc]# openssl req -new -x509 -key nginx.imyapp.com.key -out nginx.imyapp.com.crt -subj /C=CN/ST=ShenZhen/L=ShenZhen/O=DevOps/CN=nginx.imyapp.com -days 3650

#创建tomcat.imyapp.com域名的证书
[root@k8s-master multi_svc]# openssl genrsa -out tomcat.imyapp.com.key 2048
[root@k8s-master multi_svc]# openssl req -new -x509 -key tomcat.imyapp.com.key -out tomcat.imyapp.com.crt -subj /C=CN/ST=ShenZhen/L=ShenZhen/O=DevOps/CN=tomcat.imyapp.com -days 3650

#查看生成的证书
[root@k8s-master multi_svc]# ll *.com.*
-rw-r--r-- 1 root root 1298 9月 28 17:23 nginx.imyapp.com.crt
-rw-r--r-- 1 root root 1675 9月 28 17:22 nginx.imyapp.com.key
-rw-r--r-- 1 root root 1302 9月 28 17:24 tomcat.imyapp.com.crt
-rw-r--r-- 1 root root 1679 9月 28 17:24 tomcat.imyapp.com.key

2)创建​​secrte​

#创建nginx域名的secret
[root@k8s-master multi_svc]# kubectl create secret tls nginx-ingress-secret --cert=nginx.imyapp.com.crt --key=nginx.imyapp.com.key -n multisvc
secret/nginx-ingress-secret created

#创建tomcat域名的secret
[root@k8s-master multi_svc]# kubectl create secret tls tomcat-ingress-secret --cert=tomcat.imyapp.com.crt --key=tomcat.imyapp.com.key -n multisvc
secret/tomcat-ingress-secret created

#查看secret
[root@k8s-master multi_svc]# kubectl get secret -n multisvc
NAME TYPE DATA AGE
default-token-mf5wd kubernetes.io/service-account-token 3 5h12m
nginx-ingress-secret kubernetes.io/tls 2 53s
tomcat-ingress-secret kubernetes.io/tls 2 27s

3)编写带​​TLS​​​的​​Ingress​​​资源清单(这里通过复制,没有删除上面创建的​​ingress​​)

[root@k8s-master multi_svc]# cp ingress_host-ms.yaml ingress_host_https-ms.yaml
[root@k8s-master multi_svc]# vim ingress_host_https-ms.yaml
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: multi-ingress-https
namespace: multisvc
annotations:
kubernetes.io/ingress.class: "nginx"
spec:
tls:
- hosts:
- nginx.imyapp.com
secretName: nginx-ingress-secret
- hosts:
- tomcat.imyapp.com
secretName: tomcat-ingress-secret
rules:
- host: nginx.imyapp.com
http:
paths:
- path: /
backend:
serviceName: nginx-svc
servicePort: 80
- host: tomcat.imyapp.com
http:
paths:
- path: /
backend:
serviceName: tomcat-svc
servicePort: 8080

4)创建​​ingress​​资源

[root@k8s-master multi_svc]# kubectl apply -f ingress_host_https-ms.yaml
ingress.extensions/multi-ingress-https created
[root@k8s-master multi_svc]# kubectl get ingress -n multisvc
NAME HOSTS ADDRESS PORTS AGE
multi-ingress nginx.imyapp.com,tomcat.imyapp.com 80 44m
multi-ingress-https nginx.imyapp.com,tomcat.imyapp.com 80, 443 3s

5)测试,通过​​Ingress​​​控制器的前端的​​Service​​​资源的​​NodePort​​​来访问此服务,上面看到​​ingress​​​控制器的​​service​​​资源的​​443​​​端口对应的节点的​​30842​​端口。

访问​​nginx​

(八)Kubernetes Ingress资源_linux_10

访问​​tomcat​

(八)Kubernetes Ingress资源_nginx_11

将不同的服务映射到相同主机的不同路径

(八)Kubernetes Ingress资源_linux_12


在这种情况下,根据请求的​​URL​​​中的路径,请求将发送到两个不同的服务。因此,客户端可以通过一个​​IP​​​地址(​​Ingress​​​ 控制器的​​IP​​地址)访问两种不同的服务。

注意:这里​​Ingress​​​中​​path​​​的定义,需要与后端真实​​Service​​​提供的​​Path​​​一致,否则将被转发到一个不存在的​​path​​上,引发错误。


Ingress定义示例

apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: tomcat-ingress
namespace: multisvc
spec:
rules:
- host: www.imyapp.com
http:
paths:
- path: /nginx
backend:
serviceName: nginx-svc
servicePort: 80
- path: /tomcat
backend:
serviceName: tomcat-svc
servicePort: 8080


人生是条无名的河,是浅是深都要过; 人生是杯无色的茶,是苦是甜都要喝; 人生是首无畏的歌,是高是低都要唱。


举报

相关推荐

0 条评论