首页 > 解决方案 > 具有 Kubernetes Ingress 资源 (nginx) 的不同路径上的两个 Flask 应用程序

问题描述

我的目标如下:我在两个独立的 Docker 容器中有两个 Flask 应用程序,我想通过同一 IP 地址上的不同路径访问它们,如下所示:127.0.0.1/app1、127.0.0.1/app2(但使用真实的IP地址)。

我想用 Kubernetes 来做这件事。

我有一个 Kubernetes 集群正在运行(Azure Kubernetes 服务),两个 Docker 容器中的每一个都有一个部署和服务。每个应用程序的 pod 运行良好。我还在集群中安装了一个入口控制器(Nginx),现在我正试图让它与单个入口资源一起工作。

如果我按以下方式执行此操作,则它适用于 1 个单个应用程序(其中任何一个都适用于 IP 地址/):

apiVersion: extensions/v1beta1
kind: Ingress
metadata:
  name: ingress-name
  namespace: my-namespace
  annotations:
    nginx.ingress.kubernetes.io/rewrite-target: /
spec:
  rules:
  - http:
      paths:
      - path: /
        backend:
          serviceName: service1 (or service2)
          servicePort: 5000

但是当我尝试以下它不起作用时:

apiVersion: extensions/v1beta1
kind: Ingress
metadata:
  name: ingress-name
  namespace: my-namespace
  annotations:
    nginx.ingress.kubernetes.io/rewrite-target: /
spec:
  rules:
  - http:
      paths:
      - path: /app1
        backend:
          serviceName: service1 
          servicePort: 5000
      - path: /app2
        backend:
          serviceName: service2 
          servicePort: 5000

我能够看到 Flask 应用程序为它们各自路径上的两个应用程序呈现的 html 页面,但这些功能都不起作用。

除了路径似乎并不总是有效的事实(当我尝试连接到 IP-address/app1 或 IP-address/app1/ 时,我有时会被重定向到 IP-address/),问题如下(我认为):

每个 Flask 应用程序都有一个“/predict”路由,它只接受 POST 请求,其中对应用程序进行了相应的调用(每个应用程序都是一个 AI 应用程序,对给定的输入进行预测)。

两个应用程序的调用均针对 IP-address/predict,而不是 IP-address/app1/predict 或 IP-address/app2/predict。由于此路径问题,也无法访问静态文件。

我不知道这是否是正确的做法?我也尝试过使用“重写目标”,但还没有找到解决方案。

我希望有人能解释我做错了什么。

标签: nginxflaskkuberneteskubernetes-ingressnginx-ingress

解决方案


您可以考虑完全在 Ingress 清单中提供捕获组,并指定将定义源 Nginx重写规则的特定正则表达式。

Ingress在对真实清单进行一些调整后,我希望它能够按需要工作:

apiVersion: extensions/v1beta1
kind: Ingress
metadata:
  name: ingress-name
  namespace: my-namespace
  annotations:
    nginx.ingress.kubernetes.io/rewrite-target: /$2
spec:
  rules:
  - http:
      paths:
      - path: /app1(/|$)(.*)
        backend:
          serviceName: service1 
          servicePort: 5000
      - path: /app2(/|$)(.*)
        backend:
          serviceName: service2 
          servicePort: 5000

可能,您还需要在目标 URL 中添加 斜杠,指示 Nginx 引擎正确提供一些静态内容。


推荐阅读