feat: auto-trigger clone after login redirect

This commit is contained in:
CREDO23 2026-01-27 09:38:52 +02:00
parent 1c98ba989d
commit 0ad59edda0
2 changed files with 37 additions and 11 deletions

View file

@ -27,6 +27,13 @@ function LoginContent() {
const error = searchParams.get("error"); const error = searchParams.get("error");
const message = searchParams.get("message"); const message = searchParams.get("message");
const logout = searchParams.get("logout"); const logout = searchParams.get("logout");
const returnUrl = searchParams.get("returnUrl");
// Save returnUrl to localStorage so it persists through OAuth flows (e.g., Google)
// This is read by TokenHandler after successful authentication
if (returnUrl) {
localStorage.setItem("surfsense_redirect_path", decodeURIComponent(returnUrl));
}
// Show registration success message // Show registration success message
if (registered === "true") { if (registered === "true") {

View file

@ -1,8 +1,8 @@
"use client"; "use client";
import { Copy, Loader2 } from "lucide-react"; import { Copy, Loader2 } from "lucide-react";
import { useRouter } from "next/navigation"; import { useRouter, useSearchParams } from "next/navigation";
import { useState } from "react"; import { useCallback, useEffect, useRef, useState } from "react";
import { toast } from "sonner"; import { toast } from "sonner";
import { Button } from "@/components/ui/button"; import { Button } from "@/components/ui/button";
import { publicChatApiService } from "@/lib/apis/public-chat-api.service"; import { publicChatApiService } from "@/lib/apis/public-chat-api.service";
@ -14,17 +14,11 @@ interface PublicChatFooterProps {
export function PublicChatFooter({ shareToken }: PublicChatFooterProps) { export function PublicChatFooter({ shareToken }: PublicChatFooterProps) {
const router = useRouter(); const router = useRouter();
const searchParams = useSearchParams();
const [isCloning, setIsCloning] = useState(false); const [isCloning, setIsCloning] = useState(false);
const hasAutoCloned = useRef(false);
const handleCopyAndContinue = async () => { const triggerClone = useCallback(async () => {
const token = getBearerToken();
if (!token) {
const returnUrl = encodeURIComponent(`/public/${shareToken}`);
router.push(`/login?returnUrl=${returnUrl}&action=clone`);
return;
}
setIsCloning(true); setIsCloning(true);
try { try {
@ -43,6 +37,31 @@ export function PublicChatFooter({ shareToken }: PublicChatFooterProps) {
} finally { } finally {
setIsCloning(false); setIsCloning(false);
} }
}, [shareToken, router]);
// Auto-trigger clone if user just logged in with action=clone
useEffect(() => {
const action = searchParams.get("action");
const token = getBearerToken();
// Only auto-clone once, if authenticated and action=clone is present
if (action === "clone" && token && !hasAutoCloned.current && !isCloning) {
hasAutoCloned.current = true;
triggerClone();
}
}, [searchParams, isCloning, triggerClone]);
const handleCopyAndContinue = async () => {
const token = getBearerToken();
if (!token) {
// Include action=clone in the returnUrl so it persists after login
const returnUrl = encodeURIComponent(`/public/${shareToken}?action=clone`);
router.push(`/login?returnUrl=${returnUrl}`);
return;
}
await triggerClone();
}; };
return ( return (