In this guide, you use an Inja function to extract an environment variable value from the gateway proxy pod and add this value to the dynamic metadata filter in Envoy. Then, you inject the value that you stored in the dynamic metadata filter when writing access logs.

Before you begin

  1. Follow the Get started guide to install Gloo Gateway.

  2. Follow the Sample app guide to create a gateway proxy with an HTTP listener and deploy the httpbin sample app.

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

Enrich access logs

  1. Follow the steps to enable access logs on your gateway proxy.

  2. Create a GlooTrafficPolicy with the following transformation rules:

    • The env Inja function is used to extract the POD_NAME environment variable from the gateway proxy pod.
    • The value of the environment variable is added to the pod_name key in the dynamic metadata values.
      kubectl apply -f- <<EOF
    apiVersion: gloo.solo.io/v1alpha1
    kind: GlooTrafficPolicy
    metadata:
      name: transformation
      namespace: httpbin
    spec:
      targetRefs:
      - group: gateway.networking.k8s.io
        kind: HTTPRoute
        name: httpbin
      glooTransformation:
        stages:
          early:
            requests:
            - transformation:
                template:
                  dynamicMetadataValues:
                    - key: 'pod_name'
                      value: '{{ env("POD_NAME") }}'
    EOF
      
  3. Update the HTTPListenerPolicy resource to include the pod_name from the dynamic metadata values.

      kubectl apply -f- <<EOF
    apiVersion: gateway.kgateway.dev/v1alpha1
    kind: HTTPListenerPolicy
    metadata:
      name: access-logs
      namespace: gloo-system
    spec:
      targetRefs:
      - group: gateway.networking.k8s.io
        kind: Gateway
        name: http
      accessLog:
      - fileSink:
          path: /dev/stdout
          jsonFormat:
              start_time: "%START_TIME%"
              method: "%REQ(X-ENVOY-ORIGINAL-METHOD?:METHOD)%"
              path: "%REQ(X-ENVOY-ORIGINAL-PATH?:PATH)%"
              protocol: "%PROTOCOL%"
              response_code: "%RESPONSE_CODE%"
              response_flags: "%RESPONSE_FLAGS%"
              bytes_received: "%BYTES_RECEIVED%"
              bytes_sent: "%BYTES_SENT%"
              total_duration: "%DURATION%"
              resp_backend_service_time: "%RESP(X-ENVOY-UPSTREAM-SERVICE-TIME)%"
              req_x_forwarded_for: "%REQ(X-FORWARDED-FOR)%"
              user_agent: "%REQ(USER-AGENT)%"
              request_id: "%REQ(X-REQUEST-ID)%"
              authority: "%REQ(:AUTHORITY)%"
              backendHost: "%UPSTREAM_HOST%"
              backendCluster: "%UPSTREAM_CLUSTER%"
              pod_name: '%DYNAMIC_METADATA(io.solo.transformation:pod_name)%'
    EOF
      
  4. Send another request to the httpbin app.

  5. Review the access logs and verify that the pod_name is now injected into your access logs.

      kubectl -n gloo-system logs deployments/http | tail -1 | jq --sort-keys
      

    Example output:

      {
      "authority": "www.example.com:8080",
      "bytes_received": 0,
      "bytes_sent": 0,
      "method": "GET",
      "path": "/status/200",
      "pod_name": "http-844ff8bc4d-dh4pn",
      "protocol": "HTTP/1.1",
      "req_x_forwarded_for": null,
      "request_id": "132892e6-085e-400f-98da-c055ca04b714",
      "resp_upstream_service_time": "2",
      "response_code": 200,
      "response_flags": "-",
      "start_time": "2025-05-14T16:43:07.506Z",
      "total_duration": 2,
      "upstreamCluster": "kube-svc_httpbin-httpbin-8000_httpbin_httpbin_httpbin_8000",
      "upstreamHost": "10.0.12.250:8080",
      "user_agent": "curl/8.7.1"
    }
      

Cleanup

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

  kubectl delete glootrafficpolicy transformation -n httpbin
kubectl delete httplistenerpolicy access-logs -n gloo-system