/** * Authenticated Layout Route * * Guards all child routes by requiring valid authentication. * Redirects to login if no valid token exists. * * When running inside WP admin (VITE_WP_EMBED=true), performs a one-shot * bootstrap + connect handshake against the WP plugin + customer-api so * the tenant_sync_auth binding is populated without a visible setup step. * * @layer Presentation - Routes */ import { useEffect } from 'react'; import { createFileRoute, Outlet, redirect } from '@tanstack/react-router'; import { tokenStorage } from '@/infrastructure/storage/LocalTokenStorage'; import { authenticatedUserStore } from '@/infrastructure/storage/AuthenticatedUserStore'; import { getWpDomain, isWordpressEmbed, wpConnectSync, wpSyncCdnUrl } from '@/lib/wp-integration'; import { tenantsApi } from '@/infrastructure/http/api/tenant'; export const Route = createFileRoute('/_authenticated')({ beforeLoad: async ({ location }) => { const authed = authenticatedUserStore.get(); if (!tokenStorage.hasTokens() || !authed?.companyId) { tokenStorage.removeTokens(); authenticatedUserStore.clear(); throw redirect({ to: '/login', search: { redirect: location.pathname, }, }); } }, component: AuthenticatedLayout, }); function AuthenticatedLayout() { useEffect(() => { // Always sync CDN URL (cheap, idempotent) wpSyncCdnUrl(); // WP embed: auto-connect the tenant whose domain matches the WP site if (!isWordpressEmbed()) return; const wpDomain = getWpDomain(); if (!wpDomain) return; const companyId = authenticatedUserStore.get()?.companyId; if (!companyId) return; (async () => { try { const { tenants } = await tenantsApi.listTenants(companyId); const match = tenants.find((t) => t.domain === wpDomain); if (match) { await wpConnectSync(match.id, match.domain); } } catch { // Non-fatal — user can retry from the TenantDetail WP sync card } })(); }, []); return ; }