From e8a2dd29790d84b9176671277443479f560bbeec Mon Sep 17 00:00:00 2001 From: cyph3rasi Date: Tue, 14 Jul 2026 22:06:26 -0700 Subject: [PATCH] Update visible node settings immediately after admin saves Hop-State: A_06FP8ATA10D8VTQA9QBS6KR Hop-Proposal: R_06FP8ASAVWCYV52CHF5AE1G Hop-Task: T_06FP8AC8PWCNKR7C8686AXG Hop-Attempt: AT_06FP8AC8PXWTNRRHT6JBPMG --- src/app/admin/page.tsx | 4 ++++ src/components/RightSidebar.tsx | 36 +++++++++++++++++++++++++++++++-- src/components/Sidebar.tsx | 15 +++++++++++++- 3 files changed, 52 insertions(+), 3 deletions(-) diff --git a/src/app/admin/page.tsx b/src/app/admin/page.tsx index 7fc73eb..e17367e 100644 --- a/src/app/admin/page.tsx +++ b/src/app/admin/page.tsx @@ -91,6 +91,10 @@ export default function AdminPage() { body: JSON.stringify(payload), }); if (res.ok) { + const data = await res.json().catch(() => ({})); + if (data.node) { + window.dispatchEvent(new CustomEvent('synapsis:node-updated', { detail: data.node })); + } showToast('Settings saved!', 'success'); refreshAccentColor(); } else { diff --git a/src/components/RightSidebar.tsx b/src/components/RightSidebar.tsx index 7b441a6..62d2658 100644 --- a/src/components/RightSidebar.tsx +++ b/src/components/RightSidebar.tsx @@ -10,9 +10,18 @@ interface Admin { avatarUrl: string | null; } +interface NodeInfo { + name: string; + description: string; + longDescription: string; + rules: string; + bannerUrl: string; + admins: Admin[]; +} + export function RightSidebar() { const fallbackDescription = process.env.NEXT_PUBLIC_NODE_DESCRIPTION || 'A swarm social network node.'; - const [nodeInfo, setNodeInfo] = useState({ + const [nodeInfo, setNodeInfo] = useState({ name: process.env.NEXT_PUBLIC_NODE_NAME || 'Synapsis Node', description: fallbackDescription, longDescription: '', @@ -28,7 +37,7 @@ export function RightSidebar() { const [loading, setLoading] = useState(true); useEffect(() => { - fetch('/api/node', { cache: 'no-store' }) + const loadNodeInfo = () => fetch('/api/node', { cache: 'no-store' }) .then(res => res.json()) .then(data => { setNodeInfo(prev => ({ @@ -45,11 +54,34 @@ export function RightSidebar() { .catch(() => { }) .finally(() => setLoading(false)); + const handleNodeUpdated = (event: Event) => { + const updatedNode = (event as CustomEvent>).detail; + if (!updatedNode) { + void loadNodeInfo(); + return; + } + setNodeInfo(prev => ({ + ...prev, + ...updatedNode, + name: updatedNode.name ?? prev.name, + description: updatedNode.description ?? prev.description, + longDescription: updatedNode.longDescription ?? prev.longDescription, + rules: updatedNode.rules ?? prev.rules, + bannerUrl: updatedNode.bannerUrl ?? prev.bannerUrl, + admins: updatedNode.admins ?? prev.admins, + })); + }; + + void loadNodeInfo(); + window.addEventListener('synapsis:node-updated', handleNodeUpdated); + // Fetch version info fetch('/api/version') .then(res => res.json()) .then(data => setVersion(data)) .catch(() => setVersion({ version: 'unknown', buildDate: null })); + + return () => window.removeEventListener('synapsis:node-updated', handleNodeUpdated); }, []); if (loading) { diff --git a/src/components/Sidebar.tsx b/src/components/Sidebar.tsx index 0348b79..831e404 100644 --- a/src/components/Sidebar.tsx +++ b/src/components/Sidebar.tsx @@ -36,7 +36,7 @@ export function Sidebar() { const formattedHandle = user ? shortHandle(user.handle) : ''; useEffect(() => { - fetch('/api/node') + const loadLogo = () => fetch('/api/node', { cache: 'no-store' }) .then(res => res.json()) .then(data => { setCustomLogoUrl(data.logoUrl || null); @@ -44,6 +44,19 @@ export function Sidebar() { .catch(() => { setCustomLogoUrl(null); }); + + const handleNodeUpdated = (event: Event) => { + const updatedNode = (event as CustomEvent<{ logoUrl?: string | null }>).detail; + if (updatedNode && 'logoUrl' in updatedNode) { + setCustomLogoUrl(updatedNode.logoUrl || null); + return; + } + void loadLogo(); + }; + + void loadLogo(); + window.addEventListener('synapsis:node-updated', handleNodeUpdated); + return () => window.removeEventListener('synapsis:node-updated', handleNodeUpdated); }, []); const fetchUnreadNotifications = useCallback(() => {