contour icon indicating copy to clipboard operation
contour copied to clipboard

HTTPProxy ExternalName mirror 404s despite Host header being set

Open deepy opened this issue 7 months ago • 4 comments

What steps did you take and what happened: I created an ExternalName service which works when mirror: false but does not work when mirror: true

My ExternalName service looks like:

apiVersion: v1
kind: Service
metadata:
  name: external
  annotations:
    projectcontour.io/upstream-protocol.tls: 443,https
spec:
  type: ExternalName
  externalName: external-service.example.com
  ports:
  - name: https
    port: 443
    targetPort: 443

And my HTTPProxy:

apiVersion: projectcontour.io/v1
kind: HTTPProxy
metadata:
  name: proxy
spec:
  ingressClassName: contour
  virtualhost:
    fqdn: my-app.example.com
    tls:
      secretName: tls-secret
  routes:
    - services:
      - name: external
        port: 443
        requestHeadersPolicy:
          set:
            - name: Host
              value: external-service.example.com
        mirror: true
      - name: my-app
        port: 8089

What did you expect to happen: Production traffic to my-app.example.com goes to the in-cluster service my-app:8089 and is also mirrored to external-service.example.com

Anything else you would like to add: With tracing enabled I can see that the mirror is connecting to the right IP, right port, and getting a 404 I'm not seeing the request in the logs on the other side, which makes me suspect the Host header is not working (or maybe something with SNI?)

Environment:

  • Contour version: v1.32.0
  • Kubernetes version: (use kubectl version): v1.31.10-eks-931bdca
  • Kubernetes installer & version: EKS
  • Cloud provider or hardware configuration:
  • OS (e.g. from /etc/os-release):

deepy avatar Aug 13 '25 14:08 deepy

Hey @deepy! Thanks for opening your first issue. We appreciate your contribution and welcome you to our community! We are glad to have you here and to have your input on Contour. You can also join us on our mailing list and in our channel in the Kubernetes Slack Workspace

github-actions[bot] avatar Aug 13 '25 14:08 github-actions[bot]

The Contour project currently lacks enough contributors to adequately respond to all Issues.

This bot triages Issues according to the following rules:

  • After 60d of inactivity, lifecycle/stale is applied
  • After 30d of inactivity since lifecycle/stale was applied, the Issue is closed

You can:

  • Mark this Issue as fresh by commenting
  • Close this Issue
  • Offer to help out with triage

Please send feedback to the #contour channel in the Kubernetes Slack

github-actions[bot] avatar Oct 13 '25 00:10 github-actions[bot]

The Contour project currently lacks enough contributors to adequately respond to all Issues.

This bot triages Issues according to the following rules:

  • After 60d of inactivity, lifecycle/stale is applied
  • After 30d of inactivity since lifecycle/stale was applied, the Issue is closed

You can:

  • Mark this Issue as fresh by commenting
  • Close this Issue
  • Offer to help out with triage

Please send feedback to the #contour channel in the Kubernetes Slack

github-actions[bot] avatar Nov 13 '25 00:11 github-actions[bot]

Sorry for the late reply, you must have already figured this out by now.

I didn't have a change to test it myself before due to lack of time and also I've been improving some tooling to make it easier to run these kind of tests.

From what I can see, the SNI is set correctly in this scenario, but Envoy appends a -shadow suffic to the Host header in the requests sent to the mirror server which could be the reason it was rejected?

https://www.envoyproxy.io/docs/envoy/latest/api-v3/config/route/v3/route_components.proto#config-route-v3-routeaction-requestmirrorpolicy

tsaarni avatar Nov 13 '25 08:11 tsaarni