from __future__ import annotations import os import subprocess import sys from pathlib import Path import pytest from django.core.exceptions import ImproperlyConfigured from config.settings import normalize_public_base_url from scripts.configure_public_url import ConfigurationError, configure_env, normalize_public_url @pytest.mark.parametrize( ("raw", "origin", "host"), [ ( "https://vacatureradar.itworx.tech/", "https://vacatureradar.itworx.tech", "vacatureradar.itworx.tech", ), ("https://jobs.example.be:8443", "https://jobs.example.be:8443", "jobs.example.be"), ("http://127.0.0.1:1226", "http://127.0.0.1:1226", "127.0.0.1"), ], ) def test_public_url_normalization(raw, origin, host): assert normalize_public_base_url(raw) == (origin, host) assert normalize_public_url(raw) == (origin, host) @pytest.mark.parametrize( "raw", [ "vacatureradar.itworx.tech", "ftp://vacatureradar.itworx.tech", "https://user:secret@example.org", "https://example.org/app", "https://example.org?debug=1", ], ) def test_public_url_rejects_unsafe_or_unsupported_values(raw): with pytest.raises((ImproperlyConfigured, ConfigurationError)): normalize_public_base_url(raw) def test_configure_public_url_updates_only_public_security_settings(tmp_path: Path): env_file = tmp_path / ".env" env_file.write_text( "DJANGO_SECRET_KEY=keep-this-secret\n" "POSTGRES_PASSWORD=keep-this-password\n" "DJANGO_ALLOWED_HOSTS=192.168.10.150,localhost\n" "DJANGO_CSRF_TRUSTED_ORIGINS=http://192.168.10.150:1226\n", encoding="utf-8", ) changed = configure_env( env_file, "https://vacatureradar.itworx.tech/", hsts_seconds=300, cache_url="redis://127.0.0.1:6379/1", trusted_proxy_cidrs=["172.18.0.0/16"], ) content = env_file.read_text(encoding="utf-8") assert "PUBLIC_BASE_URL=https://vacatureradar.itworx.tech" in content assert "DJANGO_DEBUG=0" in content assert "vacatureradar.itworx.tech" in content assert ( "DJANGO_CSRF_TRUSTED_ORIGINS=http://192.168.10.150:1226,https://vacatureradar.itworx.tech" ) in content assert "CACHE_URL=redis://127.0.0.1:6379/1" in content assert "TRUSTED_PROXY_CIDRS=172.18.0.0/16" in content assert "DJANGO_SECRET_KEY=keep-this-secret" in content assert "POSTGRES_PASSWORD=keep-this-password" in content if os.name != "nt": assert env_file.stat().st_mode & 0o777 == 0o600 assert "DJANGO_SECRET_KEY" not in changed def test_configure_public_url_rejects_plain_http(tmp_path: Path): with pytest.raises(ConfigurationError, match="HTTPS"): configure_env(tmp_path / ".env", "http://vacatureradar.example.be") def test_public_base_url_populates_django_host_and_csrf_settings(): environment = os.environ.copy() environment.update( { "DJANGO_SECRET_KEY": "aB3!" * 16, "DJANGO_DEBUG": "0", "PUBLIC_BASE_URL": "https://vacatureradar.itworx.tech", "DEMO_MODE_ENABLED": "0", "SECURE_HSTS_SECONDS": "300", } ) result = subprocess.run( # noqa: S603 - fixed interpreter and static assertion program [ sys.executable, "-c", ( "import config.settings as settings; " "assert 'vacatureradar.itworx.tech' in settings.ALLOWED_HOSTS; " "assert 'https://vacatureradar.itworx.tech' " "in settings.CSRF_TRUSTED_ORIGINS; " "assert settings.DEBUG is False; " "assert settings.SESSION_COOKIE_SECURE is True; " "assert settings.CSRF_COOKIE_SECURE is True; " "assert settings.SECURE_SSL_REDIRECT is True" ), ], cwd=Path(__file__).resolve().parents[2], env=environment, capture_output=True, text=True, check=False, ) assert result.returncode == 0, result.stderr def test_configure_public_url_is_idempotent(tmp_path: Path): env_file = tmp_path / ".env" env_file.write_text("DJANGO_ALLOWED_HOSTS=localhost\n", encoding="utf-8") for _ in range(2): configure_env(env_file, "https://vacatureradar.example.be") content = env_file.read_text(encoding="utf-8") assert content.count("PUBLIC_BASE_URL=") == 1 assert content.count("vacatureradar.example.be") == 3