Header manipulation
Set up an external processing (extProc) server that manipulates request headers for a sample app.
This feature is an Enterprise-only feature that requires a Gloo Gateway Enterprise license.
Before you begin
Follow the Get started guide to install Gloo Gateway, set up a gateway resource, and deploy the httpbin sample app.
Get the external address of the gateway and save it in an environment variable.
Enable extProc in Gloo Gateway
You can enable external processing for all routes that the gateway serves by using the Gloo Gateway Settings resource.
- Edit the Gloo Gateway Settings resource and add your extProc settings.
kubectl edit settings default -n gloo-system
- Add the following values under the
spec
section.spec: extProc: allowModeOverride: false failureModeAllow: false filterStage: predicate: After stage: AuthZStage grpcService: extProcServerRef: name: ext-proc-grpc namespace: gloo-system processingMode: requestHeaderMode: SEND responseHeaderMode: SKIP
Setting Description allowModeOverride
Allow the extProc server to override the processing mode settings that you set. Default value is false
.failureModeAllow
Allow the extProc server to continue when an error is detected during external processing. If set to true
, the extProc server continues. If set tofalse
, external processing is stopped and an error is returned to the Envoy proxy.filterStage.predicate
How to apply the filter relative to filterStage.stage
.filterStage.stage
The stage in the filter chain where you want to enable external processing. In this example, external processing is added after the authorization stage. grpcService.extProcServerRef
The name and namespace of the Upstream resource that represents your external processing server. processingMode.requestHeaderMode
Send ( SEND
) or skip sending (SKIP
) request header information to the extProc server.processingMode.responseHeaderMode
Send ( SEND
) or skip sending (SKIP
) response header information to the extProc server.
Deploy an extProc server
Set up the extProc server. This example uses a prebuilt extProc server that manipulates request and response headers based on instructions that are sent in an
instructions
header.kubectl apply -n gloo-system -f- <<EOF apiVersion: apps/v1 kind: Deployment metadata: name: ext-proc-grpc spec: selector: matchLabels: app: ext-proc-grpc replicas: 1 template: metadata: labels: app: ext-proc-grpc spec: containers: - name: ext-proc-grpc image: gcr.io/solo-test-236622/ext-proc-example-basic-sink:0.0.2 imagePullPolicy: IfNotPresent ports: - containerPort: 18080 --- apiVersion: v1 kind: Service metadata: name: ext-proc-grpc labels: app: ext-proc-grpc annotations: gloo.solo.io/h2_service: "true" spec: ports: - port: 4444 targetPort: 18080 protocol: TCP selector: app: ext-proc-grpc EOF
The
instructions
header must be provided as a JSON string in the following format:{ "addHeaders": { "header1": "value1", "header2": "value2" }, "removeHeaders": [ "header3", "header4" ], } }
Verify that the extProc server is up and running.
kubectl get pods -n gloo-system | grep ext-proc-grpc
Create an Upstream resource that represents the extProc server. Note that you must include the
useHttp2: true
setting, because the extProc server requires the HTTP/2 protocol.If you setgloo.discovery.enabled=true
during the Gloo Gateway installation, the Upstream is automatically created for you.kubectl apply -n gloo-system -f- <<EOF apiVersion: gloo.solo.io/v1 kind: Upstream metadata: labels: app: ext-proc-grpc discovered_by: kubernetesplugin name: ext-proc-grpc namespace: gloo-system spec: discoveryMetadata: {} useHttp2: true kube: selector: app: ext-proc-grpc serviceName: ext-proc-grpc serviceNamespace: gloo-system servicePort: 4444 EOF
Verify extProc
Send a simple request to the httpbin app and make sure that you get back a 200 HTTP response code. The following request passes in two headers
header1
andheader2
that you see in your response.Example output:
{ "headers": { "Accept": [ "*/*" ], "Header1": [ "value1" ], "Header2": [ "value2" ], "Host": [ "www.example.com:8080" ], "User-Agent": [ "curl/7.77.0" ], "X-Envoy-Expected-Rq-Timeout-Ms": [ "15000" ], "X-Forwarded-Proto": [ "http" ], "X-Request-Id": [ "5ebe6cb0-24fc-427f-9bb7-8aa47e360c94" ] } }
Send another request to the httpbin app. This time, you pass along instructions for the extProc server in an
instruction
header. In the following example, you use the extProc server to add theheader3
header, and to remove theheader2
header.Example output:
{ "headers": { "Accept": [ "*/*" ], "Header1": [ "value1" ], "Header3": [ "value3" ], "Header4": [ "value4" ], "Host": [ "www.example.com:8080" ], "User-Agent": [ "curl/7.77.0" ], "X-Envoy-Expected-Rq-Timeout-Ms": [ "15000" ], "X-Forwarded-Proto": [ "http" ], "X-Request-Id": [ "a3fd7124-8485-45d5-8326-cf025bc7a01c" ] } }
Overwrite gateway settings with RouteOptions
Create a RouteOption resource that overwrites the gateway-level settings. In this example, you want to skip sending request headers to the extProc server.
kubectl apply -f- <<EOF apiVersion: gateway.solo.io/v1 kind: RouteOption metadata: name: extproc namespace: httpbin spec: options: extProc: overrides: processingMode: requestHeaderMode: SKIP EOF
Create an HTTPRoute resource for the httpbin app that references the RouteOption resource that you created for the
extproc.example
domain.kubectl apply -f- <<EOF apiVersion: gateway.networking.k8s.io/v1beta1 kind: HTTPRoute metadata: name: httpbin-extproc namespace: httpbin spec: parentRefs: - name: http namespace: gloo-system hostnames: - extproc.example rules: - filters: - type: ExtensionRef extensionRef: group: gateway.solo.io kind: RouteOption name: extproc backendRefs: - name: httpbin port: 8000 EOF
Send a request to the httpbin app and pass along instructions for the extProc server in an
instruction
header. Verify that the request header information is not processed because you configured Gloo Gateway to skip sending request headers to the extProc server for that route. For example, theheader2
header is not removed, andheader3
andheader4
are not added. Instead, you get back the instructions in aninstructions
header.Example output:
{ "headers": { "Accept": [ "*/*" ], "Header1": [ "value1" ], "Header2": [ "value2" ], "Host": [ "extproc.example:8080" ], "Instructions": [ "{\"addHeaders\":{\"header3\":\"value3\",\"header4\":\"value4\"},\"removeHeaders\":[\"instructions\", \"header2\"]}" ], "User-Agent": [ "curl/7.77.0" ], "X-Envoy-Expected-Rq-Timeout-Ms": [ "15000" ], "X-Forwarded-Proto": [ "http" ], "X-Request-Id": [ "c896a2ec-2dc2-4f91-8836-5377f2c53e7d" ] } }
Change the RouteOption resource and set
processingMode.requestHeaderMode: SEND
to send request headers for that route.kubectl apply -f- <<EOF apiVersion: gateway.solo.io/v1 kind: RouteOption metadata: name: extproc namespace: httpbin spec: options: extProc: overrides: processingMode: requestHeaderMode: SEND EOF
Send another request to the httpbin app. Verify that your instructions are now processed, and
header3
header is added and theheader2
header is removed.Example output:
{ "headers": { "Accept": [ "*/*" ], "Header1": [ "value1" ], "Header3": [ "value3" ], "Header4": [ "value4" ], "Host": [ "extproc.example:8080" ], "User-Agent": [ "curl/7.77.0" ], "X-Envoy-Expected-Rq-Timeout-Ms": [ "15000" ], "X-Forwarded-Proto": [ "http" ], "X-Request-Id": [ "943e4d99-f6c7-465e-9a25-be760220f7ec" ] } }
Cleanup
Remove the resources that you created in this guide.
kubectl delete httproute httpbin-extproc -n httpbin kubectl delete routeoption extproc -n httpbin kubectl delete upstream ext-proc-grpc -n gloo-system kubectl delete deployment ext-proc-grpc -n gloo-system kubectl delete service ext-proc-grpc -n gloo-system
Edit the Settings resource and remove the extProc settings.
kubectl edit settings default -n gloo-system