From c57828eb62334e274a3f3d608d0c4ac854e40c8f Mon Sep 17 00:00:00 2001 From: Shivaram Lingamneni Date: Thu, 19 Nov 2020 17:01:56 -0500 Subject: [PATCH] documentation updates for proxy v2 --- default.yaml | 5 ++--- docs/MANUAL.md | 19 ++++++++++++++++--- irc/utils/proxy.go | 2 -- traditional.yaml | 5 ++--- 4 files changed, 20 insertions(+), 11 deletions(-) diff --git a/default.yaml b/default.yaml index b31cb0d0..063e736b 100644 --- a/default.yaml +++ b/default.yaml @@ -53,9 +53,8 @@ server: cert: fullchain.pem key: privkey.pem # 'proxy' should typically be false. It's for cloud load balancers that - # always send PROXY headers ahead of the connection (e.g., a v1 header - # ahead of unterminated TLS, or a v2 binary header) that MUST be present - # and cannot be processed on an optional basis. + # always send a PROXY protocol header ahead of the connection. See the + # manual ("Reverse proxies") for more details. proxy: false # Example of a Unix domain socket for proxying: diff --git a/docs/MANUAL.md b/docs/MANUAL.md index 40a7e28a..55541ffb 100644 --- a/docs/MANUAL.md +++ b/docs/MANUAL.md @@ -497,10 +497,23 @@ Many clients do not have this support. However, you can designate port 6667 as a ## Reverse proxies -You may want to configure a reverse proxy, such as nginx, for TLS termination --- for example, because you need to support versions of the TLS protocol that are not implemented natively by Go, or because you want to consolidate your certificate management into a single nginx instance. Oragono supports the [PROXY protocol](https://www.haproxy.org/download/1.8/doc/proxy-protocol.txt) for preserving the end user's IP in this case. To configure a reverse proxy, use the following steps: +Oragono supports the use of reverse proxies (such as nginx, or a Kubernetes [LoadBalancer](https://kubernetes.io/docs/concepts/services-networking/service/#loadbalancer)) that sit between it and the client. In these deployments, the [PROXY protocol](https://www.haproxy.org/download/1.8/doc/proxy-protocol.txt) is used to pass the end user's IP through to Oragono. These proxies can be used to terminate TLS externally to Oragono, e.g., if you need to support versions of the TLS protocol that are not implemented natively by Go, or if you want to consolidate your certificate management into a single nginx instance. + +The first step is to add the reverse proxy's IP to `proxy-allowed-from` and `ip-limits.exempted`. (Use `localhost` to exempt all loopback IPs and Unix domain sockets.) + +After that, there are two possibilities: + +* If you're using a proxy like nginx or stunnel that terminates TLS, then forwards a PROXY v1 (ASCII) header ahead of a plaintext connection, no further Oragono configuration is required. You need only configure your proxy to send the PROXY header. Here's an [example nginx config](https://github.com/oragono/testnet.oragono.io/blob/master/nginx_stream.conf). +* If you're using a cloud load balancer that either sends a PROXY v1 header ahead of unterminated TLS (like [DigitalOcean](https://www.digitalocean.com/docs/networking/load-balancers/#proxy-protocol)) or sends a PROXY v2 (binary) header (like the [AWS "Network Load Balancer"](https://docs.aws.amazon.com/elasticloadbalancing/latest/network/load-balancer-target-groups.html#proxy-protocol)), Oragono must be configured to expect a PROXY header ahead of the connection. Add `proxy: true` to the listener config block, e.g., + +```yaml + ":6697": + tls: + cert: fullchain.pem + key: privkey.pem + proxy: true +``` -1. Add the reverse proxy's IP to `proxy-allowed-from` and `ip-limits.exempted`. (Use `localhost` to exempt all loopback IPs and Unix domain sockets.) -1. Configure your reverse proxy to connect to an appropriate Oragono listener and send the PROXY line. In this [example nginx config](https://github.com/darwin-network/slash/commit/aae9ba08d70128eb4b700cade333fe824a53562d), nginx connects to Oragono via a Unix domain socket. ## Client certificates diff --git a/irc/utils/proxy.go b/irc/utils/proxy.go index b471c185..5b14be68 100644 --- a/irc/utils/proxy.go +++ b/irc/utils/proxy.go @@ -14,8 +14,6 @@ import ( "time" ) -// TODO: handle PROXY protocol v2 (the binary protocol) - const ( // https://www.haproxy.org/download/1.8/doc/proxy-protocol.txt // "a 108-byte buffer is always enough to store all the line and a trailing zero diff --git a/traditional.yaml b/traditional.yaml index 3e96bc17..b836de48 100644 --- a/traditional.yaml +++ b/traditional.yaml @@ -27,9 +27,8 @@ server: cert: fullchain.pem key: privkey.pem # 'proxy' should typically be false. It's for cloud load balancers that - # always send PROXY headers ahead of the connection (e.g., a v1 header - # ahead of unterminated TLS, or a v2 binary header) that MUST be present - # and cannot be processed on an optional basis. + # always send a PROXY protocol header ahead of the connection. See the + # manual ("Reverse proxies") for more details. proxy: false # Example of a Unix domain socket for proxying: