rdobuilder 74698f
From 18872bf5807c96e78dc25b420fac54ac7c09e4a8 Mon Sep 17 00:00:00 2001
rdobuilder 74698f
From: =?UTF-8?q?Harald=20Jens=C3=A5s?= <hjensas@redhat.com>
rdobuilder 74698f
Date: Mon, 18 Oct 2021 20:09:29 +0200
rdobuilder 74698f
Subject: [PATCH] ProxyFix supports IPv6
rdobuilder 74698f
rdobuilder 74698f
---
rdobuilder 74698f
 src/werkzeug/middleware/proxy_fix.py | 14 +++++++-------
rdobuilder 74698f
 tests/middleware/test_proxy_fix.py   | 18 ++++++++++++++++++
rdobuilder 74698f
 2 files changed, 25 insertions(+), 7 deletions(-)
rdobuilder 74698f
rdobuilder 74698f
diff --git a/src/werkzeug/middleware/proxy_fix.py b/src/werkzeug/middleware/proxy_fix.py
rdobuilder 74698f
index e90b1b34..4cef7cc8 100644
rdobuilder 74698f
--- a/src/werkzeug/middleware/proxy_fix.py
rdobuilder 74698f
+++ b/src/werkzeug/middleware/proxy_fix.py
rdobuilder 74698f
@@ -163,18 +163,18 @@ class ProxyFix:
rdobuilder 74698f
 
rdobuilder 74698f
         x_host = self._get_real_value(self.x_host, environ_get("HTTP_X_FORWARDED_HOST"))
rdobuilder 74698f
         if x_host:
rdobuilder 74698f
-            environ["HTTP_HOST"] = x_host
rdobuilder 74698f
-            parts = x_host.split(":", 1)
rdobuilder 74698f
-            environ["SERVER_NAME"] = parts[0]
rdobuilder 74698f
-            if len(parts) == 2:
rdobuilder 74698f
-                environ["SERVER_PORT"] = parts[1]
rdobuilder 74698f
+            environ["HTTP_HOST"] = environ["SERVER_NAME"] = x_host
rdobuilder 74698f
+            # "]" to check for IPv6 address without port
rdobuilder 74698f
+            if ":" in x_host and not x_host.endswith("]"):
rdobuilder 74698f
+                environ["SERVER_NAME"], environ["SERVER_PORT"] = x_host.rsplit(":", 1)
rdobuilder 74698f
 
rdobuilder 74698f
         x_port = self._get_real_value(self.x_port, environ_get("HTTP_X_FORWARDED_PORT"))
rdobuilder 74698f
         if x_port:
rdobuilder 74698f
             host = environ.get("HTTP_HOST")
rdobuilder 74698f
             if host:
rdobuilder 74698f
-                parts = host.split(":", 1)
rdobuilder 74698f
-                host = parts[0] if len(parts) == 2 else host
rdobuilder 74698f
+                # "]" to check for IPv6 address without port
rdobuilder 74698f
+                if ":" in host and not host.endswith("]"):
rdobuilder 74698f
+                    host = host.rsplit(":", 1)[0]
rdobuilder 74698f
                 environ["HTTP_HOST"] = f"{host}:{x_port}"
rdobuilder 74698f
             environ["SERVER_PORT"] = x_port
rdobuilder 74698f
 
rdobuilder 74698f
diff --git a/tests/middleware/test_proxy_fix.py b/tests/middleware/test_proxy_fix.py
rdobuilder 74698f
index 8fc1310d..abbc05c3 100644
rdobuilder 74698f
--- a/tests/middleware/test_proxy_fix.py
rdobuilder 74698f
+++ b/tests/middleware/test_proxy_fix.py
rdobuilder 74698f
@@ -138,6 +138,24 @@ from werkzeug.wrappers import Request
rdobuilder 74698f
             "http://spam/eggs/",
rdobuilder 74698f
             id="prefix < for",
rdobuilder 74698f
         ),
rdobuilder 74698f
+        pytest.param(
rdobuilder 74698f
+            {"x_host": 1},
rdobuilder 74698f
+            {"HTTP_HOST": "spam", "HTTP_X_FORWARDED_HOST": "[2001:db8::a]"},
rdobuilder 74698f
+            "http://[2001:db8::a]/",
rdobuilder 74698f
+            id="ipv6 host",
rdobuilder 74698f
+        ),
rdobuilder 74698f
+        pytest.param(
rdobuilder 74698f
+            {"x_port": 1},
rdobuilder 74698f
+            {"HTTP_HOST": "[2001:db8::a]", "HTTP_X_FORWARDED_PORT": "8080"},
rdobuilder 74698f
+            "http://[2001:db8::a]:8080/",
rdobuilder 74698f
+            id="ipv6 port, host without port",
rdobuilder 74698f
+        ),
rdobuilder 74698f
+        pytest.param(
rdobuilder 74698f
+            {"x_port": 1},
rdobuilder 74698f
+            {"HTTP_HOST": "[2001:db8::a]:9000", "HTTP_X_FORWARDED_PORT": "8080"},
rdobuilder 74698f
+            "http://[2001:db8::a]:8080/",
rdobuilder 74698f
+            id="ipv6 - port, host with port",
rdobuilder 74698f
+        ),
rdobuilder 74698f
     ),
rdobuilder 74698f
 )
rdobuilder 74698f
 def test_proxy_fix(kwargs, base, url_root):
rdobuilder 74698f
-- 
rdobuilder 74698f
2.34.1
rdobuilder 74698f