Transformation
Alter a request before matching and routing, such as with an Inja header template.
You might transform the request or response to match a different routing destination based on the transformed content. You can also apply special transformations, such as via Inja templates. With Inja, you can write loops, conditional logic, and other functions to transform requests and responses.
For more information, see the following resources.
- Gloo Mesh Gateway API docs
- The following video that shows how you might use transformation policies with other Gloo policies such as JWT and rate limiting.
Before you begin
This guide assumes that you use the same names for components like clusters, workspaces, and namespaces as in the getting started. If you have different names, make sure to update the sample configuration files in this guide.
- Set up Gloo Mesh Gateway in a single cluster.
- Install Bookinfo and other sample apps.
Configure an HTTP listener on your gateway and set up basic routing for the sample apps.
Configure transformation policies
You can apply a transformation policy at the route level. For more information, see Apply policies.
When you attempt to apply multiple transformation policies, all policies are first sorted ascending by creation time, and then grouped by stage (preAuthz
and postAuthz
). For each stage, only the oldest policy is applied. All subsequent policies are ignored. Note that this behavior applies even if you specify the prioritizedPhase
field in your transformation policy.
Review the following sample configuration files.
Request transformation
The following example is to inject a header with a simple Inja template into a request.
apiVersion: trafficcontrol.policy.gloo.solo.io/v2
kind: TransformationPolicy
metadata:
annotations:
cluster.solo.io/cluster: ""
name: basic-auth
namespace: bookinfo
spec:
applyToRoutes:
- route:
labels:
route: httpbin
config:
request:
injaTemplate:
headers:
foo:
text: bar
Review the following table to understand this configuration. For more information, see the API docs.
Setting | Description |
---|---|
spec.applyToRoutes | Use labels to configure which routes to apply the policy to. This example label matches the app and route from the example route table that you apply separately. If omitted and you do not have another selector such as applyToDestinations , the policy applies to all routes in the workspace. |
config.request | Transform the request before sending to the upstream service. The example adds a foo: bar header. |
Response transformation
The following example is to inject a header with a simple Inja template into a response.
apiVersion: trafficcontrol.policy.gloo.solo.io/v2
kind: TransformationPolicy
metadata:
annotations:
cluster.solo.io/cluster: ""
name: basic-auth
namespace: bookinfo
spec:
applyToRoutes:
- route:
labels:
route: httpbin
config:
response:
injaTemplate:
headers:
foo1:
text: bar1
Review the following table to understand this configuration. For more information, see the API docs.
Setting | Description |
---|---|
spec.applyToRoutes | Use labels to configure which routes to apply the policy to. This example label matches the app and route from the example route table that you apply separately. If omitted and you do not have another selector such as applyToDestinations , the policy applies to all routes in the workspace. |
config.response | Transform the response before returning to the client. The example adds a foo: bar header. |
Replace request and response string with random
You can use a replace_with_random
function in a transformation policy to replace a string in a request and response with a random, unique value per request-response pair in the header, body, or metadata. For example, you might have a request with an ID, nonce, or other sanitized value that shares the value with other requests. You want to replace this value with a new, random value that is unique to the request so that you can build response-specific logic in your app.
- The function is in the format:
replace_with_random(source_string, pattern_to_replace_string)
. - The
pattern_to_replace_string
pattern is an exact match string. - The replaced value is a 128-bit, base64-encoded random number.
Review the following example Inja template.
apiVersion: trafficcontrol.policy.gloo.solo.io/v2
kind: TransformationPolicy
metadata:
annotations:
cluster.solo.io/cluster: ""
name: transformation-one
namespace: bookinfo
spec:
applyToRoutes:
- route:
labels:
route: ratings
config:
phase:
postAuthz:
priority: 10
response:
injaTemplate:
advancedTemplates: false
parseBodyBehavior: DontParse
headers:
baz:
text: '{{ replace_with_random(header("baz"), "pattern-to-replace") }}'
foo:
text: '{{ replace_with_random(header("x-foo"), "another-pattern-to-replace") }}'
body:
text: ' {{ replace_with_random(body(), "pattern-to-replace") }}'
Review the following table to understand this configuration. For more information, see the API docs.
Setting | Description |
---|---|
spec.applyToRoutes | Use labels to configure which routes to apply the policy to. This example label matches the app and route from the example route table that you apply separately. If omitted and you do not have another selector such as applyToDestinations , the policy applies to all routes in the workspace. |
config.phase | Set when to apply the transformation filter in the request chain, either before (preAuthz ) or after (postAuthz ) authorization. You can also set the priority if you have multiple policies in the same phase. The lowest numbered priority is run first. For more information, see Order of applied policies. This example sets postAuthz so that the policy can extract authorization information such as an external auth ID or JWT token. |
config.response.injaTemplate | The Inja template with header and body rules to use to transform data in the response that is received from the upstream service before returning the response to the client. To configure an Inja template to transform data before sending a request to an upstream, you can use config.request.injaTemplate . |
advancedTemplates: false | Set to false to use simple naming and dot notation (such as time.start ) for the extraction rules in the template. For more information, see the Envoy transformation proto. |
parseBodyBehavior: DontParse | Set to DontParse to treat the response and request bodies as plain text, not JSON (ParseAsJson ). |
headers | Configure the replacement rules for request headers. The example replaces the pattern-to-replace pattern in the baz header and the another-pattern-to-replace pattern in the x-foo header. |
body | Configure the replacement rules for the request body. The example replaces the pattern-to-replace pattern anywhere in the request body. The replacement value for the pattern-to-replace pattern in the body is the same as the replacement value in the baz header because the patterns match. However, the replacement value for the body differs from the foo header because the patterns do not match. |
Verify transformation policies
Want to check the validity of your Inja transformations before applying the policy to your cluster? Check out the meshctl x validate resources
CLI command, which lets you specify an Istio or Envoy version to verify the Envoy filters that the transformation policy is translated into. For example, a command such as meshctl x validate resources mypolicy.yaml --istio-version=1.22.5-patch0 --input-snapshot input.json --output-snapshot output.json
checks the Envoy configuration that your transformation policy translates into, in the context of your Gloo environment. For more information and examples, see the command reference and the resource validation overview.
Apply the example transformation policy in the workload cluster.
kubectl apply -f transformation-policy.yaml
Send a request to the
httpbin
app through the ingress gateway.- HTTP:
curl -vik --resolve www.example.com:80:${INGRESS_GW_IP} http://www.example.com:80/status/200 -H "X-httpbin: true"
- HTTPS:
curl -vik --resolve www.example.com:443:${INGRESS_GW_IP} https://www.example.com:443/status/200 -H "X-httpbin: true"
- HTTP:
Verify that you notice the transformed request and response headers.
Cleanup
You can optionally remove the resources that you set up as part of this guide.
kubectl -n bookinfo delete transformationpolicy basic-auth