diff --git a/src/App.tsx b/src/App.tsx index 1c815e6..5badc03 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -1,15 +1,17 @@ /* - * SPDX-FileCopyrightText: 2020 Stalwart Labs LLC + * SPDX-FileCopyrightText: 2026 Coffey Labs LLC * - * SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-SEL + * SPDX-License-Identifier: AGPL-3.0-only */ import { Suspense } from 'react'; import { Outlet } from 'react-router-dom'; -import { ErrorBoundary } from '@/components/layout/ErrorBoundary'; + import { LoadingFallback } from '@/components/common/LoadingFallback'; +import { ErrorBoundary } from '@/components/layout/ErrorBoundary'; import { Toaster } from '@/components/ui/toaster'; +/** Every route renders inside this: a crash screen, a loading screen while pages load, and toasts. */ export default function App() { return ( diff --git a/src/components/common/EnterpriseUpsell.tsx b/src/components/common/EnterpriseUpsell.tsx deleted file mode 100644 index cf1c34b..0000000 --- a/src/components/common/EnterpriseUpsell.tsx +++ /dev/null @@ -1,24 +0,0 @@ -/* - * SPDX-FileCopyrightText: 2020 Stalwart Labs LLC - * SPDX-FileCopyrightText: 2026 Coffey Labs LLC - * - * SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-SEL - * - * Modified by Coffey Labs in 2026 for INBUXA. - */ - -interface EnterpriseUpsellProps { - open: boolean; - onClose: () => void; -} - -/** - * INBUXA: nothing to sell. There is one edition, every feature is in it, and - * the edition is never anything but complete (see accountStore), so this - * never opens. It stays as an empty component so the places upstream calls - * it from merge without conflicts. - */ -export function EnterpriseUpsell({ open }: EnterpriseUpsellProps) { - void open; - return null; -} diff --git a/src/components/common/LoadingFallback.tsx b/src/components/common/LoadingFallback.tsx index 5944f41..7d9d437 100644 --- a/src/components/common/LoadingFallback.tsx +++ b/src/components/common/LoadingFallback.tsx @@ -1,24 +1,23 @@ /* - * SPDX-FileCopyrightText: 2020 Stalwart Labs LLC * SPDX-FileCopyrightText: 2026 Coffey Labs LLC * - * SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-SEL - * - * Modified by Coffey Labs in 2026 for INBUXA. + * SPDX-License-Identifier: AGPL-3.0-only */ import { Loader2 } from 'lucide-react'; import { useTranslation } from 'react-i18next'; -import { cn } from '@/lib/utils'; -import inbuxaMark from '@/assets/inbuxa-mark.png'; +import inbuxaMark from '@/assets/inbuxa-mark.png'; +import { cn } from '@/lib/utils'; + +/** The bouncing cat and "Loading…", in a page's place or filling the screen. */ export function LoadingFallback({ fullScreen = false }: { fullScreen?: boolean }) { const { t } = useTranslation(); return (

- + {t('common.loading')}

diff --git a/src/components/common/Logo.tsx b/src/components/common/Logo.tsx index 91e3796..54ad0d9 100644 --- a/src/components/common/Logo.tsx +++ b/src/components/common/Logo.tsx @@ -1,16 +1,14 @@ /* - * SPDX-FileCopyrightText: 2020 Stalwart Labs LLC * SPDX-FileCopyrightText: 2026 Coffey Labs LLC * - * SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-SEL - * - * Modified by Coffey Labs in 2026 for INBUXA. + * SPDX-License-Identifier: AGPL-3.0-only */ import { useEffect, useSyncExternalStore } from 'react'; import { useTranslation } from 'react-i18next'; -import { getLogoState, loadLogoOnce, subscribeToLogo } from '@/lib/logoCache'; + import inbuxaMark from '@/assets/inbuxa-mark.png'; +import { getLogoState, loadLogoOnce, subscribeToLogo } from '@/lib/logoCache'; export function DefaultLogo() { const { t } = useTranslation(); @@ -58,21 +56,20 @@ export function DefaultLogo() { ); } +/** + * The server's own logo if an admin set one, else inbuxa's. Until the server + * answers, an empty space the logo's size holds the layout still. + */ export default function Logo() { const { t } = useTranslation(); const logo = useSyncExternalStore(subscribeToLogo, getLogoState, getLogoState); - - useEffect(() => { - loadLogoOnce(); - }, []); - - if (logo.status === 'custom') { - return {t('logo.alt',; + useEffect(loadLogoOnce, []); + switch (logo.status) { + case 'custom': + return {t('logo.alt',; + case 'loading': + return