ClauseGuard / web /components /extension-bridge.tsx
anky2002's picture
Refactor LoginPage to use Suspense for loading state and improve auth state handling in ExtensionBridge
59a9b47
"use client";
import { useEffect } from "react";
import { createClient } from "@/lib/supabase/client";
/**
* ExtensionBridge — syncs auth to Chrome extension.
* Uses window.postMessage which content script picks up.
* Handles: initial load, sign in, sign out, token refresh, tab switch.
*/
export function ExtensionBridge() {
const supabase = createClient();
function sendAuthToExtension(token: string, email: string, name: string, userId: string, plan: string) {
// Content script listens for this via window.addEventListener("message")
window.postMessage({
type: "CLAUSEGUARD_AUTH_SYNC",
token, email, name, userId, plan,
}, window.location.origin);
}
async function syncCurrentUser() {
try {
const { data: { user } } = await supabase.auth.getUser();
if (!user) {
sendAuthToExtension("", "", "", "", "free");
return;
}
const { data: { session } } = await supabase.auth.getSession();
if (!session) {
sendAuthToExtension("", "", "", "", "free");
return;
}
const { data: profile } = await supabase
.from("profiles")
.select("plan, full_name")
.eq("id", user.id)
.single();
sendAuthToExtension(
session.access_token,
user.email || "",
profile?.full_name || user.user_metadata?.full_name || user.user_metadata?.name || "",
user.id,
profile?.plan || "free",
);
} catch {}
}
useEffect(() => {
// Sync on initial page load (already logged in user opens new tab)
syncCurrentUser();
// Sync on every auth state change
const { data: { subscription } } = supabase.auth.onAuthStateChange(async (event, session) => {
// Handle ALL events that mean "user is logged in"
if (session && (event === "SIGNED_IN" || event === "INITIAL_SESSION" || event === "TOKEN_REFRESHED")) {
let profileData = null;
try {
const result = await supabase
.from("profiles")
.select("plan, full_name")
.eq("id", session.user.id)
.single();
profileData = result.data;
} catch {
// ignore
}
sendAuthToExtension(
session.access_token,
session.user.email || "",
profileData?.full_name || session.user.user_metadata?.full_name || "",
session.user.id,
profileData?.plan || "free",
);
}
if (event === "SIGNED_OUT") {
sendAuthToExtension("", "", "", "", "free");
}
});
// Also sync when tab becomes visible (user switches back to this tab)
function onVisible() {
if (document.visibilityState === "visible") syncCurrentUser();
}
document.addEventListener("visibilitychange", onVisible);
return () => {
subscription.unsubscribe();
document.removeEventListener("visibilitychange", onVisible);
};
}, []);
return null;
}