Support return_to redirect with token for iOS Safari
Login page accepts return_to URL. After login, redirects to return_to with auth_token in URL so target site can set its own first-party cookie (works around iOS Safari ITP). Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
31
server.py
31
server.py
@@ -358,8 +358,8 @@ def format_date(value, length: int = 10) -> str:
|
||||
# ============ Auth UI Endpoints ============
|
||||
|
||||
@app.get("/login", response_class=HTMLResponse)
|
||||
async def ui_login_page(request: Request):
|
||||
"""Login page."""
|
||||
async def ui_login_page(request: Request, return_to: str = None):
|
||||
"""Login page. Accepts optional return_to URL for redirect after login."""
|
||||
username = get_user_from_cookie(request)
|
||||
if username:
|
||||
return HTMLResponse(base_html("Already Logged In", f'''
|
||||
@@ -369,10 +369,14 @@ async def ui_login_page(request: Request):
|
||||
<p><a href="/" class="text-blue-400 hover:text-blue-300">Go to home page</a></p>
|
||||
''', username))
|
||||
|
||||
content = '''
|
||||
# Hidden field for return_to URL
|
||||
return_to_field = f'<input type="hidden" name="return_to" value="{return_to}">' if return_to else ''
|
||||
|
||||
content = f'''
|
||||
<h2 class="text-xl font-semibold text-white mb-6">Login</h2>
|
||||
<div id="login-result"></div>
|
||||
<form hx-post="/login" hx-target="#login-result" hx-swap="innerHTML" class="space-y-4 max-w-md">
|
||||
{return_to_field}
|
||||
<div>
|
||||
<label for="username" class="block text-sm font-medium text-gray-300 mb-2">Username</label>
|
||||
<input type="text" id="username" name="username" required
|
||||
@@ -398,6 +402,7 @@ async def ui_login_submit(request: Request):
|
||||
form = await request.form()
|
||||
username = form.get("username", "").strip()
|
||||
password = form.get("password", "")
|
||||
return_to = form.get("return_to", "").strip()
|
||||
|
||||
if not username or not password:
|
||||
return HTMLResponse('<div class="bg-red-900/50 border border-red-700 text-red-300 px-4 py-3 rounded-lg mb-4">Username and password are required</div>')
|
||||
@@ -408,10 +413,22 @@ async def ui_login_submit(request: Request):
|
||||
|
||||
token = create_access_token(user.username, l2_server=f"https://{DOMAIN}")
|
||||
|
||||
response = HTMLResponse(f'''
|
||||
<div class="bg-green-900/50 border border-green-700 text-green-300 px-4 py-3 rounded-lg mb-4">Login successful! Redirecting...</div>
|
||||
<script>window.location.href = "/";</script>
|
||||
''')
|
||||
# If return_to is specified, redirect there with token for the other site to set its own cookie
|
||||
if return_to and return_to.startswith("http"):
|
||||
# Append token to return_to URL for the target site to set its own cookie
|
||||
separator = "&" if "?" in return_to else "?"
|
||||
redirect_url = f"{return_to}{separator}auth_token={token.access_token}"
|
||||
response = HTMLResponse(f'''
|
||||
<div class="bg-green-900/50 border border-green-700 text-green-300 px-4 py-3 rounded-lg mb-4">Login successful! Redirecting...</div>
|
||||
<script>window.location.href = "{redirect_url}";</script>
|
||||
''')
|
||||
else:
|
||||
response = HTMLResponse(f'''
|
||||
<div class="bg-green-900/50 border border-green-700 text-green-300 px-4 py-3 rounded-lg mb-4">Login successful! Redirecting...</div>
|
||||
<script>window.location.href = "/";</script>
|
||||
''')
|
||||
|
||||
# Always set cookie on L2 as well
|
||||
response.set_cookie(
|
||||
key="auth_token",
|
||||
value=token.access_token,
|
||||
|
||||
Reference in New Issue
Block a user