diff --git a/api/v1alpha1/accesslogging_types.go b/api/v1alpha1/accesslogging_types.go
index edc19e97599..31eac69f122 100644
--- a/api/v1alpha1/accesslogging_types.go
+++ b/api/v1alpha1/accesslogging_types.go
@@ -37,7 +37,6 @@ type ProxyAccessLogSetting struct {
// If type is defined, the accesslog settings would apply to the relevant component (as-is).
// +kubebuilder:validation:Enum=Listener;Route
// +optional
- // +notImplementedHide
Type *ProxyAccessLogType `json:"type,omitempty"`
}
diff --git a/internal/gatewayapi/listener.go b/internal/gatewayapi/listener.go
index 0c69d7b3097..5c85e561ea1 100644
--- a/internal/gatewayapi/listener.go
+++ b/internal/gatewayapi/listener.go
@@ -241,7 +241,6 @@ func (t *Translator) processAccessLog(envoyproxy *egv1a1.EnvoyProxy, resources *
},
}, nil
}
-
if envoyproxy.Spec.Telemetry.AccessLog.Disable {
return nil, nil
}
@@ -249,6 +248,16 @@ func (t *Translator) processAccessLog(envoyproxy *egv1a1.EnvoyProxy, resources *
irAccessLog := &ir.AccessLog{}
// translate the access log configuration to the IR
for i, accessLog := range envoyproxy.Spec.Telemetry.AccessLog.Settings {
+ var accessLogType *ir.ProxyAccessLogType
+ if accessLog.Type != nil {
+ switch *accessLog.Type {
+ case egv1a1.ProxyAccessLogTypeRoute:
+ accessLogType = ptr.To(ir.ProxyAccessLogTypeRoute)
+ case egv1a1.ProxyAccessLogTypeListener:
+ accessLogType = ptr.To(ir.ProxyAccessLogTypeListener)
+ }
+ }
+
var format egv1a1.ProxyAccessLogFormat
if accessLog.Format != nil {
format = *accessLog.Format
@@ -274,6 +283,16 @@ func (t *Translator) processAccessLog(envoyproxy *egv1a1.EnvoyProxy, resources *
return nil, utilerrors.NewAggregate(errs)
}
+ if len(accessLog.Sinks) == 0 {
+ al := &ir.TextAccessLog{
+ Format: format.Text,
+ CELMatches: validExprs,
+ LogType: accessLogType,
+ Path: "/dev/stdout",
+ }
+ irAccessLog.Text = append(irAccessLog.Text, al)
+ }
+
for j, sink := range accessLog.Sinks {
switch sink.Type {
case egv1a1.ProxyAccessLogSinkTypeFile:
@@ -287,6 +306,7 @@ func (t *Translator) processAccessLog(envoyproxy *egv1a1.EnvoyProxy, resources *
Format: format.Text,
Path: sink.File.Path,
CELMatches: validExprs,
+ LogType: accessLogType,
}
irAccessLog.Text = append(irAccessLog.Text, al)
case egv1a1.ProxyAccessLogFormatTypeJSON:
@@ -299,6 +319,7 @@ func (t *Translator) processAccessLog(envoyproxy *egv1a1.EnvoyProxy, resources *
JSON: format.JSON,
Path: sink.File.Path,
CELMatches: validExprs,
+ LogType: accessLogType,
}
irAccessLog.JSON = append(irAccessLog.JSON, al)
}
@@ -329,6 +350,7 @@ func (t *Translator) processAccessLog(envoyproxy *egv1a1.EnvoyProxy, resources *
Traffic: traffic,
Type: sink.ALS.Type,
CELMatches: validExprs,
+ LogType: accessLogType,
}
if al.Type == egv1a1.ALSEnvoyProxyAccessLogTypeHTTP && sink.ALS.HTTP != nil {
@@ -339,7 +361,6 @@ func (t *Translator) processAccessLog(envoyproxy *egv1a1.EnvoyProxy, resources *
}
al.HTTP = http
}
-
switch format.Type {
case egv1a1.ProxyAccessLogFormatTypeJSON:
al.Attributes = format.JSON
@@ -367,6 +388,7 @@ func (t *Translator) processAccessLog(envoyproxy *egv1a1.EnvoyProxy, resources *
Settings: ds,
},
Traffic: traffic,
+ LogType: accessLogType,
}
if len(ds) == 0 {
@@ -391,7 +413,6 @@ func (t *Translator) processAccessLog(envoyproxy *egv1a1.EnvoyProxy, resources *
}
}
}
-
return irAccessLog, nil
}
diff --git a/internal/gatewayapi/testdata/envoyproxy-accesslog-types.in.yaml b/internal/gatewayapi/testdata/envoyproxy-accesslog-types.in.yaml
new file mode 100644
index 00000000000..03977e33075
--- /dev/null
+++ b/internal/gatewayapi/testdata/envoyproxy-accesslog-types.in.yaml
@@ -0,0 +1,236 @@
+envoyProxyForGatewayClass:
+ apiVersion: gateway.envoyproxy.io/v1alpha1
+ kind: EnvoyProxy
+ metadata:
+ namespace: envoy-gateway-system
+ name: test
+ spec:
+ telemetry:
+ accessLog:
+ settings:
+ - type: Route
+ - type: Listener
+ - type: Route
+ format:
+ type: Text
+ text: |
+ this is a route log
+ sinks:
+ - type: File
+ file:
+ path: /dev/stdout
+ - type: ALS
+ als:
+ logName: accesslog
+ backendRefs:
+ - name: envoy-als
+ namespace: monitoring
+ port: 9000
+ http:
+ requestHeaders:
+ - x-client-ip-address
+ responseHeaders:
+ - cache-control
+ responseTrailers:
+ - expires
+ type: HTTP
+ - type: ALS
+ als:
+ backendRefs:
+ - name: envoy-als
+ namespace: monitoring
+ port: 9000
+ type: TCP
+ - type: OpenTelemetry
+ openTelemetry:
+ host: otel-collector.monitoring.svc.cluster.local
+ port: 4317
+ resources:
+ k8s.cluster.name: "cluster-1"
+ - type: Listener
+ format:
+ type: Text
+ text: |
+ this is a listener log
+ sinks:
+ - type: File
+ file:
+ path: /dev/stdout
+ - type: ALS
+ als:
+ logName: accesslog
+ backendRefs:
+ - name: envoy-als
+ namespace: monitoring
+ port: 9000
+ http:
+ requestHeaders:
+ - x-client-ip-address
+ responseHeaders:
+ - cache-control
+ responseTrailers:
+ - expires
+ type: HTTP
+ - type: ALS
+ als:
+ backendRefs:
+ - name: envoy-als
+ namespace: monitoring
+ port: 9000
+ type: TCP
+ - type: OpenTelemetry
+ openTelemetry:
+ host: otel-collector.monitoring.svc.cluster.local
+ port: 4317
+ resources:
+ k8s.cluster.name: "cluster-1"
+ - format:
+ type: Text
+ text: |
+ this is a Global log
+ sinks:
+ - type: File
+ file:
+ path: /dev/stdout
+ - type: ALS
+ als:
+ logName: accesslog
+ backendRefs:
+ - name: envoy-als
+ namespace: monitoring
+ port: 9000
+ http:
+ requestHeaders:
+ - x-client-ip-address
+ responseHeaders:
+ - cache-control
+ responseTrailers:
+ - expires
+ type: HTTP
+ - type: ALS
+ als:
+ backendRefs:
+ - name: envoy-als
+ namespace: monitoring
+ port: 9000
+ type: TCP
+ - type: OpenTelemetry
+ openTelemetry:
+ host: otel-collector.monitoring.svc.cluster.local
+ port: 4317
+ resources:
+ k8s.cluster.name: "cluster-1"
+ provider:
+ type: Kubernetes
+ kubernetes:
+ envoyService:
+ type: LoadBalancer
+ envoyDeployment:
+ replicas: 2
+ container:
+ env:
+ - name: env_a
+ value: env_a_value
+ - name: env_b
+ value: env_b_name
+ image: "envoyproxy/envoy:distroless-dev"
+ resources:
+ requests:
+ cpu: 100m
+ memory: 512Mi
+ securityContext:
+ runAsUser: 2000
+ allowPrivilegeEscalation: false
+ pod:
+ annotations:
+ key1: val1
+ key2: val2
+ affinity:
+ nodeAffinity:
+ requiredDuringSchedulingIgnoredDuringExecution:
+ nodeSelectorTerms:
+ - matchExpressions:
+ - key: cloud.google.com/gke-nodepool
+ operator: In
+ values:
+ - router-node
+ tolerations:
+ - effect: NoSchedule
+ key: node-type
+ operator: Exists
+ value: "router"
+ securityContext:
+ runAsUser: 1000
+ runAsGroup: 3000
+ fsGroup: 2000
+ fsGroupChangePolicy: "OnRootMismatch"
+ volumes:
+ - name: certs
+ secret:
+ secretName: envoy-cert
+gateways:
+- apiVersion: gateway.networking.k8s.io/v1
+ kind: Gateway
+ metadata:
+ namespace: envoy-gateway
+ name: gateway-1
+ spec:
+ gatewayClassName: envoy-gateway-class
+ listeners:
+ - name: http
+ protocol: HTTP
+ port: 80
+ allowedRoutes:
+ namespaces:
+ from: Same
+httpRoutes:
+- apiVersion: gateway.networking.k8s.io/v1
+ kind: HTTPRoute
+ metadata:
+ namespace: envoy-gateway
+ name: httproute-1
+ spec:
+ parentRefs:
+ - namespace: envoy-gateway
+ name: gateway-1
+ rules:
+ - matches:
+ - path:
+ type: Exact
+ value: "/exact"
+ backendRefs:
+ - name: service-1
+ port: 8080
+services:
+- apiVersion: v1
+ kind: Service
+ metadata:
+ name: envoy-als
+ namespace: monitoring
+ spec:
+ type: ClusterIP
+ ports:
+ - name: grpc
+ port: 9000
+ appProtocol: grpc
+ protocol: TCP
+ targetPort: 9000
+endpointSlices:
+- apiVersion: discovery.k8s.io/v1
+ kind: EndpointSlice
+ metadata:
+ name: endpointslice-envoy-als
+ namespace: monitoring
+ labels:
+ kubernetes.io/service-name: envoy-als
+ addressType: IPv4
+ ports:
+ - name: grpc
+ protocol: TCP
+ appProtocol: grpc
+ port: 9090
+ endpoints:
+ - addresses:
+ - "10.240.0.10"
+ conditions:
+ ready: true
diff --git a/internal/gatewayapi/testdata/envoyproxy-accesslog-types.out.yaml b/internal/gatewayapi/testdata/envoyproxy-accesslog-types.out.yaml
new file mode 100644
index 00000000000..9c2c0d1cf82
--- /dev/null
+++ b/internal/gatewayapi/testdata/envoyproxy-accesslog-types.out.yaml
@@ -0,0 +1,460 @@
+gateways:
+- apiVersion: gateway.networking.k8s.io/v1
+ kind: Gateway
+ metadata:
+ creationTimestamp: null
+ name: gateway-1
+ namespace: envoy-gateway
+ spec:
+ gatewayClassName: envoy-gateway-class
+ listeners:
+ - allowedRoutes:
+ namespaces:
+ from: Same
+ name: http
+ port: 80
+ protocol: HTTP
+ status:
+ listeners:
+ - attachedRoutes: 1
+ conditions:
+ - lastTransitionTime: null
+ message: Sending translated listener configuration to the data plane
+ reason: Programmed
+ status: "True"
+ type: Programmed
+ - lastTransitionTime: null
+ message: Listener has been successfully translated
+ reason: Accepted
+ status: "True"
+ type: Accepted
+ - lastTransitionTime: null
+ message: Listener references have been resolved
+ reason: ResolvedRefs
+ status: "True"
+ type: ResolvedRefs
+ name: http
+ supportedKinds:
+ - group: gateway.networking.k8s.io
+ kind: HTTPRoute
+ - group: gateway.networking.k8s.io
+ kind: GRPCRoute
+httpRoutes:
+- apiVersion: gateway.networking.k8s.io/v1
+ kind: HTTPRoute
+ metadata:
+ creationTimestamp: null
+ name: httproute-1
+ namespace: envoy-gateway
+ spec:
+ parentRefs:
+ - name: gateway-1
+ namespace: envoy-gateway
+ rules:
+ - backendRefs:
+ - name: service-1
+ port: 8080
+ matches:
+ - path:
+ type: Exact
+ value: /exact
+ status:
+ parents:
+ - conditions:
+ - lastTransitionTime: null
+ message: Route is accepted
+ reason: Accepted
+ status: "True"
+ type: Accepted
+ - lastTransitionTime: null
+ message: Service envoy-gateway/service-1 not found
+ reason: BackendNotFound
+ status: "False"
+ type: ResolvedRefs
+ controllerName: gateway.envoyproxy.io/gatewayclass-controller
+ parentRef:
+ name: gateway-1
+ namespace: envoy-gateway
+infraIR:
+ envoy-gateway/gateway-1:
+ proxy:
+ config:
+ apiVersion: gateway.envoyproxy.io/v1alpha1
+ kind: EnvoyProxy
+ metadata:
+ creationTimestamp: null
+ name: test
+ namespace: envoy-gateway-system
+ spec:
+ logging: {}
+ provider:
+ kubernetes:
+ envoyDeployment:
+ container:
+ env:
+ - name: env_a
+ value: env_a_value
+ - name: env_b
+ value: env_b_name
+ image: envoyproxy/envoy:distroless-dev
+ resources:
+ requests:
+ cpu: 100m
+ memory: 512Mi
+ securityContext:
+ allowPrivilegeEscalation: false
+ runAsUser: 2000
+ pod:
+ affinity:
+ nodeAffinity:
+ requiredDuringSchedulingIgnoredDuringExecution:
+ nodeSelectorTerms:
+ - matchExpressions:
+ - key: cloud.google.com/gke-nodepool
+ operator: In
+ values:
+ - router-node
+ annotations:
+ key1: val1
+ key2: val2
+ securityContext:
+ fsGroup: 2000
+ fsGroupChangePolicy: OnRootMismatch
+ runAsGroup: 3000
+ runAsUser: 1000
+ tolerations:
+ - effect: NoSchedule
+ key: node-type
+ operator: Exists
+ value: router
+ volumes:
+ - name: certs
+ secret:
+ secretName: envoy-cert
+ replicas: 2
+ envoyService:
+ type: LoadBalancer
+ type: Kubernetes
+ telemetry:
+ accessLog:
+ settings:
+ - sinks: null
+ type: Route
+ - sinks: null
+ type: Listener
+ - format:
+ text: |
+ this is a route log
+ type: Text
+ sinks:
+ - file:
+ path: /dev/stdout
+ type: File
+ - als:
+ backendRefs:
+ - name: envoy-als
+ namespace: monitoring
+ port: 9000
+ http:
+ requestHeaders:
+ - x-client-ip-address
+ responseHeaders:
+ - cache-control
+ responseTrailers:
+ - expires
+ logName: accesslog
+ type: HTTP
+ type: ALS
+ - als:
+ backendRefs:
+ - name: envoy-als
+ namespace: monitoring
+ port: 9000
+ type: TCP
+ type: ALS
+ - openTelemetry:
+ host: otel-collector.monitoring.svc.cluster.local
+ port: 4317
+ resources:
+ k8s.cluster.name: cluster-1
+ type: OpenTelemetry
+ type: Route
+ - format:
+ text: |
+ this is a listener log
+ type: Text
+ sinks:
+ - file:
+ path: /dev/stdout
+ type: File
+ - als:
+ backendRefs:
+ - name: envoy-als
+ namespace: monitoring
+ port: 9000
+ http:
+ requestHeaders:
+ - x-client-ip-address
+ responseHeaders:
+ - cache-control
+ responseTrailers:
+ - expires
+ logName: accesslog
+ type: HTTP
+ type: ALS
+ - als:
+ backendRefs:
+ - name: envoy-als
+ namespace: monitoring
+ port: 9000
+ type: TCP
+ type: ALS
+ - openTelemetry:
+ host: otel-collector.monitoring.svc.cluster.local
+ port: 4317
+ resources:
+ k8s.cluster.name: cluster-1
+ type: OpenTelemetry
+ type: Listener
+ - format:
+ text: |
+ this is a Global log
+ type: Text
+ sinks:
+ - file:
+ path: /dev/stdout
+ type: File
+ - als:
+ backendRefs:
+ - name: envoy-als
+ namespace: monitoring
+ port: 9000
+ http:
+ requestHeaders:
+ - x-client-ip-address
+ responseHeaders:
+ - cache-control
+ responseTrailers:
+ - expires
+ logName: accesslog
+ type: HTTP
+ type: ALS
+ - als:
+ backendRefs:
+ - name: envoy-als
+ namespace: monitoring
+ port: 9000
+ type: TCP
+ type: ALS
+ - openTelemetry:
+ host: otel-collector.monitoring.svc.cluster.local
+ port: 4317
+ resources:
+ k8s.cluster.name: cluster-1
+ type: OpenTelemetry
+ status: {}
+ listeners:
+ - address: null
+ name: envoy-gateway/gateway-1/http
+ ports:
+ - containerPort: 10080
+ name: http-80
+ protocol: HTTP
+ servicePort: 80
+ metadata:
+ labels:
+ gateway.envoyproxy.io/owning-gateway-name: gateway-1
+ gateway.envoyproxy.io/owning-gateway-namespace: envoy-gateway
+ name: envoy-gateway/gateway-1
+xdsIR:
+ envoy-gateway/gateway-1:
+ accessLog:
+ als:
+ - destination:
+ name: accesslog_als_2_1
+ settings:
+ - addressType: IP
+ endpoints:
+ - host: 10.240.0.10
+ port: 9090
+ protocol: GRPC
+ http:
+ requestHeaders:
+ - x-client-ip-address
+ responseHeaders:
+ - cache-control
+ responseTrailers:
+ - expires
+ logType: Route
+ name: accesslog
+ text: |
+ this is a route log
+ type: HTTP
+ - destination:
+ name: accesslog_als_2_2
+ settings:
+ - addressType: IP
+ endpoints:
+ - host: 10.240.0.10
+ port: 9090
+ protocol: GRPC
+ logType: Route
+ name: envoy-gateway-system/test
+ text: |
+ this is a route log
+ type: TCP
+ - destination:
+ name: accesslog_als_3_1
+ settings:
+ - addressType: IP
+ endpoints:
+ - host: 10.240.0.10
+ port: 9090
+ protocol: GRPC
+ http:
+ requestHeaders:
+ - x-client-ip-address
+ responseHeaders:
+ - cache-control
+ responseTrailers:
+ - expires
+ logType: Listener
+ name: accesslog
+ text: |
+ this is a listener log
+ type: HTTP
+ - destination:
+ name: accesslog_als_3_2
+ settings:
+ - addressType: IP
+ endpoints:
+ - host: 10.240.0.10
+ port: 9090
+ protocol: GRPC
+ logType: Listener
+ name: envoy-gateway-system/test
+ text: |
+ this is a listener log
+ type: TCP
+ - destination:
+ name: accesslog_als_4_1
+ settings:
+ - addressType: IP
+ endpoints:
+ - host: 10.240.0.10
+ port: 9090
+ protocol: GRPC
+ http:
+ requestHeaders:
+ - x-client-ip-address
+ responseHeaders:
+ - cache-control
+ responseTrailers:
+ - expires
+ name: accesslog
+ text: |
+ this is a Global log
+ type: HTTP
+ - destination:
+ name: accesslog_als_4_2
+ settings:
+ - addressType: IP
+ endpoints:
+ - host: 10.240.0.10
+ port: 9090
+ protocol: GRPC
+ name: envoy-gateway-system/test
+ text: |
+ this is a Global log
+ type: TCP
+ openTelemetry:
+ - authority: otel-collector.monitoring.svc.cluster.local
+ destination:
+ name: accesslog_otel_2_3
+ settings:
+ - endpoints:
+ - host: otel-collector.monitoring.svc.cluster.local
+ port: 4317
+ protocol: GRPC
+ weight: 1
+ logType: Route
+ resources:
+ k8s.cluster.name: cluster-1
+ text: |
+ this is a route log
+ - authority: otel-collector.monitoring.svc.cluster.local
+ destination:
+ name: accesslog_otel_3_3
+ settings:
+ - endpoints:
+ - host: otel-collector.monitoring.svc.cluster.local
+ port: 4317
+ protocol: GRPC
+ weight: 1
+ logType: Listener
+ resources:
+ k8s.cluster.name: cluster-1
+ text: |
+ this is a listener log
+ - authority: otel-collector.monitoring.svc.cluster.local
+ destination:
+ name: accesslog_otel_4_3
+ settings:
+ - endpoints:
+ - host: otel-collector.monitoring.svc.cluster.local
+ port: 4317
+ protocol: GRPC
+ weight: 1
+ resources:
+ k8s.cluster.name: cluster-1
+ text: |
+ this is a Global log
+ text:
+ - logType: Route
+ path: /dev/stdout
+ - logType: Listener
+ path: /dev/stdout
+ - format: |
+ this is a route log
+ logType: Route
+ path: /dev/stdout
+ - format: |
+ this is a listener log
+ logType: Listener
+ path: /dev/stdout
+ - format: |
+ this is a Global log
+ path: /dev/stdout
+ http:
+ - address: 0.0.0.0
+ hostnames:
+ - '*'
+ isHTTP2: false
+ metadata:
+ kind: Gateway
+ name: gateway-1
+ namespace: envoy-gateway
+ sectionName: http
+ name: envoy-gateway/gateway-1/http
+ path:
+ escapedSlashesAction: UnescapeAndRedirect
+ mergeSlashes: true
+ port: 10080
+ routes:
+ - destination:
+ name: httproute/envoy-gateway/httproute-1/rule/0
+ settings:
+ - weight: 1
+ directResponse:
+ statusCode: 500
+ hostname: '*'
+ isHTTP2: false
+ metadata:
+ kind: HTTPRoute
+ name: httproute-1
+ namespace: envoy-gateway
+ name: httproute/envoy-gateway/httproute-1/rule/0/match/0/*
+ pathMatch:
+ distinct: false
+ exact: /exact
+ name: ""
diff --git a/internal/ir/xds.go b/internal/ir/xds.go
index 40e7da917f3..53eb34fa2a6 100644
--- a/internal/ir/xds.go
+++ b/internal/ir/xds.go
@@ -1739,6 +1739,13 @@ type RateLimitValue struct {
Unit RateLimitUnit `json:"unit" yaml:"unit"`
}
+type ProxyAccessLogType egv1a1.ProxyAccessLogType
+
+const (
+ ProxyAccessLogTypeRoute = ProxyAccessLogType(egv1a1.ProxyAccessLogTypeRoute)
+ ProxyAccessLogTypeListener = ProxyAccessLogType(egv1a1.ProxyAccessLogTypeListener)
+)
+
// AccessLog holds the access logging configuration.
// +k8s:deepcopy-gen=true
type AccessLog struct {
@@ -1751,17 +1758,19 @@ type AccessLog struct {
// TextAccessLog holds the configuration for text access logging.
// +k8s:deepcopy-gen=true
type TextAccessLog struct {
- CELMatches []string `json:"celMatches,omitempty" yaml:"celMatches,omitempty"`
- Format *string `json:"format,omitempty" yaml:"format,omitempty"`
- Path string `json:"path" yaml:"path"`
+ CELMatches []string `json:"celMatches,omitempty" yaml:"celMatches,omitempty"`
+ Format *string `json:"format,omitempty" yaml:"format,omitempty"`
+ Path string `json:"path" yaml:"path"`
+ LogType *ProxyAccessLogType `json:"logType,omitempty" yaml:"logType,omitempty"`
}
// JSONAccessLog holds the configuration for JSON access logging.
// +k8s:deepcopy-gen=true
type JSONAccessLog struct {
- CELMatches []string `json:"celMatches,omitempty" yaml:"celMatches,omitempty"`
- JSON map[string]string `json:"json,omitempty" yaml:"json,omitempty"`
- Path string `json:"path" yaml:"path"`
+ CELMatches []string `json:"celMatches,omitempty" yaml:"celMatches,omitempty"`
+ JSON map[string]string `json:"json,omitempty" yaml:"json,omitempty"`
+ Path string `json:"path" yaml:"path"`
+ LogType *ProxyAccessLogType `json:"logType,omitempty" yaml:"logType,omitempty"`
}
// ALSAccessLog holds the configuration for gRPC ALS access logging.
@@ -1775,6 +1784,7 @@ type ALSAccessLog struct {
Text *string `json:"text,omitempty" yaml:"text,omitempty"`
Attributes map[string]string `json:"attributes,omitempty" yaml:"attributes,omitempty"`
HTTP *ALSAccessLogHTTP `json:"http,omitempty" yaml:"http,omitempty"`
+ LogType *ProxyAccessLogType `json:"logType,omitempty" yaml:"logType,omitempty"`
}
// ALSAccessLogHTTP holds the configuration for HTTP ALS access logging.
@@ -1788,13 +1798,14 @@ type ALSAccessLogHTTP struct {
// OpenTelemetryAccessLog holds the configuration for OpenTelemetry access logging.
// +k8s:deepcopy-gen=true
type OpenTelemetryAccessLog struct {
- CELMatches []string `json:"celMatches,omitempty" yaml:"celMatches,omitempty"`
- Authority string `json:"authority,omitempty" yaml:"authority,omitempty"`
- Text *string `json:"text,omitempty" yaml:"text,omitempty"`
- Attributes map[string]string `json:"attributes,omitempty" yaml:"attributes,omitempty"`
- Resources map[string]string `json:"resources,omitempty" yaml:"resources,omitempty"`
- Destination RouteDestination `json:"destination,omitempty" yaml:"destination,omitempty"`
- Traffic *TrafficFeatures `json:"traffic,omitempty" yaml:"traffic,omitempty"`
+ CELMatches []string `json:"celMatches,omitempty" yaml:"celMatches,omitempty"`
+ Authority string `json:"authority,omitempty" yaml:"authority,omitempty"`
+ Text *string `json:"text,omitempty" yaml:"text,omitempty"`
+ Attributes map[string]string `json:"attributes,omitempty" yaml:"attributes,omitempty"`
+ Resources map[string]string `json:"resources,omitempty" yaml:"resources,omitempty"`
+ Destination RouteDestination `json:"destination,omitempty" yaml:"destination,omitempty"`
+ Traffic *TrafficFeatures `json:"traffic,omitempty" yaml:"traffic,omitempty"`
+ LogType *ProxyAccessLogType `json:"logType,omitempty" yaml:"logType,omitempty"`
}
// EnvoyPatchPolicy defines the intermediate representation of the EnvoyPatchPolicy resource.
diff --git a/internal/ir/zz_generated.deepcopy.go b/internal/ir/zz_generated.deepcopy.go
index 4400b555dd7..1a0185bbb9f 100644
--- a/internal/ir/zz_generated.deepcopy.go
+++ b/internal/ir/zz_generated.deepcopy.go
@@ -47,6 +47,11 @@ func (in *ALSAccessLog) DeepCopyInto(out *ALSAccessLog) {
*out = new(ALSAccessLogHTTP)
(*in).DeepCopyInto(*out)
}
+ if in.LogType != nil {
+ in, out := &in.LogType, &out.LogType
+ *out = new(ProxyAccessLogType)
+ **out = **in
+ }
}
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ALSAccessLog.
@@ -1690,6 +1695,11 @@ func (in *JSONAccessLog) DeepCopyInto(out *JSONAccessLog) {
(*out)[key] = val
}
}
+ if in.LogType != nil {
+ in, out := &in.LogType, &out.LogType
+ *out = new(ProxyAccessLogType)
+ **out = **in
+ }
}
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new JSONAccessLog.
@@ -1976,6 +1986,11 @@ func (in *OpenTelemetryAccessLog) DeepCopyInto(out *OpenTelemetryAccessLog) {
*out = new(TrafficFeatures)
(*in).DeepCopyInto(*out)
}
+ if in.LogType != nil {
+ in, out := &in.LogType, &out.LogType
+ *out = new(ProxyAccessLogType)
+ **out = **in
+ }
}
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new OpenTelemetryAccessLog.
@@ -2985,6 +3000,11 @@ func (in *TextAccessLog) DeepCopyInto(out *TextAccessLog) {
*out = new(string)
**out = **in
}
+ if in.LogType != nil {
+ in, out := &in.LogType, &out.LogType
+ *out = new(ProxyAccessLogType)
+ **out = **in
+ }
}
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new TextAccessLog.
diff --git a/internal/xds/translator/accesslog.go b/internal/xds/translator/accesslog.go
index 8acb6e4b005..6660ba8fab6 100644
--- a/internal/xds/translator/accesslog.go
+++ b/internal/xds/translator/accesslog.go
@@ -90,15 +90,24 @@ var (
}
)
-func buildXdsAccessLog(al *ir.AccessLog, forListener bool) []*accesslog.AccessLog {
+func buildXdsAccessLog(al *ir.AccessLog, accessLogType ir.ProxyAccessLogType) []*accesslog.AccessLog {
if al == nil {
return nil
}
totalLen := len(al.Text) + len(al.JSON) + len(al.OpenTelemetry)
accessLogs := make([]*accesslog.AccessLog, 0, totalLen)
+
// handle text file access logs
for _, text := range al.Text {
+ // Filter out logs that are not Global or match the desired access log type
+ if !(text.LogType == nil || *text.LogType == accessLogType) {
+ continue
+ }
+
+ // NR is only added to listener logs originating from a global log configuration
+ defaultLogTypeForListener := accessLogType == ir.ProxyAccessLogTypeListener && text.LogType == nil
+
filelog := &fileaccesslog.FileAccessLog{
Path: text.Path,
}
@@ -131,11 +140,19 @@ func buildXdsAccessLog(al *ir.AccessLog, forListener bool) []*accesslog.AccessLo
ConfigType: &accesslog.AccessLog_TypedConfig{
TypedConfig: accesslogAny,
},
- Filter: buildAccessLogFilter(text.CELMatches, forListener),
+ Filter: buildAccessLogFilter(text.CELMatches, defaultLogTypeForListener),
})
}
// handle json file access logs
for _, json := range al.JSON {
+ // Filter out logs that are not Global or match the desired access log type
+ if !(json.LogType == nil || *json.LogType == accessLogType) {
+ continue
+ }
+
+ // NR is only added to listener logs originating from a global log configuration
+ defaultLogTypeForListener := accessLogType == ir.ProxyAccessLogTypeListener && json.LogType == nil
+
jsonFormat := &structpb.Struct{
Fields: make(map[string]*structpb.Value, len(json.JSON)),
}
@@ -174,11 +191,19 @@ func buildXdsAccessLog(al *ir.AccessLog, forListener bool) []*accesslog.AccessLo
ConfigType: &accesslog.AccessLog_TypedConfig{
TypedConfig: accesslogAny,
},
- Filter: buildAccessLogFilter(json.CELMatches, forListener),
+ Filter: buildAccessLogFilter(json.CELMatches, defaultLogTypeForListener),
})
}
// handle ALS access logs
for _, als := range al.ALS {
+ // Filter out logs that are not Global or match the desired access log type
+ if !(als.LogType == nil || *als.LogType == accessLogType) {
+ continue
+ }
+
+ // NR is only added to listener logs originating from a global log configuration
+ defaultLogTypeForListener := accessLogType == ir.ProxyAccessLogTypeListener && als.LogType == nil
+
cc := &grpcaccesslog.CommonGrpcAccessLogConfig{
LogName: als.LogName,
GrpcService: &cfgcore.GrpcService{
@@ -209,7 +234,7 @@ func buildXdsAccessLog(al *ir.AccessLog, forListener bool) []*accesslog.AccessLo
ConfigType: &accesslog.AccessLog_TypedConfig{
TypedConfig: accesslogAny,
},
- Filter: buildAccessLogFilter(als.CELMatches, forListener),
+ Filter: buildAccessLogFilter(als.CELMatches, defaultLogTypeForListener),
})
case egv1a1.ALSEnvoyProxyAccessLogTypeTCP:
alCfg := &grpcaccesslog.TcpGrpcAccessLogConfig{
@@ -222,12 +247,20 @@ func buildXdsAccessLog(al *ir.AccessLog, forListener bool) []*accesslog.AccessLo
ConfigType: &accesslog.AccessLog_TypedConfig{
TypedConfig: accesslogAny,
},
- Filter: buildAccessLogFilter(als.CELMatches, forListener),
+ Filter: buildAccessLogFilter(als.CELMatches, defaultLogTypeForListener),
})
}
}
// handle open telemetry access logs
for _, otel := range al.OpenTelemetry {
+ // Filter out logs that are not Global or match the desired access log type
+ if !(otel.LogType == nil || *otel.LogType == accessLogType) {
+ continue
+ }
+
+ // NR is only added to listener logs originating from a global log configuration
+ defaultLogTypeForListener := accessLogType == ir.ProxyAccessLogTypeListener && otel.LogType == nil
+
al := &otelaccesslog.OpenTelemetryAccessLogConfig{
CommonConfig: &grpcaccesslog.CommonGrpcAccessLogConfig{
LogName: otelLogName,
@@ -270,7 +303,7 @@ func buildXdsAccessLog(al *ir.AccessLog, forListener bool) []*accesslog.AccessLo
ConfigType: &accesslog.AccessLog_TypedConfig{
TypedConfig: accesslogAny,
},
- Filter: buildAccessLogFilter(otel.CELMatches, forListener),
+ Filter: buildAccessLogFilter(otel.CELMatches, defaultLogTypeForListener),
})
}
@@ -292,13 +325,13 @@ func celAccessLogFilter(expr string) *accesslog.AccessLogFilter {
}
}
-func buildAccessLogFilter(exprs []string, forListener bool) *accesslog.AccessLogFilter {
+func buildAccessLogFilter(exprs []string, withNoRouteMatchFilter bool) *accesslog.AccessLogFilter {
// add filter for access logs
var filters []*accesslog.AccessLogFilter
for _, expr := range exprs {
filters = append(filters, celAccessLogFilter(expr))
}
- if forListener {
+ if withNoRouteMatchFilter {
filters = append(filters, listenerAccessLogFilter)
}
diff --git a/internal/xds/translator/listener.go b/internal/xds/translator/listener.go
index 98f7c28e372..9cc8e61f6ed 100644
--- a/internal/xds/translator/listener.go
+++ b/internal/xds/translator/listener.go
@@ -151,7 +151,7 @@ func originalIPDetectionExtensions(clientIPDetection *ir.ClientIPDetectionSettin
// TODO: Improve function parameters
func buildXdsTCPListener(name, address string, port uint32, keepalive *ir.TCPKeepalive, connection *ir.ClientConnection, accesslog *ir.AccessLog) *listenerv3.Listener {
socketOptions := buildTCPSocketOptions(keepalive)
- al := buildXdsAccessLog(accesslog, true)
+ al := buildXdsAccessLog(accesslog, ir.ProxyAccessLogTypeListener)
bufferLimitBytes := buildPerConnectionBufferLimitBytes(connection)
return &listenerv3.Listener{
Name: name,
@@ -183,7 +183,7 @@ func buildPerConnectionBufferLimitBytes(connection *ir.ClientConnection) *wrappe
func buildXdsQuicListener(name, address string, port uint32, accesslog *ir.AccessLog) *listenerv3.Listener {
xdsListener := &listenerv3.Listener{
Name: name + "-quic",
- AccessLog: buildXdsAccessLog(accesslog, true),
+ AccessLog: buildXdsAccessLog(accesslog, ir.ProxyAccessLogTypeListener),
Address: &corev3.Address{
Address: &corev3.Address_SocketAddress{
SocketAddress: &corev3.SocketAddress{
@@ -220,7 +220,7 @@ func buildXdsQuicListener(name, address string, port uint32, accesslog *ir.Acces
func (t *Translator) addHCMToXDSListener(xdsListener *listenerv3.Listener, irListener *ir.HTTPListener,
accesslog *ir.AccessLog, tracing *ir.Tracing, http3Listener bool, connection *ir.ClientConnection,
) error {
- al := buildXdsAccessLog(accesslog, false)
+ al := buildXdsAccessLog(accesslog, ir.ProxyAccessLogTypeRoute)
hcmTracing, err := buildHCMTracing(tracing)
if err != nil {
@@ -494,7 +494,7 @@ func addXdsTCPFilterChain(xdsListener *listenerv3.Listener, irRoute *ir.TCPRoute
statPrefix = strings.Join([]string{statPrefix, strconv.Itoa(int(xdsListener.Address.GetSocketAddress().GetPortValue()))}, "-")
mgr := &tcpv3.TcpProxy{
- AccessLog: buildXdsAccessLog(accesslog, false),
+ AccessLog: buildXdsAccessLog(accesslog, ir.ProxyAccessLogTypeRoute),
StatPrefix: statPrefix,
ClusterSpecifier: &tcpv3.TcpProxy_Cluster{
Cluster: clusterName,
@@ -773,7 +773,7 @@ func buildXdsUDPListener(clusterName string, udpListener *ir.UDPListener, access
udpProxy := &udpv3.UdpProxyConfig{
StatPrefix: statPrefix,
- AccessLog: buildXdsAccessLog(accesslog, false),
+ AccessLog: buildXdsAccessLog(accesslog, ir.ProxyAccessLogTypeRoute),
RouteSpecifier: &udpv3.UdpProxyConfig_Matcher{
Matcher: &matcher.Matcher{
OnNoMatch: &matcher.Matcher_OnMatch{
@@ -794,7 +794,7 @@ func buildXdsUDPListener(clusterName string, udpListener *ir.UDPListener, access
xdsListener := &listenerv3.Listener{
Name: udpListener.Name,
- AccessLog: buildXdsAccessLog(accesslog, true),
+ AccessLog: buildXdsAccessLog(accesslog, ir.ProxyAccessLogTypeListener),
Address: &corev3.Address{
Address: &corev3.Address_SocketAddress{
SocketAddress: &corev3.SocketAddress{
diff --git a/internal/xds/translator/testdata/in/xds-ir/accesslog-types.yaml b/internal/xds/translator/testdata/in/xds-ir/accesslog-types.yaml
new file mode 100644
index 00000000000..d2458abfce9
--- /dev/null
+++ b/internal/xds/translator/testdata/in/xds-ir/accesslog-types.yaml
@@ -0,0 +1,184 @@
+accessLog:
+ als:
+ - destination:
+ name: accesslog_als_0_1
+ settings:
+ - addressType: IP
+ endpoints:
+ - host: 10.240.0.10
+ port: 9090
+ protocol: GRPC
+ http:
+ requestHeaders:
+ - x-client-ip-address
+ responseHeaders:
+ - cache-control
+ responseTrailers:
+ - expires
+ logType: Route
+ name: accesslog
+ text: |
+ this is a route log
+ type: HTTP
+ - destination:
+ name: accesslog_als_0_2
+ settings:
+ - addressType: IP
+ endpoints:
+ - host: 10.240.0.10
+ port: 9090
+ protocol: GRPC
+ logType: Route
+ name: envoy-gateway-system/test
+ text: |
+ this is a route log
+ type: TCP
+ - destination:
+ name: accesslog_als_1_1
+ settings:
+ - addressType: IP
+ endpoints:
+ - host: 10.240.0.10
+ port: 9090
+ protocol: GRPC
+ http:
+ requestHeaders:
+ - x-client-ip-address
+ responseHeaders:
+ - cache-control
+ responseTrailers:
+ - expires
+ logType: Listener
+ name: accesslog
+ text: |
+ this is a listener log
+ type: HTTP
+ - destination:
+ name: accesslog_als_1_2
+ settings:
+ - addressType: IP
+ endpoints:
+ - host: 10.240.0.10
+ port: 9090
+ protocol: GRPC
+ logType: Listener
+ name: envoy-gateway-system/test
+ text: |
+ this is a listener log
+ type: TCP
+ - destination:
+ name: accesslog_als_2_1
+ settings:
+ - addressType: IP
+ endpoints:
+ - host: 10.240.0.10
+ port: 9090
+ protocol: GRPC
+ http:
+ requestHeaders:
+ - x-client-ip-address
+ responseHeaders:
+ - cache-control
+ responseTrailers:
+ - expires
+ name: accesslog
+ text: |
+ this is a Global log
+ type: HTTP
+ - destination:
+ name: accesslog_als_2_2
+ settings:
+ - addressType: IP
+ endpoints:
+ - host: 10.240.0.10
+ port: 9090
+ protocol: GRPC
+ name: envoy-gateway-system/test
+ text: |
+ this is a Global log
+ type: TCP
+ openTelemetry:
+ - authority: otel-collector.monitoring.svc.cluster.local
+ destination:
+ name: accesslog_otel_0_3
+ settings:
+ - endpoints:
+ - host: otel-collector.monitoring.svc.cluster.local
+ port: 4317
+ protocol: GRPC
+ weight: 1
+ logType: Route
+ resources:
+ k8s.cluster.name: cluster-1
+ text: |
+ this is a route log
+ - authority: otel-collector.monitoring.svc.cluster.local
+ destination:
+ name: accesslog_otel_1_3
+ settings:
+ - endpoints:
+ - host: otel-collector.monitoring.svc.cluster.local
+ port: 4317
+ protocol: GRPC
+ weight: 1
+ logType: Listener
+ resources:
+ k8s.cluster.name: cluster-1
+ text: |
+ this is a listener log
+ - authority: otel-collector.monitoring.svc.cluster.local
+ destination:
+ name: accesslog_otel_2_3
+ settings:
+ - endpoints:
+ - host: otel-collector.monitoring.svc.cluster.local
+ port: 4317
+ protocol: GRPC
+ weight: 1
+ resources:
+ k8s.cluster.name: cluster-1
+ text: |
+ this is a Global log
+ text:
+ - logType: Route
+ path: /dev/stdout
+ - logType: Listener
+ path: /dev/stdout
+ - format: |
+ this is a route log
+ logType: Route
+ path: /dev/stdout
+ - format: |
+ this is a listener log
+ logType: Listener
+ path: /dev/stdout
+ - format: |
+ this is a Global log
+ path: /dev/stdout
+http:
+ - address: 0.0.0.0
+ hostnames:
+ - '*'
+ isHTTP2: false
+ metadata:
+ kind: Gateway
+ name: gateway-1
+ namespace: envoy-gateway
+ sectionName: http
+ name: envoy-gateway/gateway-1/http
+ path:
+ escapedSlashesAction: UnescapeAndRedirect
+ mergeSlashes: true
+ port: 10080
+ routes:
+ - name: "direct-route"
+ hostname: "*"
+ destination:
+ name: "direct-route-dest"
+ settings:
+ - endpoints:
+ - host: "1.2.3.4"
+ port: 50000
+ directResponse:
+ body: "Unknown custom filter type: UnsupportedType"
+ statusCode: 500
diff --git a/internal/xds/translator/testdata/out/xds-ir/accesslog-types.clusters.yaml b/internal/xds/translator/testdata/out/xds-ir/accesslog-types.clusters.yaml
new file mode 100644
index 00000000000..e0328b6e26c
--- /dev/null
+++ b/internal/xds/translator/testdata/out/xds-ir/accesslog-types.clusters.yaml
@@ -0,0 +1,263 @@
+- circuitBreakers:
+ thresholds:
+ - maxRetries: 1024
+ commonLbConfig:
+ localityWeightedLbConfig: {}
+ connectTimeout: 10s
+ dnsLookupFamily: V4_ONLY
+ edsClusterConfig:
+ edsConfig:
+ ads: {}
+ resourceApiVersion: V3
+ serviceName: direct-route-dest
+ lbPolicy: LEAST_REQUEST
+ name: direct-route-dest
+ outlierDetection: {}
+ perConnectionBufferLimitBytes: 32768
+ type: EDS
+- circuitBreakers:
+ thresholds:
+ - maxRetries: 1024
+ commonLbConfig:
+ localityWeightedLbConfig: {}
+ connectTimeout: 10s
+ dnsLookupFamily: V4_ONLY
+ edsClusterConfig:
+ edsConfig:
+ ads: {}
+ resourceApiVersion: V3
+ serviceName: accesslog_als_0_1
+ lbPolicy: LEAST_REQUEST
+ name: accesslog_als_0_1
+ outlierDetection: {}
+ perConnectionBufferLimitBytes: 32768
+ type: EDS
+ typedExtensionProtocolOptions:
+ envoy.extensions.upstreams.http.v3.HttpProtocolOptions:
+ '@type': type.googleapis.com/envoy.extensions.upstreams.http.v3.HttpProtocolOptions
+ explicitHttpConfig:
+ http2ProtocolOptions:
+ initialConnectionWindowSize: 1048576
+ initialStreamWindowSize: 65536
+- circuitBreakers:
+ thresholds:
+ - maxRetries: 1024
+ commonLbConfig:
+ localityWeightedLbConfig: {}
+ connectTimeout: 10s
+ dnsLookupFamily: V4_ONLY
+ edsClusterConfig:
+ edsConfig:
+ ads: {}
+ resourceApiVersion: V3
+ serviceName: accesslog_als_0_2
+ lbPolicy: LEAST_REQUEST
+ name: accesslog_als_0_2
+ outlierDetection: {}
+ perConnectionBufferLimitBytes: 32768
+ type: EDS
+ typedExtensionProtocolOptions:
+ envoy.extensions.upstreams.http.v3.HttpProtocolOptions:
+ '@type': type.googleapis.com/envoy.extensions.upstreams.http.v3.HttpProtocolOptions
+ explicitHttpConfig:
+ http2ProtocolOptions:
+ initialConnectionWindowSize: 1048576
+ initialStreamWindowSize: 65536
+- circuitBreakers:
+ thresholds:
+ - maxRetries: 1024
+ commonLbConfig:
+ localityWeightedLbConfig: {}
+ connectTimeout: 10s
+ dnsLookupFamily: V4_ONLY
+ edsClusterConfig:
+ edsConfig:
+ ads: {}
+ resourceApiVersion: V3
+ serviceName: accesslog_als_1_1
+ lbPolicy: LEAST_REQUEST
+ name: accesslog_als_1_1
+ outlierDetection: {}
+ perConnectionBufferLimitBytes: 32768
+ type: EDS
+ typedExtensionProtocolOptions:
+ envoy.extensions.upstreams.http.v3.HttpProtocolOptions:
+ '@type': type.googleapis.com/envoy.extensions.upstreams.http.v3.HttpProtocolOptions
+ explicitHttpConfig:
+ http2ProtocolOptions:
+ initialConnectionWindowSize: 1048576
+ initialStreamWindowSize: 65536
+- circuitBreakers:
+ thresholds:
+ - maxRetries: 1024
+ commonLbConfig:
+ localityWeightedLbConfig: {}
+ connectTimeout: 10s
+ dnsLookupFamily: V4_ONLY
+ edsClusterConfig:
+ edsConfig:
+ ads: {}
+ resourceApiVersion: V3
+ serviceName: accesslog_als_1_2
+ lbPolicy: LEAST_REQUEST
+ name: accesslog_als_1_2
+ outlierDetection: {}
+ perConnectionBufferLimitBytes: 32768
+ type: EDS
+ typedExtensionProtocolOptions:
+ envoy.extensions.upstreams.http.v3.HttpProtocolOptions:
+ '@type': type.googleapis.com/envoy.extensions.upstreams.http.v3.HttpProtocolOptions
+ explicitHttpConfig:
+ http2ProtocolOptions:
+ initialConnectionWindowSize: 1048576
+ initialStreamWindowSize: 65536
+- circuitBreakers:
+ thresholds:
+ - maxRetries: 1024
+ commonLbConfig:
+ localityWeightedLbConfig: {}
+ connectTimeout: 10s
+ dnsLookupFamily: V4_ONLY
+ edsClusterConfig:
+ edsConfig:
+ ads: {}
+ resourceApiVersion: V3
+ serviceName: accesslog_als_2_1
+ lbPolicy: LEAST_REQUEST
+ name: accesslog_als_2_1
+ outlierDetection: {}
+ perConnectionBufferLimitBytes: 32768
+ type: EDS
+ typedExtensionProtocolOptions:
+ envoy.extensions.upstreams.http.v3.HttpProtocolOptions:
+ '@type': type.googleapis.com/envoy.extensions.upstreams.http.v3.HttpProtocolOptions
+ explicitHttpConfig:
+ http2ProtocolOptions:
+ initialConnectionWindowSize: 1048576
+ initialStreamWindowSize: 65536
+- circuitBreakers:
+ thresholds:
+ - maxRetries: 1024
+ commonLbConfig:
+ localityWeightedLbConfig: {}
+ connectTimeout: 10s
+ dnsLookupFamily: V4_ONLY
+ edsClusterConfig:
+ edsConfig:
+ ads: {}
+ resourceApiVersion: V3
+ serviceName: accesslog_als_2_2
+ lbPolicy: LEAST_REQUEST
+ name: accesslog_als_2_2
+ outlierDetection: {}
+ perConnectionBufferLimitBytes: 32768
+ type: EDS
+ typedExtensionProtocolOptions:
+ envoy.extensions.upstreams.http.v3.HttpProtocolOptions:
+ '@type': type.googleapis.com/envoy.extensions.upstreams.http.v3.HttpProtocolOptions
+ explicitHttpConfig:
+ http2ProtocolOptions:
+ initialConnectionWindowSize: 1048576
+ initialStreamWindowSize: 65536
+- circuitBreakers:
+ thresholds:
+ - maxRetries: 1024
+ commonLbConfig:
+ localityWeightedLbConfig: {}
+ connectTimeout: 10s
+ dnsLookupFamily: V4_ONLY
+ dnsRefreshRate: 30s
+ lbPolicy: LEAST_REQUEST
+ loadAssignment:
+ clusterName: accesslog_otel_0_3
+ endpoints:
+ - lbEndpoints:
+ - endpoint:
+ address:
+ socketAddress:
+ address: otel-collector.monitoring.svc.cluster.local
+ portValue: 4317
+ loadBalancingWeight: 1
+ loadBalancingWeight: 1
+ locality:
+ region: accesslog_otel_0_3/backend/0
+ name: accesslog_otel_0_3
+ outlierDetection: {}
+ perConnectionBufferLimitBytes: 32768
+ respectDnsTtl: true
+ type: STRICT_DNS
+ typedExtensionProtocolOptions:
+ envoy.extensions.upstreams.http.v3.HttpProtocolOptions:
+ '@type': type.googleapis.com/envoy.extensions.upstreams.http.v3.HttpProtocolOptions
+ explicitHttpConfig:
+ http2ProtocolOptions:
+ initialConnectionWindowSize: 1048576
+ initialStreamWindowSize: 65536
+- circuitBreakers:
+ thresholds:
+ - maxRetries: 1024
+ commonLbConfig:
+ localityWeightedLbConfig: {}
+ connectTimeout: 10s
+ dnsLookupFamily: V4_ONLY
+ dnsRefreshRate: 30s
+ lbPolicy: LEAST_REQUEST
+ loadAssignment:
+ clusterName: accesslog_otel_1_3
+ endpoints:
+ - lbEndpoints:
+ - endpoint:
+ address:
+ socketAddress:
+ address: otel-collector.monitoring.svc.cluster.local
+ portValue: 4317
+ loadBalancingWeight: 1
+ loadBalancingWeight: 1
+ locality:
+ region: accesslog_otel_1_3/backend/0
+ name: accesslog_otel_1_3
+ outlierDetection: {}
+ perConnectionBufferLimitBytes: 32768
+ respectDnsTtl: true
+ type: STRICT_DNS
+ typedExtensionProtocolOptions:
+ envoy.extensions.upstreams.http.v3.HttpProtocolOptions:
+ '@type': type.googleapis.com/envoy.extensions.upstreams.http.v3.HttpProtocolOptions
+ explicitHttpConfig:
+ http2ProtocolOptions:
+ initialConnectionWindowSize: 1048576
+ initialStreamWindowSize: 65536
+- circuitBreakers:
+ thresholds:
+ - maxRetries: 1024
+ commonLbConfig:
+ localityWeightedLbConfig: {}
+ connectTimeout: 10s
+ dnsLookupFamily: V4_ONLY
+ dnsRefreshRate: 30s
+ lbPolicy: LEAST_REQUEST
+ loadAssignment:
+ clusterName: accesslog_otel_2_3
+ endpoints:
+ - lbEndpoints:
+ - endpoint:
+ address:
+ socketAddress:
+ address: otel-collector.monitoring.svc.cluster.local
+ portValue: 4317
+ loadBalancingWeight: 1
+ loadBalancingWeight: 1
+ locality:
+ region: accesslog_otel_2_3/backend/0
+ name: accesslog_otel_2_3
+ outlierDetection: {}
+ perConnectionBufferLimitBytes: 32768
+ respectDnsTtl: true
+ type: STRICT_DNS
+ typedExtensionProtocolOptions:
+ envoy.extensions.upstreams.http.v3.HttpProtocolOptions:
+ '@type': type.googleapis.com/envoy.extensions.upstreams.http.v3.HttpProtocolOptions
+ explicitHttpConfig:
+ http2ProtocolOptions:
+ initialConnectionWindowSize: 1048576
+ initialStreamWindowSize: 65536
diff --git a/internal/xds/translator/testdata/out/xds-ir/accesslog-types.endpoints.yaml b/internal/xds/translator/testdata/out/xds-ir/accesslog-types.endpoints.yaml
new file mode 100644
index 00000000000..e9526ab5d90
--- /dev/null
+++ b/internal/xds/translator/testdata/out/xds-ir/accesslog-types.endpoints.yaml
@@ -0,0 +1,84 @@
+- clusterName: direct-route-dest
+ endpoints:
+ - lbEndpoints:
+ - endpoint:
+ address:
+ socketAddress:
+ address: 1.2.3.4
+ portValue: 50000
+ loadBalancingWeight: 1
+ loadBalancingWeight: 1
+ locality:
+ region: direct-route-dest/backend/0
+- clusterName: accesslog_als_0_1
+ endpoints:
+ - lbEndpoints:
+ - endpoint:
+ address:
+ socketAddress:
+ address: 10.240.0.10
+ portValue: 9090
+ loadBalancingWeight: 1
+ loadBalancingWeight: 1
+ locality:
+ region: accesslog_als_0_1/backend/0
+- clusterName: accesslog_als_0_2
+ endpoints:
+ - lbEndpoints:
+ - endpoint:
+ address:
+ socketAddress:
+ address: 10.240.0.10
+ portValue: 9090
+ loadBalancingWeight: 1
+ loadBalancingWeight: 1
+ locality:
+ region: accesslog_als_0_2/backend/0
+- clusterName: accesslog_als_1_1
+ endpoints:
+ - lbEndpoints:
+ - endpoint:
+ address:
+ socketAddress:
+ address: 10.240.0.10
+ portValue: 9090
+ loadBalancingWeight: 1
+ loadBalancingWeight: 1
+ locality:
+ region: accesslog_als_1_1/backend/0
+- clusterName: accesslog_als_1_2
+ endpoints:
+ - lbEndpoints:
+ - endpoint:
+ address:
+ socketAddress:
+ address: 10.240.0.10
+ portValue: 9090
+ loadBalancingWeight: 1
+ loadBalancingWeight: 1
+ locality:
+ region: accesslog_als_1_2/backend/0
+- clusterName: accesslog_als_2_1
+ endpoints:
+ - lbEndpoints:
+ - endpoint:
+ address:
+ socketAddress:
+ address: 10.240.0.10
+ portValue: 9090
+ loadBalancingWeight: 1
+ loadBalancingWeight: 1
+ locality:
+ region: accesslog_als_2_1/backend/0
+- clusterName: accesslog_als_2_2
+ endpoints:
+ - lbEndpoints:
+ - endpoint:
+ address:
+ socketAddress:
+ address: 10.240.0.10
+ portValue: 9090
+ loadBalancingWeight: 1
+ loadBalancingWeight: 1
+ locality:
+ region: accesslog_als_2_2/backend/0
diff --git a/internal/xds/translator/testdata/out/xds-ir/accesslog-types.listeners.yaml b/internal/xds/translator/testdata/out/xds-ir/accesslog-types.listeners.yaml
new file mode 100644
index 00000000000..dbb30726378
--- /dev/null
+++ b/internal/xds/translator/testdata/out/xds-ir/accesslog-types.listeners.yaml
@@ -0,0 +1,300 @@
+- accessLog:
+ - name: envoy.access_loggers.file
+ typedConfig:
+ '@type': type.googleapis.com/envoy.extensions.access_loggers.file.v3.FileAccessLog
+ logFormat:
+ textFormatSource:
+ inlineString: |
+ {"start_time":"%START_TIME%","method":"%REQ(:METHOD)%","x-envoy-origin-path":"%REQ(X-ENVOY-ORIGINAL-PATH?:PATH)%","protocol":"%PROTOCOL%","response_code":"%RESPONSE_CODE%","response_flags":"%RESPONSE_FLAGS%","response_code_details":"%RESPONSE_CODE_DETAILS%","connection_termination_details":"%CONNECTION_TERMINATION_DETAILS%","upstream_transport_failure_reason":"%UPSTREAM_TRANSPORT_FAILURE_REASON%","bytes_received":"%BYTES_RECEIVED%","bytes_sent":"%BYTES_SENT%","duration":"%DURATION%","x-envoy-upstream-service-time":"%RESP(X-ENVOY-UPSTREAM-SERVICE-TIME)%","x-forwarded-for":"%REQ(X-FORWARDED-FOR)%","user-agent":"%REQ(USER-AGENT)%","x-request-id":"%REQ(X-REQUEST-ID)%",":authority":"%REQ(:AUTHORITY)%","upstream_host":"%UPSTREAM_HOST%","upstream_cluster":"%UPSTREAM_CLUSTER%","upstream_local_address":"%UPSTREAM_LOCAL_ADDRESS%","downstream_local_address":"%DOWNSTREAM_LOCAL_ADDRESS%","downstream_remote_address":"%DOWNSTREAM_REMOTE_ADDRESS%","requested_server_name":"%REQUESTED_SERVER_NAME%","route_name":"%ROUTE_NAME%"}
+ path: /dev/stdout
+ - name: envoy.access_loggers.file
+ typedConfig:
+ '@type': type.googleapis.com/envoy.extensions.access_loggers.file.v3.FileAccessLog
+ logFormat:
+ textFormatSource:
+ inlineString: |
+ this is a listener log
+ path: /dev/stdout
+ - filter:
+ responseFlagFilter:
+ flags:
+ - NR
+ name: envoy.access_loggers.file
+ typedConfig:
+ '@type': type.googleapis.com/envoy.extensions.access_loggers.file.v3.FileAccessLog
+ logFormat:
+ textFormatSource:
+ inlineString: |
+ this is a Global log
+ path: /dev/stdout
+ - name: envoy.access_loggers.http_grpc
+ typedConfig:
+ '@type': type.googleapis.com/envoy.extensions.access_loggers.grpc.v3.HttpGrpcAccessLogConfig
+ additionalRequestHeadersToLog:
+ - x-client-ip-address
+ additionalResponseHeadersToLog:
+ - cache-control
+ additionalResponseTrailersToLog:
+ - expires
+ commonConfig:
+ grpcService:
+ envoyGrpc:
+ clusterName: accesslog_als_1_1
+ logName: accesslog
+ transportApiVersion: V3
+ - name: envoy.access_loggers.tcp_grpc
+ typedConfig:
+ '@type': type.googleapis.com/envoy.extensions.access_loggers.grpc.v3.TcpGrpcAccessLogConfig
+ commonConfig:
+ grpcService:
+ envoyGrpc:
+ clusterName: accesslog_als_1_2
+ logName: envoy-gateway-system/test
+ transportApiVersion: V3
+ - filter:
+ responseFlagFilter:
+ flags:
+ - NR
+ name: envoy.access_loggers.http_grpc
+ typedConfig:
+ '@type': type.googleapis.com/envoy.extensions.access_loggers.grpc.v3.HttpGrpcAccessLogConfig
+ additionalRequestHeadersToLog:
+ - x-client-ip-address
+ additionalResponseHeadersToLog:
+ - cache-control
+ additionalResponseTrailersToLog:
+ - expires
+ commonConfig:
+ grpcService:
+ envoyGrpc:
+ clusterName: accesslog_als_2_1
+ logName: accesslog
+ transportApiVersion: V3
+ - filter:
+ responseFlagFilter:
+ flags:
+ - NR
+ name: envoy.access_loggers.tcp_grpc
+ typedConfig:
+ '@type': type.googleapis.com/envoy.extensions.access_loggers.grpc.v3.TcpGrpcAccessLogConfig
+ commonConfig:
+ grpcService:
+ envoyGrpc:
+ clusterName: accesslog_als_2_2
+ logName: envoy-gateway-system/test
+ transportApiVersion: V3
+ - name: envoy.access_loggers.open_telemetry
+ typedConfig:
+ '@type': type.googleapis.com/envoy.extensions.access_loggers.open_telemetry.v3.OpenTelemetryAccessLogConfig
+ attributes:
+ values:
+ - key: k8s.namespace.name
+ value:
+ stringValue: '%ENVIRONMENT(ENVOY_GATEWAY_NAMESPACE)%'
+ - key: k8s.pod.name
+ value:
+ stringValue: '%ENVIRONMENT(ENVOY_POD_NAME)%'
+ body:
+ stringValue: |
+ this is a listener log
+ commonConfig:
+ grpcService:
+ envoyGrpc:
+ authority: otel-collector.monitoring.svc.cluster.local
+ clusterName: accesslog_otel_1_3
+ logName: otel_envoy_accesslog
+ transportApiVersion: V3
+ resourceAttributes:
+ values:
+ - key: k8s.cluster.name
+ value:
+ stringValue: cluster-1
+ - filter:
+ responseFlagFilter:
+ flags:
+ - NR
+ name: envoy.access_loggers.open_telemetry
+ typedConfig:
+ '@type': type.googleapis.com/envoy.extensions.access_loggers.open_telemetry.v3.OpenTelemetryAccessLogConfig
+ attributes:
+ values:
+ - key: k8s.namespace.name
+ value:
+ stringValue: '%ENVIRONMENT(ENVOY_GATEWAY_NAMESPACE)%'
+ - key: k8s.pod.name
+ value:
+ stringValue: '%ENVIRONMENT(ENVOY_POD_NAME)%'
+ body:
+ stringValue: |
+ this is a Global log
+ commonConfig:
+ grpcService:
+ envoyGrpc:
+ authority: otel-collector.monitoring.svc.cluster.local
+ clusterName: accesslog_otel_2_3
+ logName: otel_envoy_accesslog
+ transportApiVersion: V3
+ resourceAttributes:
+ values:
+ - key: k8s.cluster.name
+ value:
+ stringValue: cluster-1
+ address:
+ socketAddress:
+ address: 0.0.0.0
+ portValue: 10080
+ defaultFilterChain:
+ filters:
+ - name: envoy.filters.network.http_connection_manager
+ typedConfig:
+ '@type': type.googleapis.com/envoy.extensions.filters.network.http_connection_manager.v3.HttpConnectionManager
+ accessLog:
+ - name: envoy.access_loggers.file
+ typedConfig:
+ '@type': type.googleapis.com/envoy.extensions.access_loggers.file.v3.FileAccessLog
+ logFormat:
+ textFormatSource:
+ inlineString: |
+ {"start_time":"%START_TIME%","method":"%REQ(:METHOD)%","x-envoy-origin-path":"%REQ(X-ENVOY-ORIGINAL-PATH?:PATH)%","protocol":"%PROTOCOL%","response_code":"%RESPONSE_CODE%","response_flags":"%RESPONSE_FLAGS%","response_code_details":"%RESPONSE_CODE_DETAILS%","connection_termination_details":"%CONNECTION_TERMINATION_DETAILS%","upstream_transport_failure_reason":"%UPSTREAM_TRANSPORT_FAILURE_REASON%","bytes_received":"%BYTES_RECEIVED%","bytes_sent":"%BYTES_SENT%","duration":"%DURATION%","x-envoy-upstream-service-time":"%RESP(X-ENVOY-UPSTREAM-SERVICE-TIME)%","x-forwarded-for":"%REQ(X-FORWARDED-FOR)%","user-agent":"%REQ(USER-AGENT)%","x-request-id":"%REQ(X-REQUEST-ID)%",":authority":"%REQ(:AUTHORITY)%","upstream_host":"%UPSTREAM_HOST%","upstream_cluster":"%UPSTREAM_CLUSTER%","upstream_local_address":"%UPSTREAM_LOCAL_ADDRESS%","downstream_local_address":"%DOWNSTREAM_LOCAL_ADDRESS%","downstream_remote_address":"%DOWNSTREAM_REMOTE_ADDRESS%","requested_server_name":"%REQUESTED_SERVER_NAME%","route_name":"%ROUTE_NAME%"}
+ path: /dev/stdout
+ - name: envoy.access_loggers.file
+ typedConfig:
+ '@type': type.googleapis.com/envoy.extensions.access_loggers.file.v3.FileAccessLog
+ logFormat:
+ textFormatSource:
+ inlineString: |
+ this is a route log
+ path: /dev/stdout
+ - name: envoy.access_loggers.file
+ typedConfig:
+ '@type': type.googleapis.com/envoy.extensions.access_loggers.file.v3.FileAccessLog
+ logFormat:
+ textFormatSource:
+ inlineString: |
+ this is a Global log
+ path: /dev/stdout
+ - name: envoy.access_loggers.http_grpc
+ typedConfig:
+ '@type': type.googleapis.com/envoy.extensions.access_loggers.grpc.v3.HttpGrpcAccessLogConfig
+ additionalRequestHeadersToLog:
+ - x-client-ip-address
+ additionalResponseHeadersToLog:
+ - cache-control
+ additionalResponseTrailersToLog:
+ - expires
+ commonConfig:
+ grpcService:
+ envoyGrpc:
+ clusterName: accesslog_als_0_1
+ logName: accesslog
+ transportApiVersion: V3
+ - name: envoy.access_loggers.tcp_grpc
+ typedConfig:
+ '@type': type.googleapis.com/envoy.extensions.access_loggers.grpc.v3.TcpGrpcAccessLogConfig
+ commonConfig:
+ grpcService:
+ envoyGrpc:
+ clusterName: accesslog_als_0_2
+ logName: envoy-gateway-system/test
+ transportApiVersion: V3
+ - name: envoy.access_loggers.http_grpc
+ typedConfig:
+ '@type': type.googleapis.com/envoy.extensions.access_loggers.grpc.v3.HttpGrpcAccessLogConfig
+ additionalRequestHeadersToLog:
+ - x-client-ip-address
+ additionalResponseHeadersToLog:
+ - cache-control
+ additionalResponseTrailersToLog:
+ - expires
+ commonConfig:
+ grpcService:
+ envoyGrpc:
+ clusterName: accesslog_als_2_1
+ logName: accesslog
+ transportApiVersion: V3
+ - name: envoy.access_loggers.tcp_grpc
+ typedConfig:
+ '@type': type.googleapis.com/envoy.extensions.access_loggers.grpc.v3.TcpGrpcAccessLogConfig
+ commonConfig:
+ grpcService:
+ envoyGrpc:
+ clusterName: accesslog_als_2_2
+ logName: envoy-gateway-system/test
+ transportApiVersion: V3
+ - name: envoy.access_loggers.open_telemetry
+ typedConfig:
+ '@type': type.googleapis.com/envoy.extensions.access_loggers.open_telemetry.v3.OpenTelemetryAccessLogConfig
+ attributes:
+ values:
+ - key: k8s.namespace.name
+ value:
+ stringValue: '%ENVIRONMENT(ENVOY_GATEWAY_NAMESPACE)%'
+ - key: k8s.pod.name
+ value:
+ stringValue: '%ENVIRONMENT(ENVOY_POD_NAME)%'
+ body:
+ stringValue: |
+ this is a route log
+ commonConfig:
+ grpcService:
+ envoyGrpc:
+ authority: otel-collector.monitoring.svc.cluster.local
+ clusterName: accesslog_otel_0_3
+ logName: otel_envoy_accesslog
+ transportApiVersion: V3
+ resourceAttributes:
+ values:
+ - key: k8s.cluster.name
+ value:
+ stringValue: cluster-1
+ - name: envoy.access_loggers.open_telemetry
+ typedConfig:
+ '@type': type.googleapis.com/envoy.extensions.access_loggers.open_telemetry.v3.OpenTelemetryAccessLogConfig
+ attributes:
+ values:
+ - key: k8s.namespace.name
+ value:
+ stringValue: '%ENVIRONMENT(ENVOY_GATEWAY_NAMESPACE)%'
+ - key: k8s.pod.name
+ value:
+ stringValue: '%ENVIRONMENT(ENVOY_POD_NAME)%'
+ body:
+ stringValue: |
+ this is a Global log
+ commonConfig:
+ grpcService:
+ envoyGrpc:
+ authority: otel-collector.monitoring.svc.cluster.local
+ clusterName: accesslog_otel_2_3
+ logName: otel_envoy_accesslog
+ transportApiVersion: V3
+ resourceAttributes:
+ values:
+ - key: k8s.cluster.name
+ value:
+ stringValue: cluster-1
+ commonHttpProtocolOptions:
+ headersWithUnderscoresAction: REJECT_REQUEST
+ http2ProtocolOptions:
+ initialConnectionWindowSize: 1048576
+ initialStreamWindowSize: 65536
+ maxConcurrentStreams: 100
+ httpFilters:
+ - name: envoy.filters.http.router
+ typedConfig:
+ '@type': type.googleapis.com/envoy.extensions.filters.http.router.v3.Router
+ suppressEnvoyHeaders: true
+ mergeSlashes: true
+ normalizePath: true
+ pathWithEscapedSlashesAction: UNESCAPE_AND_REDIRECT
+ rds:
+ configSource:
+ ads: {}
+ resourceApiVersion: V3
+ routeConfigName: envoy-gateway/gateway-1/http
+ serverHeaderTransformation: PASS_THROUGH
+ statPrefix: http-10080
+ useRemoteAddress: true
+ name: envoy-gateway/gateway-1/http
+ name: envoy-gateway/gateway-1/http
+ perConnectionBufferLimitBytes: 32768
diff --git a/internal/xds/translator/testdata/out/xds-ir/accesslog-types.routes.yaml b/internal/xds/translator/testdata/out/xds-ir/accesslog-types.routes.yaml
new file mode 100644
index 00000000000..ff2210f8d50
--- /dev/null
+++ b/internal/xds/translator/testdata/out/xds-ir/accesslog-types.routes.yaml
@@ -0,0 +1,20 @@
+- ignorePortInHostMatching: true
+ name: envoy-gateway/gateway-1/http
+ virtualHosts:
+ - domains:
+ - '*'
+ metadata:
+ filterMetadata:
+ envoy-gateway:
+ resources:
+ - kind: Gateway
+ name: gateway-1
+ namespace: envoy-gateway
+ sectionName: http
+ name: envoy-gateway/gateway-1/http/*
+ routes:
+ - directResponse:
+ status: 500
+ match:
+ prefix: /
+ name: direct-route
diff --git a/site/content/en/latest/api/extension_types.md b/site/content/en/latest/api/extension_types.md
index bc01189920d..c26a8c713f8 100644
--- a/site/content/en/latest/api/extension_types.md
+++ b/site/content/en/latest/api/extension_types.md
@@ -2995,6 +2995,7 @@ _Appears in:_
| `format` | _[ProxyAccessLogFormat](#proxyaccesslogformat)_ | false | Format defines the format of accesslog.
This will be ignored if sink type is ALS. |
| `matches` | _string array_ | true | Matches defines the match conditions for accesslog in CEL expression.
An accesslog will be emitted only when one or more match conditions are evaluated to true.
Invalid [CEL](https://www.envoyproxy.io/docs/envoy/latest/xds/type/v3/cel.proto.html#common-expression-language-cel-proto) expressions will be ignored. |
| `sinks` | _[ProxyAccessLogSink](#proxyaccesslogsink) array_ | true | Sinks defines the sinks of accesslog. |
+| `type` | _[ProxyAccessLogType](#proxyaccesslogtype)_ | false | Type defines the component emitting the accesslog, such as Listener and Route.
If type not defined, the setting would apply to:
(1) All Routes.
(2) Listeners if and only if Envoy does not find a matching route for a request.
If type is defined, the accesslog settings would apply to the relevant component (as-is). |
#### ProxyAccessLogSink
diff --git a/site/content/en/latest/tasks/observability/proxy-accesslog.md b/site/content/en/latest/tasks/observability/proxy-accesslog.md
index fb0200f1739..17d444b8636 100644
--- a/site/content/en/latest/tasks/observability/proxy-accesslog.md
+++ b/site/content/en/latest/tasks/observability/proxy-accesslog.md
@@ -249,3 +249,62 @@ Envoy Gateway provides additional metadata about the K8s resources that were tra
For example, details about the `HTTPRoute` and `GRPCRoute` (kind, group, name, namespace and annotations) are available
for access log formatter using the `METADATA` operator. To enrich logs, users can add log operator such as:
`%METADATA(ROUTE:envoy-gateway:resources)%` to their access log format.
+
+## Access Log Types
+
+By default, Access Log settings would apply to:
+- All Routes
+- If traffic is not matched by any Route known to Envoy, the Listener would emit the access log instead
+
+Users may wish to customize this behavior:
+- Emit Access Logs by all Listeners for all traffic with specific settings
+- Do not emit Route-oriented access logs when a route is not matched.
+
+To achieve this, users can select if Access Log settings follow the default behavior or apply specifically to
+Routes or Listeners by specifying the setting's type.
+
+**Note**: When users define their own Access Log settings (with or without a type), the default Envoy Gateway
+file access log is no longer configured. It can be re-enabled explicitly by adding empty settings for the desired components.
+
+In the following example:
+- Route Access logs would use the default Envoy Gateway format and sink
+- Listener Access logs are customized to report transport-level failures and connection attributes
+
+```shell
+kubectl apply -f - <This will be ignored if sink type is ALS. |
| `matches` | _string array_ | true | Matches defines the match conditions for accesslog in CEL expression.
An accesslog will be emitted only when one or more match conditions are evaluated to true.
Invalid [CEL](https://www.envoyproxy.io/docs/envoy/latest/xds/type/v3/cel.proto.html#common-expression-language-cel-proto) expressions will be ignored. |
| `sinks` | _[ProxyAccessLogSink](#proxyaccesslogsink) array_ | true | Sinks defines the sinks of accesslog. |
+| `type` | _[ProxyAccessLogType](#proxyaccesslogtype)_ | false | Type defines the component emitting the accesslog, such as Listener and Route.
If type not defined, the setting would apply to:
(1) All Routes.
(2) Listeners if and only if Envoy does not find a matching route for a request.
If type is defined, the accesslog settings would apply to the relevant component (as-is). |
#### ProxyAccessLogSink
diff --git a/test/config/gatewayclass.yaml b/test/config/gatewayclass.yaml
index fa07a159305..6e8acf3d0f8 100644
--- a/test/config/gatewayclass.yaml
+++ b/test/config/gatewayclass.yaml
@@ -68,6 +68,15 @@ spec:
namespace: monitoring
port: 8080
type: HTTP
+ - type: Listener
+ format:
+ type: Text
+ text: |
+ LISTENER ACCESS LOG %UPSTREAM_PROTOCOL% %RESPONSE_CODE%
+ sinks:
+ - type: File
+ file:
+ path: /dev/stdout
tracing:
provider:
backendRefs:
diff --git a/test/e2e/tests/accesslog.go b/test/e2e/tests/accesslog.go
index 2019d92568c..b2c9a28ac94 100644
--- a/test/e2e/tests/accesslog.go
+++ b/test/e2e/tests/accesslog.go
@@ -81,6 +81,38 @@ var FileAccessLogTest = suite.ConformanceTest{
runLogTest(t, suite, gwAddr, expectedResponse, labels, match, 0)
})
+
+ t.Run("Listener Logs", func(t *testing.T) {
+ // Ensure that Listener is emitting the log: protocol and response code should be
+ // empty in listener logs as they are upstream L7 attributes
+ expectedMatch := "LISTENER ACCESS LOG - 0"
+ ns := "gateway-conformance-infra"
+ routeNN := types.NamespacedName{Name: "accesslog-file", Namespace: ns}
+ gwNN := types.NamespacedName{Name: "same-namespace", Namespace: ns}
+ gwAddr := kubernetes.GatewayAndHTTPRoutesMustBeAccepted(t, suite.Client, suite.TimeoutConfig, suite.ControllerName, kubernetes.NewGatewayRef(gwNN), routeNN)
+
+ expectedResponse := httputils.ExpectedResponse{
+ Request: httputils.Request{
+ Path: "/file",
+ Headers: map[string]string{
+ "connection": "close",
+ },
+ },
+ ExpectedRequest: &httputils.ExpectedRequest{
+ Request: httputils.Request{
+ Path: "/file",
+ },
+ },
+ Response: httputils.Response{
+ StatusCode: 200,
+ },
+ Namespace: ns,
+ }
+ // make sure listener is ready
+ httputils.MakeRequestAndExpectEventuallyConsistentResponse(t, suite.RoundTripper, suite.TimeoutConfig, gwAddr, expectedResponse)
+
+ runLogTest(t, suite, gwAddr, expectedResponse, labels, expectedMatch, 0)
+ })
},
}