69087988b1
Docker/1Panel 反代时 request.client.host 为 172.18.0.1;可信内网跳读取 X-Real-IP/X-Forwarded-For。 Co-authored-by: Cursor <cursoragent@cursor.com>
46 lines
1.4 KiB
Python
46 lines
1.4 KiB
Python
"""Tests for reverse-proxy client IP resolution."""
|
|
|
|
from unittest.mock import MagicMock
|
|
|
|
from server.utils.client_ip import get_client_ip
|
|
|
|
|
|
def _req(direct: str, headers: dict[str, str] | None = None):
|
|
request = MagicMock()
|
|
request.client = MagicMock(host=direct)
|
|
hdrs = headers or {}
|
|
|
|
def _get(key: str, default: str = "") -> str:
|
|
return hdrs.get(key, default)
|
|
|
|
request.headers.get = _get
|
|
return request
|
|
|
|
|
|
class TestGetClientIp:
|
|
def test_docker_bridge_uses_x_real_ip(self):
|
|
ip = get_client_ip(_req("172.18.0.1", {"X-Real-IP": "203.0.113.10"}))
|
|
assert ip == "203.0.113.10"
|
|
|
|
def test_docker_bridge_uses_xff_last(self):
|
|
ip = get_client_ip(_req("172.18.0.1", {"X-Forwarded-For": "10.0.0.1, 203.0.113.11"}))
|
|
assert ip == "203.0.113.11"
|
|
|
|
def test_public_direct_ignores_spoofed_headers(self):
|
|
ip = get_client_ip(_req("198.51.100.5", {"X-Real-IP": "10.0.0.1"}))
|
|
assert ip == "198.51.100.5"
|
|
|
|
def test_loopback_trusts_x_real_ip(self):
|
|
ip = get_client_ip(_req("127.0.0.1", {"X-Real-IP": "203.0.113.12"}))
|
|
assert ip == "203.0.113.12"
|
|
|
|
def test_no_headers_falls_back_to_direct(self):
|
|
ip = get_client_ip(_req("172.18.0.1", {}))
|
|
assert ip == "172.18.0.1"
|
|
|
|
def test_empty_direct_unknown(self):
|
|
request = MagicMock()
|
|
request.client = None
|
|
request.headers.get = lambda _k, d="": d
|
|
assert get_client_ip(request) == "unknown"
|