k8s控制器的选择
想要在k8s中实现Ingress方式暴露服务,需要在k8s中先部署好相应的控制器,因为Ingress只是规则的集合,而真正工作的是Ingress-controoller。
在k8s的Ingress中,有很多控制器可以选择,比较流行的有Nginx-controoller和traefik,这里以部署traefik为例。
traefik的官网地址为
https://traefik.io/
其中,在开始部署traefik之前,我们可以利用先前部署的Nginx服务,这样实验的时候就只需要部署traefik就可以了。具体的部署过程可以参考官方文档
https://doc.traefik.io/
- 创建一个 IngressRoute Definition,即路由入口定义
# vim traefik_ingressroute.yaml
apiVersion: apiextensions.k8s.io/v1beta1
kind: CustomResourceDefinition
metadata:
name: ingressroutes.traefik.containo.us
spec:
group: traefik.containo.us
version: v1alpha1
names:
kind: IngressRoute
plural: ingressroutes
singular: ingressroute
scope: Namespaced
---
apiVersion: apiextensions.k8s.io/v1beta1
kind: CustomResourceDefinition
metadata:
name: middlewares.traefik.containo.us
spec:
group: traefik.containo.us
version: v1alpha1
names:
kind: Middleware
plural: middlewares
singular: middleware
scope: Namespaced
---
apiVersion: apiextensions.k8s.io/v1beta1
kind: CustomResourceDefinition
metadata:
name: ingressroutetcps.traefik.containo.us
spec:
group: traefik.containo.us
version: v1alpha1
names:
kind: IngressRouteTCP
plural: ingressroutetcps
singular: ingressroutetcp
scope: Namespaced
---
apiVersion: apiextensions.k8s.io/v1beta1
kind: CustomResourceDefinition
metadata:
name: ingressrouteudps.traefik.containo.us
spec:
group: traefik.containo.us
version: v1alpha1
names:
kind: IngressRouteUDP
plural: ingressrouteudps
singular: ingressrouteudp
scope: Namespaced
---
apiVersion: apiextensions.k8s.io/v1beta1
kind: CustomResourceDefinition
metadata:
name: tlsoptions.traefik.containo.us
spec:
group: traefik.containo.us
version: v1alpha1
names:
kind: TLSOption
plural: tlsoptions
singular: tlsoption
scope: Namespaced
---
apiVersion: apiextensions.k8s.io/v1beta1
kind: CustomResourceDefinition
metadata:
name: tlsstores.traefik.containo.us
spec:
group: traefik.containo.us
version: v1alpha1
names:
kind: TLSStore
plural: tlsstores
singular: tlsstore
scope: Namespaced
---
apiVersion: apiextensions.k8s.io/v1beta1
kind: CustomResourceDefinition
metadata:
name: traefikservices.traefik.containo.us
spec:
group: traefik.containo.us
version: v1alpha1
names:
kind: TraefikService
plural: traefikservices
singular: traefikservice
scope: Namespaced
---
kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
name: traefik-ingress-controller
rules:
- apiGroups:
- ""
resources:
- services
- endpoints
- secrets
verbs:
- get
- list
- watch
- apiGroups:
- extensions
- networking.k8s.io
resources:
- ingresses
- ingressclasses
verbs:
- get
- list
- watch
- apiGroups:
- extensions
resources:
- ingresses/status
verbs:
- update
- apiGroups:
- traefik.containo.us
resources:
- middlewares
- ingressroutes
- traefikservices
- ingressroutetcps
- ingressrouteudps
- tlsoptions
- tlsstores
verbs:
- get
- list
- watch
---
kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
name: traefik-ingress-controller
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: traefik-ingress-controller
subjects:
- kind: ServiceAccount
name: traefik-ingress-controller
namespace: default
创建该规则 # kubectl apply -f traefik_ingressroute.yaml
2. 创建traefik自身的server服务
# vim traefik_svc.yaml
apiVersion: v1
kind: Service
metadata:
name: traefik
spec:
type: NodePort
ports:
- protocol: TCP
name: web
port: 8000
- protocol: TCP
name: admin
port: 8080
- protocol: TCP
name: websecure
port: 4443
selector:
app: traefik
--------------------------------------------------
创建svc
# kubectl apply -f traefik_svc.yaml
查看svc是否启动
[root@master ~]$ kubectl get svc
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
kubernetes ClusterIP 10.1.0.1 <none> 443/TCP 25d
mysql ClusterIP 10.1.147.181 <none> 3306/TCP 19d
nginxsvc NodePort 10.1.196.113 <none> 80:30000/TCP 20d
traefik NodePort 10.1.242.105 <none> 8000:32627/TCP,8080:30211/TCP,4443:30113/TCP
3. 创建traefik的deployment控制器
# vim traefik_dep.yaml
apiVersion: v1
kind: ServiceAccount
metadata:
namespace: default
name: traefik-ingress-controller
---
kind: Deployment
apiVersion: apps/v1
metadata:
namespace: default
name: traefik
labels:
app: traefik
spec:
replicas: 1
selector:
matchLabels:
app: traefik
template:
metadata:
labels:
app: traefik
spec:
serviceAccountName: traefik-ingress-controller
containers:
- name: traefik
image: traefik:v2.3
args:
- --api.insecure
- --accesslog
- --entrypoints.web.Address=:8000
- --entrypoints.websecure.Address=:4443
- --providers.kubernetescrd
- --certificatesresolvers.myresolver.acme.tlschallenge
- --certificatesresolvers.myresolver.acme.email=foo@you.com
- --certificatesresolvers.myresolver.acme.storage=acme.json
# Please note that this is the staging Let's Encrypt server.
# Once you get things working, you should remove that whole line altogether.
- --certificatesresolvers.myresolver.acme.caserver=https://acme-staging-v02.api.letsencrypt.org/directory
ports:
- name: web
containerPort: 8000
- name: websecure
containerPort: 4443
- name: admin
containerPort: 8080
#创建deployment
#$ kubectl apply -f traefik_dep.yaml
#查看pod是否创建成功
[root@master ~]$ kubectl get pod
NAME READY STATUS RESTARTS AGE
mysql-k478j 1/1 Running 10 19d
nginx-df96546d9-ck5vg 1/1 Running 11 19d
nginx-df96546d9-jltkw 1/1 Running 11 19d
traefik-6b458d8d99-lrbq5 1/1 Running 1 33h
4. 上面的server服务采用的Nodeport:PORT 方式暴露,查看相应的端口映射,
[root@master ~]$ kubectl get svc
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE traefik NodePort 10.1.242.105 <none> 8000:32627/TCP,8080:30211/TCP,4443:30113/TCP 33
查看traefik_svc.yaml可知:
- protocol: TCP
name: web port: 8000
- protocol: TCP
name: admin port: 8080
- protocol: TCP
name: websecure port: 4443
admin管理页面的端口为8080,映射为节点端口为30211,这时可以在浏览器上输入任意NodePort:30211,即可进入traefik提供的管理页面,
到了这个时候,可以说,Ingress-controoller已经添加完成了,接下来要做的,是将你想暴露出去的server,创建相应的Ingress规则。
5. 这里要暴露的是Nginx的server服务,先新建相应的yaml文件
# vim nginx_ingress.yaml
apiVersion: traefik.containo.us/v1alpha1
kind: IngressRoute
metadata:
name: simpleingressroute
namespace: default
spec:
entryPoints:
- web
routes:
- match: www.app.com ###这里的意思是将请求到该域名的访问转发给后端定义的service, Host(`your.example.com`) && PathPrefix(`/notls`)
kind: Rule
services:
- name: nginx_svc #######此处要跟想暴露的svc的名称一致
port: 80
---------------------------------
创建规则
# kubectl apply -f nginx_ingress.yaml
此时,只要访问上文定义的 www.app.com 即可访问到nginx_svc提供的服务,在这里,我们再采用Nginx搭建反向代理负载均衡服务器,上文中,我们定义了traefik服务的相关端口,其中web端口为8000,映射到节点的端口为32627,所以后端代理节点的server为NodeIp+32627即可,以下为参考配置文件:
[root@lb1 ~]$ vim /etc/nginx/conf.d/upstream.conf
upstream web { server 192.168.75.140:32627 fail_timeout=10s max_fails=3; server 192.168.75.135:32627 fail_timeout=10s max_fails=3; server 192.168.75.133:32627 fail_timeout=10s max_fails=3; ip_hash; } server { listen 80; server_name www.app.com; location / { proxy_pass http://web; proxy_set_header Host $host; proxy_set_header X-Forwarded-For $remote_addr; proxy_next_upstream error timeout http_404 http_403; } }
这时候,从浏览器访问www.app.com,可以发现,已经可以通过域名进行访问了。
到这里,最简单的基于http进行访问的方式已经完成了!
本文作者为lishengyu,转载请注明。