Skip to content
If you are interested in trying out Gloo Gateway with the Kubernetes Gateway API, check out Solo Enterprise for kgateway. This version adds enterprise functionality on top of the kgateway open source project.

Inject response headers

Page as Markdown

Use custom Gloo Gateway functions to inject headers into responses.

Before you begin

  1. Follow the Get started guide to install Gloo Gateway, set up a gateway resource, and deploy the httpbin sample app.

  2. Get the external address of the gateway and save it in an environment variable.

    export INGRESS_GW_ADDRESS=$(kubectl get svc -n gloo-system gloo-proxy-http -o jsonpath="{.status.loadBalancer.ingress[0]['hostname','ip']}")
    echo $INGRESS_GW_ADDRESS  
    kubectl port-forward deployment/gloo-proxy-http -n gloo-system 8080:8080

Inject response headers

  1. Create a RouteOption or VirtualHostOption resource with your transformation rules. The following rules are specified:

    • x-solo-response: Use the value from the x-solo-request request header and populate the value of that header into an x-solo-response response header.
    • x-podname: Retrieve the value of the POD_NAME environment variable and add the value to the x-podname response header. Because the transformation is processed in the gateway proxy, these environment variables refer to the variables that are set on the proxy. You can view supported environment variables when you run kubectl get deployment gloo-proxy-http -n gloo-system -o yaml and look at the spec.containers.env section.
    • x-season: Adds a static string value of summer to the x-season response header.
    • x-solo-response-raw: Adds a static string hello value with all escape characters intact.
    • x-replace: Replaces the pattern-to-replace text in the baz header with a random string.
      kubectl apply -f- <<EOF
      apiVersion: gateway.solo.io/v1
      kind: RouteOption
      metadata:
        name: transformation
        namespace: httpbin
      spec:
        targetRefs:
        - group: gateway.networking.k8s.io
          kind: HTTPRoute
          name: httpbin
        options:
          transformations:
            responseTransformation:
              transformationTemplate:
                headers:
                  x-solo-response:
                    text: '{{ request_header("x-solo-request") }}'
                  x-podname:
                     text: '{{ env("POD_NAME") }}'
                  x-season:
                     text: 'summer'
                  x-solo-response-raw:
                    text: '{{ raw_string("hello") }}' # Sets a static value
                  x-replace: 
                    text: '{{ replace_with_random(request_header("baz"), "pattern-to-replace") }}'
      EOF
      kubectl apply -n gloo-system -f- <<EOF
      apiVersion: gateway.solo.io/v1
      kind: VirtualHostOption
      metadata:
        name: transformation
        namespace: gloo-system
      spec:
        options:
          transformations:
            responseTransformation:
              transformationTemplate:
                headers:
                  x-solo-response:
                    text: '{{ request_header("x-solo-request") }}'
                  x-podname:
                     text: '{{ env("POD_NAME") }}'
                  x-season:
                     text: 'summer'
                  x-solo-response-raw:
                    text: '{{ raw_string("hello") }}' # Sets a static value
                  x-replace: 
                    text: '{{ replace_with_random(request_header("baz"), "pattern-to-replace") }}'
        targetRefs:
        - group: gateway.networking.k8s.io
          kind: Gateway
          name: http
          namespace: gloo-system
      EOF
  2. Send a request to the httpbin app and include the x-solo-request request header. Verify that you get back a 200 HTTP response code and that the following response headers are included:

    • x-podname with the name of the gateway proxy pod
    • x-season that is set to summer
    • x-solo-response that is set to the value of the x-solo-request request header.
    • x-solo-response-raw that is set to hello.
    • x-replace that is set to a random string.
      curl -vik http://$INGRESS_GW_ADDRESS:8080/response-headers \
       -H "host: www.example.com:8080" \
       -H "x-solo-request: my custom request header" \
       -H "baz: pattern-to-replace"
      curl -vik localhost:8080/response-headers \
      -H "host: www.example.com" \
      -H "x-solo-request: my custom request header" \
      -H "baz: pattern-to-replace"

    Example output:

    * Mark bundle as not supporting multiuse
    < HTTP/1.1 200 OK
    HTTP/1.1 200 OK
    < access-control-allow-credentials: true
    access-control-allow-credentials: true
    < access-control-allow-origin: *
    access-control-allow-origin: *
    < content-type: application/json; encoding=utf-8
    content-type: application/json; encoding=utf-8
    < date: Wed, 26 Jun 2024 02:54:48 GMT
    date: Wed, 26 Jun 2024 02:54:48 GMT
    < content-length: 3
    content-length: 3
    < x-envoy-upstream-service-time: 2
    x-envoy-upstream-service-time: 2
    < server: envoy
    server: envoy
    < x-envoy-decorator-operation: httpbin.httpbin.svc.cluster.local:8000/*
    x-envoy-decorator-operation: httpbin.httpbin.svc.cluster.local:8000/*
    < x-podname: gloo-proxy-http-844ff8bc4d-dh4pn
    x-podname: gloo-proxy-http-844ff8bc4d-dh4pn
    < x-season: summer
    x-season: summer
    < x-solo-response: my custom request header
    x-solo-response: my custom request header
    < x-solo-response-raw: hello
    x-solo-response-raw: hello
    < x-replace: Fsazjxq8+gpwcx6LlRu3kw
    x-replace: Fsazjxq8+gpwcx6LlRu3kw  

Cleanup

You can remove the resources that you created in this guide.

kubectl delete virtualhostoption transformation -n gloo-system
kubectl delete routeoption transformation -n httpbin