Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Gateway API HttpRoute with URLRewrite of type: ReplacePrefixMatch ignores other matches conditions like method or headers #6554

Open
1 task done
tporeba opened this issue Oct 21, 2024 · 0 comments
Labels
bug Something isn't working

Comments

@tporeba
Copy link

tporeba commented Oct 21, 2024

Is there an existing issue for this?

  • I have searched the existing issues

Current Behavior

I noticed that Gateway API HTTPRoutes that use URLRewrite filter with type: ReplacePrefixMatch is silently ignoring matches conditions other than path, for example method or headers, maybe others too.

When I change the type of URLRewrite to ReplaceFullPath then everything is OK.
Here is affected config example:

http_route-prefix_rewrite.yml.txt

apiVersion: gateway.networking.k8s.io/v1
kind: HTTPRoute
metadata:
  creationTimestamp: '2024-10-21T10:41:54Z'
  generation: 14
  labels:
    app.kubernetes.io/instance: kong
    app.kubernetes.io/managed-by: Helm
    app.kubernetes.io/name: config
    app.kubernetes.io/version: 1.0.0
    argocd.argoproj.io/instance: kong
    helm.sh/chart: config-6.0.0
  name: kong-config-route
  namespace: kong
  resourceVersion: '49961261'
  uid: 5cc9d3ea-7b36-480d-8f60-1ff6461790e4
spec:
  parentRefs:
    - group: gateway.networking.k8s.io
      kind: Gateway
      name: kong
      namespace: kong
  rules:
    - backendRefs:
        - group: ''
          kind: Service
          name: some-service
          namespace: some-namespace
          port: 8904
          weight: 1
      filters:
        - type: URLRewrite
          urlRewrite:
            path:
              replaceFullPath: /some/path/replacement
              type: ReplaceFullPath
      matches:
        - method: POST
          path:
            type: PathPrefix
            value: /some/path/prefix

and json fragment of configuration dumps from KIC obtained by

curl -sv localhost:10256/debug/config/successful

as described in https://docs.konghq.com/kubernetes-ingress-controller/latest/reference/troubleshooting/#dumping-generated-kong-configuration

dump_prefix_rewrite.json

      {
        "connect_timeout": 60000,
        "host": "httproute.kong.kong-config-route._.0",
        "id": "1638e369-7332-5a42-992c-d5dd48183c8f",
        "name": "httproute.kong.kong-config-route._.0",
        "port": 8904,
        "protocol": "http",
        "read_timeout": 1210000,
        "retries": 5,
        "write_timeout": 1210000,
        "tags": [
          "k8s-name:some-service",
          "k8s-namespace:some-namespace",
          "k8s-kind:Service",
          "k8s-uid:d79a6634-9ce2-4c74-a024-c92348f91b2e",
          "k8s-version:v1"
        ],
        "routes": [
          {
            "expression": "(http.path == \"/some/path/prefix\") || (http.path ~ \"^/some/path/prefix(/.*)\")",
            "id": "398f29d3-3965-5c1b-a37d-4174eebcca3c",
            "name": "httproute.kong.kong-config-route._.0.0",
            "preserve_host": true,
            "priority": 35184510504959,
            "strip_path": false,
            "tags": [
              "k8s-name:kong-config-route",
              "k8s-namespace:kong",
              "k8s-kind:HTTPRoute",
              "k8s-uid:5cc9d3ea-7b36-480d-8f60-1ff6461790e4",
              "k8s-group:gateway.networking.k8s.io",
              "k8s-version:v1"
            ],
            "https_redirect_status_code": 426,
            "plugins": [
              {
                "name": "request-transformer",
                "config": {
                  "add": {
                    "body": [],
                    "headers": [],
                    "querystring": []
                  },
                  "append": {
                    "body": [],
                    "headers": [],
                    "querystring": []
                  },
                  "http_method": null,
                  "remove": {
                    "body": [],
                    "headers": [],
                    "querystring": []
                  },
                  "rename": {
                    "body": [],
                    "headers": [],
                    "querystring": []
                  },
                  "replace": {
                    "body": [],
                    "headers": [],
                    "querystring": [],
                    "uri": "/some/path/prefixReplacement$(uri_captures[1])"
                  }
                },
                "enabled": true,
                "protocols": [
                  "grpc",
                  "grpcs",
                  "http",
                  "https"
                ]
              }
            ]
          }
        ]
      }

Notice, that expression does not contain any condition related to the method match.
Same happens with headers and maybe others too.

Expected Behavior

For comparison see the correct behaviour for URLRewrite type ReplaceFullPath:

The crucial difference is in the expression, where method condition is included, as expected.

"expression": "((http.path == \"/some/path/prefix\") || (http.path ^= \"/some/path/prefix/\")) && (http.method == \"POST\")",

Steps To Reproduce

1. Configure your KIC as described in https://docs.konghq.com/kubernetes-ingress-controller/latest/reference/troubleshooting/#dumping-generated-kong-configuration
2. Install the HTTPRoute from one of objects from attached files to a running cluster with KIC
3. Dump the config of KIC
4. Review the rules and compare the result you get from those two `HTTPRoute` yamls.

You will notice that `(http.method == \"POST\")` condition is not present in one version. 

This can be also confirmed by comparing a `curl -X POST` vs `curl -X GET` on some live configuration - you will see that when `ReplacePrefixMatch` is used, the `GET` requests are also matched by the rule, which is unexpected.

Kong Ingress Controller version

v3.3.1

Kubernetes version

{
  "clientVersion": {
    "major": "1",
    "minor": "29",
    "gitVersion": "v1.29.5",
    "gitCommit": "59755ff595fa4526236b0cc03aa2242d941a5171",
    "gitTreeState": "clean",
    "buildDate": "2024-05-14T10:46:12Z",
    "goVersion": "go1.21.9",
    "compiler": "gc",
    "platform": "linux/amd64"
  },
  "kustomizeVersion": "v5.0.4-0.20230601165947-6ce0bf390ce3",
  "serverVersion": {
    "major": "1",
    "minor": "29",
    "gitVersion": "v1.29.5",
    "gitCommit": "59755ff595fa4526236b0cc03aa2242d941a5171",
    "gitTreeState": "clean",
    "buildDate": "2024-05-14T10:39:39Z",
    "goVersion": "go1.21.9",
    "compiler": "gc",
    "platform": "linux/amd64"
  }
}

Anything else?

No response

@tporeba tporeba added the bug Something isn't working label Oct 21, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working
Projects
None yet
Development

No branches or pull requests

1 participant