feat(events): stream Redis invalidations over SSE
This commit is contained in:
@@ -0,0 +1,34 @@
|
||||
"use client";
|
||||
|
||||
import { useRouter } from "next/navigation";
|
||||
import { useEffect } from "react";
|
||||
|
||||
import { parseInvalidationEvent } from "@/lib/events/invalidation";
|
||||
import { createRefreshScheduler } from "@/lib/events/refresh";
|
||||
|
||||
export function LiveRefresh({ endpoint }: { endpoint: string }) {
|
||||
const router = useRouter();
|
||||
|
||||
useEffect(() => {
|
||||
const scheduler = createRefreshScheduler(() => router.refresh());
|
||||
const source = new EventSource(endpoint);
|
||||
const connected = () => scheduler.connected();
|
||||
const notified = (message: Event) => {
|
||||
if (!(message instanceof MessageEvent) || typeof message.data !== "string") {
|
||||
return;
|
||||
}
|
||||
const event = parseInvalidationEvent(message.data);
|
||||
if (event) scheduler.notified(event);
|
||||
};
|
||||
source.addEventListener("open", connected);
|
||||
source.addEventListener("invalidation", notified);
|
||||
return () => {
|
||||
source.removeEventListener("open", connected);
|
||||
source.removeEventListener("invalidation", notified);
|
||||
source.close();
|
||||
scheduler.dispose();
|
||||
};
|
||||
}, [endpoint, router]);
|
||||
|
||||
return null;
|
||||
}
|
||||
@@ -7,6 +7,7 @@ import {
|
||||
} from "@/components/public/block-renderer";
|
||||
import { SectionDrawer } from "@/components/public/section-drawer";
|
||||
import { SiteHeader } from "@/components/public/site-header";
|
||||
import { LiveRefresh } from "@/components/live-refresh";
|
||||
import { Alert, AlertDescription, AlertTitle } from "@/components/ui/alert";
|
||||
import { Badge } from "@/components/ui/badge";
|
||||
import { Separator } from "@/components/ui/separator";
|
||||
@@ -18,6 +19,9 @@ export function GuideShell({ snapshot }: { snapshot: PageSnapshot }) {
|
||||
|
||||
return (
|
||||
<div className="min-h-svh bg-background">
|
||||
{process.env.BUZZ_DEMO_MODE === "true" ? null : (
|
||||
<LiveRefresh endpoint={`/api/events/page/${snapshot.page.id}`} />
|
||||
)}
|
||||
<SiteHeader />
|
||||
<div className="sticky top-0 z-30 border-b bg-background/95 supports-backdrop-filter:backdrop-blur">
|
||||
<div className="mx-auto w-full max-w-7xl px-4 sm:px-6">
|
||||
|
||||
Reference in New Issue
Block a user