mirror of
https://github.com/MODSetter/SurfSense.git
synced 2026-07-20 23:21:06 +02:00
157 lines
5.4 KiB
TypeScript
157 lines
5.4 KiB
TypeScript
import type { Metadata, Viewport } from "next";
|
|
import "./globals.css";
|
|
import { RootProvider } from "fumadocs-ui/provider/next";
|
|
import { Roboto } from "next/font/google";
|
|
import Script from "next/script";
|
|
import { AnnouncementToastProvider } from "@/components/announcements/AnnouncementToastProvider";
|
|
import { DesktopUpdateToast } from "@/components/desktop/desktop-update-toast";
|
|
import { AuthCutoverPurge } from "@/components/providers/AuthCutoverPurge";
|
|
import { GlobalLoadingProvider } from "@/components/providers/GlobalLoadingProvider";
|
|
import { I18nProvider } from "@/components/providers/I18nProvider";
|
|
import { PostHogProvider } from "@/components/providers/PostHogProvider";
|
|
import { ZeroProvider } from "@/components/providers/ZeroProvider";
|
|
import {
|
|
OrganizationJsonLd,
|
|
SoftwareApplicationJsonLd,
|
|
WebSiteJsonLd,
|
|
} from "@/components/seo/json-ld";
|
|
import { ThemeProvider } from "@/components/theme/theme-provider";
|
|
import { Toaster } from "@/components/ui/sonner";
|
|
import { LocaleProvider } from "@/contexts/LocaleContext";
|
|
import { PlatformProvider } from "@/contexts/platform-context";
|
|
import { BUILD_TIME_AUTH_TYPE } from "@/lib/env-config";
|
|
import { ReactQueryClientProvider } from "@/lib/query-client/query-client.provider";
|
|
import { getRuntimeAuthInitScript, resolveRuntimeAuthUiMode } from "@/lib/runtime-auth-config";
|
|
import { cn } from "@/lib/utils";
|
|
|
|
const roboto = Roboto({
|
|
subsets: ["latin"],
|
|
weight: ["400", "500", "700"],
|
|
display: "swap",
|
|
variable: "--font-roboto",
|
|
});
|
|
|
|
/**
|
|
* Viewport configuration for mobile keyboard handling.
|
|
* - interactiveWidget: 'resizes-content' tells mobile browsers (especially Chrome Android)
|
|
* to resize the CSS layout viewport when the virtual keyboard opens, so sticky elements
|
|
* (like the chat input bar) stay visible above the keyboard.
|
|
* - viewportFit: 'cover' enables env(safe-area-inset-*) for notched/home-indicator devices.
|
|
*/
|
|
export const viewport: Viewport = {
|
|
width: "device-width",
|
|
initialScale: 1,
|
|
viewportFit: "cover",
|
|
interactiveWidget: "resizes-content",
|
|
};
|
|
|
|
export const metadata: Metadata = {
|
|
metadataBase: new URL("https://www.surfsense.com"),
|
|
alternates: {
|
|
canonical: "https://www.surfsense.com",
|
|
},
|
|
title: "SurfSense - NotebookLM for Open Web Research",
|
|
description:
|
|
"SurfSense is an open-source open web research platform. Your AI agents research the live web with structured data from Reddit, YouTube, Amazon, Google Maps, Google Search, and any page, through one API or MCP server.",
|
|
keywords: [
|
|
"open web research platform",
|
|
"web research for AI agents",
|
|
"live web data for agents",
|
|
"web scraping API",
|
|
"reddit scraper api",
|
|
"youtube scraper api",
|
|
"deep research agent",
|
|
"mcp server",
|
|
"agent harness",
|
|
"open source NotebookLM alternative",
|
|
"SurfSense",
|
|
],
|
|
openGraph: {
|
|
title: "SurfSense - NotebookLM for Open Web Research",
|
|
description:
|
|
"SurfSense is an open-source open web research platform. Your AI agents research the live web with structured data from Reddit, YouTube, Amazon, Google Maps, Google Search, and any page, through one API or MCP server.",
|
|
url: "https://www.surfsense.com",
|
|
siteName: "SurfSense",
|
|
type: "website",
|
|
images: [
|
|
{
|
|
url: "/og-image.png",
|
|
width: 1200,
|
|
height: 630,
|
|
alt: "SurfSense - Open Web Research Platform for AI Agents",
|
|
},
|
|
],
|
|
locale: "en_US",
|
|
},
|
|
twitter: {
|
|
card: "summary_large_image",
|
|
title: "SurfSense - NotebookLM for Open Web Research",
|
|
description:
|
|
"SurfSense is an open-source open web research platform. Your AI agents research the live web with structured data from Reddit, YouTube, Amazon, Google Maps, Google Search, and any page, through one API or MCP server.",
|
|
creator: "@SurfSenseAI",
|
|
site: "@SurfSenseAI",
|
|
images: [
|
|
{
|
|
url: "/og-image-twitter.png",
|
|
width: 1200,
|
|
height: 630,
|
|
alt: "SurfSense - Open Web Research Platform for AI Agents",
|
|
},
|
|
],
|
|
},
|
|
};
|
|
|
|
export default function RootLayout({
|
|
children,
|
|
}: Readonly<{
|
|
children: React.ReactNode;
|
|
}>) {
|
|
// Using client-side i18n
|
|
// Language can be switched dynamically through LanguageSwitcher component
|
|
// Locale state is managed by LocaleContext and persisted in localStorage
|
|
return (
|
|
<html
|
|
lang="en"
|
|
data-surfsense-auth-type={resolveRuntimeAuthUiMode(BUILD_TIME_AUTH_TYPE)}
|
|
suppressHydrationWarning
|
|
>
|
|
<head>
|
|
<Script id="surfsense-runtime-auth-init" strategy="beforeInteractive">
|
|
{getRuntimeAuthInitScript(BUILD_TIME_AUTH_TYPE)}
|
|
</Script>
|
|
<link rel="preconnect" href="https://api.github.com" />
|
|
<OrganizationJsonLd />
|
|
<WebSiteJsonLd />
|
|
<SoftwareApplicationJsonLd />
|
|
</head>
|
|
<body className={cn(roboto.className, "bg-main-panel antialiased h-full w-full ")}>
|
|
<PostHogProvider>
|
|
<LocaleProvider>
|
|
<I18nProvider>
|
|
<ThemeProvider
|
|
attribute="class"
|
|
enableSystem
|
|
disableTransitionOnChange
|
|
defaultTheme="system"
|
|
>
|
|
<PlatformProvider>
|
|
<RootProvider>
|
|
<ReactQueryClientProvider>
|
|
<AuthCutoverPurge />
|
|
<ZeroProvider>
|
|
<GlobalLoadingProvider>{children}</GlobalLoadingProvider>
|
|
</ZeroProvider>
|
|
</ReactQueryClientProvider>
|
|
<DesktopUpdateToast />
|
|
<Toaster />
|
|
<AnnouncementToastProvider />
|
|
</RootProvider>
|
|
</PlatformProvider>
|
|
</ThemeProvider>
|
|
</I18nProvider>
|
|
</LocaleProvider>
|
|
</PostHogProvider>
|
|
</body>
|
|
</html>
|
|
);
|
|
}
|