Skip to content

Commit

Permalink
add support for preserving clientIP
Browse files Browse the repository at this point in the history
  • Loading branch information
salonichf5 committed Aug 20, 2024
1 parent 34654d7 commit 8835f3a
Show file tree
Hide file tree
Showing 20 changed files with 813 additions and 38 deletions.
59 changes: 59 additions & 0 deletions apis/v1alpha1/nginxproxy_types.go
Original file line number Diff line number Diff line change
Expand Up @@ -53,6 +53,12 @@ type NginxProxySpec struct {
//
// +optional
Telemetry *Telemetry `json:"telemetry,omitempty"`
// RewriteClientIP defines configuration for rewriting the client IP to the original client's IP.
// +kubebuilder:validation:XValidation:message="if mode is set, trustedAddresses is a required field",rule="!(has(self.mode) && !has(self.trustedAddresses))"
//
// +optional
//nolint:lll
RewriteClientIP *RewriteClientIP `json:"rewriteClientIP,omitempty"`
// DisableHTTP2 defines if http2 should be disabled for all servers.
// Default is false, meaning http2 will be enabled for all servers.
//
Expand Down Expand Up @@ -114,3 +120,56 @@ type TelemetryExporter struct {
// +kubebuilder:validation:Pattern=`^(?:http?:\/\/)?[a-z0-9]([a-z0-9-]{0,61}[a-z0-9])?(?:\.[a-z0-9]([a-z0-9-]{0,61}[a-z0-9])?)*(?::\d{1,5})?$`
Endpoint string `json:"endpoint"`
}

// RewriteClientIP specifies the configuration for rewriting the client's IP address.
type RewriteClientIP struct {
// Mode defines how NGINX will rewrite the client's IP address.
// Possible modes: ProxyProtocol, XForwardedFor.
//
// +optional
Mode *RewriteClientIPModeType `json:"mode,omitempty"`

// SetIPRecursively configures whether recursive search is used for selecting client's
// address from the X-Forwarded-For header and used in conjunction with TrustedAddresses.
// If enabled, NGINX will recurse on the values in X-Forwarded-Header from the end of
// array to start of array and select the first untrusted IP.
//
// +optional
SetIPRecursively *bool `json:"setIPRecursively,omitempty"`

// TrustedAddresses specifies the addresses that are trusted to send correct client IP information.
// If a request comes from a trusted address, NGINX will rewrite the client IP information,
// and forward it to the backend in the X-Forwarded-For* and X-Real-IP headers.
// This field is required if mode is set.
// +kubebuilder:validation:MaxItems=16
// +listType=atomic
//
//
// +optional
TrustedAddresses []TrustedAddress `json:"trustedAddresses,omitempty"`
}

// RewriteClientIPModeType defines how NGINX Gateway Fabric will determine the client's original IP address.
// +kubebuilder:validation:Enum=ProxyProtocol;XForwardedFor
type RewriteClientIPModeType string

const (
// RewriteClientIPModeProxyProtocol configures NGINX to accept PROXY protocol and,
// set the client's IP address to the IP address in the PROXY protocol header.
// Sets the proxy_protocol parameter to the listen directive on all servers, and sets real_ip_header
// to proxy_protocol: https://nginx.org/en/docs/http/ngx_http_realip_module.html#real_ip_header.
RewriteClientIPModeProxyProtocol RewriteClientIPModeType = "ProxyProtocol"

// RewriteClientIPModeXForwardedFor configures NGINX to set the client's IP address to the
// IP address in the X-Forwarded-For HTTP header.
// https://nginx.org/en/docs/http/ngx_http_realip_module.html#real_ip_header.
RewriteClientIPModeXForwardedFor RewriteClientIPModeType = "XForwardedFor"
)

// TrustedAddress is a string value representing a CIDR block.
// Examples: 0.0.0.0/0
//
// +kubebuilder:validation:Pattern=`^(?:(?:[0-9]{1,3}\.){3}[0-9]{1,3}(?:\/(?:[0-9]|[12][0-9]|3[0-2]))?|(?:[0-9a-fA-F]{1,4}:){7}[0-9a-fA-F]{1,4}(?:\/(?:[0-9]|[1-9][0-9]|1[0-1][0-9]|12[0-8]))?)$`
//
//nolint:lll
type TrustedAddress string
35 changes: 35 additions & 0 deletions apis/v1alpha1/zz_generated.deepcopy.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

4 changes: 4 additions & 0 deletions charts/nginx-gateway-fabric/values.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -93,6 +93,10 @@ nginx:
{}
# disableHTTP2: false
# ipFamily: dual
# rewriteClientIP:
# mode: "ProxyProtocol"
# trustedAddresses: ["0.0.0.0/0"]
# setIPRecursively: true
# telemetry:
# exporter:
# endpoint: otel-collector.default.svc:4317
Expand Down
38 changes: 38 additions & 0 deletions config/crd/bases/gateway.nginx.org_nginxproxies.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,44 @@ spec:
- ipv4
- ipv6
type: string
rewriteClientIP:
description: RewriteClientIP defines configuration for rewriting the
client IP to the original client's IP.
properties:
mode:
description: |-
Mode defines how NGINX will rewrite the client's IP address.
Possible modes: ProxyProtocol, XForwardedFor.
enum:
- ProxyProtocol
- XForwardedFor
type: string
setIPRecursively:
description: |-
SetIPRecursively configures whether recursive search is used for selecting client's
address from the X-Forwarded-For header and used in conjunction with TrustedAddresses.
If enabled, NGINX will recurse on the values in X-Forwarded-Header from the end of
array to start of array and select the first untrusted IP.
type: boolean
trustedAddresses:
description: |-
TrustedAddresses specifies the addresses that are trusted to send correct client IP information.
If a request comes from a trusted address, NGINX will rewrite the client IP information,
and forward it to the backend in the X-Forwarded-For* and X-Real-IP headers.
This field is required if mode is set.
items:
description: |-
TrustedAddress is a string value representing a CIDR block.
Examples: 0.0.0.0/0
pattern: ^(?:(?:[0-9]{1,3}\.){3}[0-9]{1,3}(?:\/(?:[0-9]|[12][0-9]|3[0-2]))?|(?:[0-9a-fA-F]{1,4}:){7}[0-9a-fA-F]{1,4}(?:\/(?:[0-9]|[1-9][0-9]|1[0-1][0-9]|12[0-8]))?)$
type: string
maxItems: 16
type: array
x-kubernetes-list-type: atomic
type: object
x-kubernetes-validations:
- message: if mode is set, trustedAddresses is a required field
rule: '!(has(self.mode) && !has(self.trustedAddresses))'
telemetry:
description: Telemetry specifies the OpenTelemetry configuration.
properties:
Expand Down
20 changes: 20 additions & 0 deletions deploy/azure/deploy.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -321,6 +321,10 @@ metadata:
name: nginx
spec:
controllerName: gateway.nginx.org/nginx-gateway-controller
parametersRef:
group: gateway.nginx.org
kind: NginxProxy
name: nginx-gateway-proxy-config
---
apiVersion: gateway.nginx.org/v1alpha1
kind: NginxGateway
Expand All @@ -334,3 +338,19 @@ metadata:
spec:
logging:
level: info
---
# Source: nginx-gateway-fabric/templates/nginxproxy.yaml
apiVersion: gateway.nginx.org/v1alpha1
kind: NginxProxy
metadata:
name: nginx-gateway-proxy-config
labels:
app.kubernetes.io/name: nginx-gateway
app.kubernetes.io/instance: nginx-gateway
app.kubernetes.io/version: "edge"
spec:
rewriteClientIP:
mode: ProxyProtocol
setIPRecursively: true
trustedAddresses:
- 0.0.0.0/0
38 changes: 38 additions & 0 deletions deploy/crds.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -707,6 +707,44 @@ spec:
- ipv4
- ipv6
type: string
rewriteClientIP:
description: RewriteClientIP defines configuration for rewriting the
client IP to the original client's IP.
properties:
mode:
description: |-
Mode defines how NGINX will rewrite the client's IP address.
Possible modes: ProxyProtocol, XForwardedFor.
enum:
- ProxyProtocol
- XForwardedFor
type: string
setIPRecursively:
description: |-
SetIPRecursively configures whether recursive search is used for selecting client's
address from the X-Forwarded-For header and used in conjunction with TrustedAddresses.
If enabled, NGINX will recurse on the values in X-Forwarded-Header from the end of
array to start of array and select the first untrusted IP.
type: boolean
trustedAddresses:
description: |-
TrustedAddresses specifies the addresses that are trusted to send correct client IP information.
If a request comes from a trusted address, NGINX will rewrite the client IP information,
and forward it to the backend in the X-Forwarded-For* and X-Real-IP headers.
This field is required if mode is set.
items:
description: |-
TrustedAddress is a string value representing a CIDR block.
Examples: 0.0.0.0/0
pattern: ^(?:(?:[0-9]{1,3}\.){3}[0-9]{1,3}(?:\/(?:[0-9]|[12][0-9]|3[0-2]))?|(?:[0-9a-fA-F]{1,4}:){7}[0-9a-fA-F]{1,4}(?:\/(?:[0-9]|[1-9][0-9]|1[0-1][0-9]|12[0-8]))?)$
type: string
maxItems: 16
type: array
x-kubernetes-list-type: atomic
type: object
x-kubernetes-validations:
- message: if mode is set, trustedAddresses is a required field
rule: '!(has(self.mode) && !has(self.trustedAddresses))'
telemetry:
description: Telemetry specifies the OpenTelemetry configuration.
properties:
Expand Down
20 changes: 20 additions & 0 deletions deploy/default/deploy.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -319,6 +319,10 @@ metadata:
name: nginx
spec:
controllerName: gateway.nginx.org/nginx-gateway-controller
parametersRef:
group: gateway.nginx.org
kind: NginxProxy
name: nginx-gateway-proxy-config
---
apiVersion: gateway.nginx.org/v1alpha1
kind: NginxGateway
Expand All @@ -332,3 +336,19 @@ metadata:
spec:
logging:
level: info
---
# Source: nginx-gateway-fabric/templates/nginxproxy.yaml
apiVersion: gateway.nginx.org/v1alpha1
kind: NginxProxy
metadata:
name: nginx-gateway-proxy-config
labels:
app.kubernetes.io/name: nginx-gateway
app.kubernetes.io/instance: nginx-gateway
app.kubernetes.io/version: "edge"
spec:
rewriteClientIP:
mode: ProxyProtocol
setIPRecursively: true
trustedAddresses:
- 0.0.0.0/0
20 changes: 20 additions & 0 deletions deploy/experimental/deploy.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -325,6 +325,10 @@ metadata:
name: nginx
spec:
controllerName: gateway.nginx.org/nginx-gateway-controller
parametersRef:
group: gateway.nginx.org
kind: NginxProxy
name: nginx-gateway-proxy-config
---
apiVersion: gateway.nginx.org/v1alpha1
kind: NginxGateway
Expand All @@ -338,3 +342,19 @@ metadata:
spec:
logging:
level: info
---
# Source: nginx-gateway-fabric/templates/nginxproxy.yaml
apiVersion: gateway.nginx.org/v1alpha1
kind: NginxProxy
metadata:
name: nginx-gateway-proxy-config
labels:
app.kubernetes.io/name: nginx-gateway
app.kubernetes.io/instance: nginx-gateway
app.kubernetes.io/version: "edge"
spec:
rewriteClientIP:
mode: ProxyProtocol
setIPRecursively: true
trustedAddresses:
- 0.0.0.0/0
20 changes: 20 additions & 0 deletions deploy/nodeport/deploy.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -319,6 +319,10 @@ metadata:
name: nginx
spec:
controllerName: gateway.nginx.org/nginx-gateway-controller
parametersRef:
group: gateway.nginx.org
kind: NginxProxy
name: nginx-gateway-proxy-config
---
apiVersion: gateway.nginx.org/v1alpha1
kind: NginxGateway
Expand All @@ -332,3 +336,19 @@ metadata:
spec:
logging:
level: info
---
# Source: nginx-gateway-fabric/templates/nginxproxy.yaml
apiVersion: gateway.nginx.org/v1alpha1
kind: NginxProxy
metadata:
name: nginx-gateway-proxy-config
labels:
app.kubernetes.io/name: nginx-gateway
app.kubernetes.io/instance: nginx-gateway
app.kubernetes.io/version: "edge"
spec:
rewriteClientIP:
mode: ProxyProtocol
setIPRecursively: true
trustedAddresses:
- 0.0.0.0/0
15 changes: 12 additions & 3 deletions internal/mode/static/nginx/config/http/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -109,13 +109,22 @@ type ProxySSLVerify struct {

// ServerConfig holds configuration for an HTTP server and IP family to be used by NGINX.
type ServerConfig struct {
Servers []Server
IPFamily shared.IPFamily
Plus bool
Servers []Server
RewriteClientIP RewriteClientIPSettings
IPFamily shared.IPFamily
Plus bool
}

// Include defines a file that's included via the include directive.
type Include struct {
Name string
Content []byte
}

// RewriteClientIP holds the configuration for the rewrite client IP settings.
type RewriteClientIPSettings struct {
RealIPHeader string
RealIPFrom []string
Recursive bool
ProxyProtocol bool
}
Loading

0 comments on commit 8835f3a

Please sign in to comment.