auth: Only automatically redirect for same domain redirects.

If the `deactivated_redirect` belongs to the same domain as
`EXTERNAL_HOST`, automatically redirect, otherwise just point
user to the new URL.
This commit is contained in:
Aman Agrawal
2025-06-18 19:38:48 +05:30
committed by Tim Abbott
parent ba32e732c7
commit 9b15dce1b2
6 changed files with 71 additions and 19 deletions

View File

@@ -3,7 +3,7 @@ import secrets
from collections.abc import Callable, Mapping
from functools import wraps
from typing import TYPE_CHECKING, Any, Concatenate, TypeAlias, cast
from urllib.parse import urlencode, urljoin
from urllib.parse import urlencode, urljoin, urlsplit
import jwt
import orjson
@@ -63,7 +63,11 @@ from zerver.lib.realm_icon import realm_icon_url
from zerver.lib.request import RequestNotes
from zerver.lib.response import json_success
from zerver.lib.sessions import set_expirable_session_var
from zerver.lib.subdomains import get_subdomain, is_subdomain_root_or_alias
from zerver.lib.subdomains import (
get_subdomain,
get_subdomain_from_hostname,
is_subdomain_root_or_alias,
)
from zerver.lib.typed_endpoint import typed_endpoint
from zerver.lib.url_encoding import append_url_query_string
from zerver.lib.user_agent import parse_user_agent
@@ -820,16 +824,21 @@ def redirect_to_misconfigured_ldap_notice(request: HttpRequest, error_type: int)
def show_deactivation_notice(request: HttpRequest, next: str = "/") -> HttpResponse:
realm = get_realm_from_request(request)
if realm and realm.deactivated:
if realm.deactivated_redirect is not None:
# URL hash is automatically preserved by the browser.
# See https://stackoverflow.com/a/5283739
redirect_to = get_safe_redirect_to(next, realm.deactivated_redirect)
return HttpResponseRedirect(redirect_to)
realm_data_scrubbed = RealmAuditLog.objects.filter(
realm=realm, event_type=AuditLogEventType.REALM_SCRUBBED
).exists()
context = {"realm_data_deleted": realm_data_scrubbed}
context = {
"realm_data_deleted": realm_data_scrubbed,
"deactivated_redirect": realm.deactivated_redirect,
}
if realm.deactivated_redirect is not None:
split = urlsplit(realm.deactivated_redirect)
host = f"{split.scheme}://{split.netloc}"
# If the redirect is in the same domain, do an automatic redirect.
if get_subdomain_from_hostname(host) is not None:
redirect_to = get_safe_redirect_to(next, realm.deactivated_redirect)
context["auto_redirect_to"] = redirect_to
return render(request, "zerver/deactivated.html", context=context)
return HttpResponseRedirect(reverse("login_page"))