案例:
准备
准备两个的Deployment与对应的SVC
使用自建的pyapp镜像
app.py V4版本 之前还有V1 V2 V3
from flask import Flask, request, jsonify
import socket
app = Flask(__name__)
version = "v4"
@app.route('/', methods=['GET'])
def stop_endpoint():
name = request.args.get('name', None) # 从 URL 查询字符串中获取 name 参数
# 返回响应
return jsonify({'version': version})
@app.route('/hostname', methods=['GET'])
def get_hostname():
hostname = socket.gethostname()
return jsonify({'version': version, 'hostname': hostname})
@app.errorhandler(404)
def page_not_found(e):
url = request.path
return jsonify({'version': version, 'url': url})
if __name__ == '__main__':
app.run("0.0.0.0", debug=True) # 在开发模式下运行 Flask 应用
dockerfile
FROM python
WORKDIR /app
RUN pip3 --no-cache-dir install -i https://mirrors.aliyun.com/pypi/simple/ flask
COPY app.py /app/app.py
EXPOSE 5000
ENTRYPOINT ["python3", "app.py"]
镜像
harbor.tangotz.com/pyapp/pyapp:v4
harbor.tangotz.com/pyapp/pyapp:v3
使用V3 V4两个镜像,创建两个deployment
deploy-v3.yml
apiVersion: apps/v1
kind: Deployment
metadata:
name: pyapp-v3-deployment
spec:
replicas: 3
selector:
matchLabels:
app: pyapp_v3
template:
metadata:
labels:
app: pyapp_v3
spec:
containers:
- image: harbor.tangotz.com/pyapp/pyapp:v3
name: pyapp-v3-pod
ports:
- containerPort: 5000
deploy-v4.yml
apiVersion: apps/v1
kind: Deployment
metadata:
name: pyapp-v4-deployment
spec:
replicas: 3
selector:
matchLabels:
app: pyapp_v4
template:
metadata:
labels:
app: pyapp_v4
spec:
containers:
- image: harbor.tangotz.com/pyapp/pyapp:v4
name: pyapp-v4-pod
ports:
- containerPort: 5000
创建对应的SVC
svc-v3.yml
apiVersion: v1
kind: Service
metadata:
name: pyapp-v3-svc
spec:
selector:
app: pyapp_v3
ports:
- port: 8080
targetPort: 5000
svc-v4.yml
apiVersion: v1
kind: Service
metadata:
name: pyapp-v4-svc
spec:
selector:
app: pyapp_v4
ports:
- port: 8080
targetPort: 5000
实现目标1
访问 v3.tangotz.com 转发到svc-v3上
ingress-v3.yml
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: pyapp-v3-ingress
spec:
ingressClassName: nginx
rules:
- host: v3.tangotz.com
http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: pyapp-v3-svc
port:
number: 8080
访问 v4.tangotz.com 转发到svc-v4上
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: pyapp-v4-ingress
spec:
ingressClassName: nginx
rules:
- host: v4.tangotz.com
http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: pyapp-v4-svc
port:
number: 8080
效果:
实现目标2
访问 v.tangotz.com/v3 转发到svc-v3上
访问 v.tangotz.com/v4 转发到svc-v4上
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: ingress-v
annotations:
nginx.ingress.kubernetes.io/rewrite-target: /$2
spec:
ingressClassName: nginx
rules:
- host: v.tangotz.com
http:
paths:
- path: /v3(/|$)(.*)
pathType: ImplementationSpecific
backend:
service:
name: pyapp-v3-svc
port:
number: 8080
- path: /v4(/|$)(.*)
pathType: ImplementationSpecific
backend:
service:
name: pyapp-v4-svc
port:
number: 8080
在写这个示例的时候,关于path正则遇到了一些小麻烦,这个示例的核心是根据url的开头是/v3 /v4来决定流量代理到那个svc上,并将请求重写,去掉/v3 /v4,直接访问后面的路径。
最初写的是/v3/(.*) ,匹配组相应的就是$1,但是这个写法不能匹配/v3或者/v4,因为单独的/v3 /v3是没有后面的是无法和path中的正则匹配,多了一个/
效果
实现目标3
https配置
创建tls secret
使用阿里云创建一个免费证书做演示
kubectl create secret tls ssl-tangotz --cert=./ssl.tangotz.com.pem --key=./ssl.tangotz.com.key
在资源文件中添加tls配置
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: ingress-tls
spec:
ingressClassName: nginx
rules:
- host: ssl.tangotz.com
http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: pyapp-v4-svc
port:
number: 8080
tls:
- hosts:
- ssl.tangotz.com
secretName: ssl-tangotz
修改hosts文件用以实现访问
效果
注意:使用特殊方式上网时,注意检查浏览器代理情况,防止出现Hosts修改不生效的情况。