// Initialize i18next BEFORE any component that calls useTranslation is loaded.
// react-i18next's useTranslation reads from the global i18next instance the
// moment a consumer mounts, so the side-effect init has to land before the
// providers below are imported.
import { StrictMode } from 'react'
import ReactDOM from 'react-dom/client'
import {
  QueryCache,
  QueryClient,
  QueryClientProvider,
} from '@tanstack/react-query'
import { RouterProvider, createRouter } from '@tanstack/react-router'
import i18nInstance from '@/i18n'
import { toast } from 'sonner'
import { handleServerError } from '@/lib/handle-server-error'
import { LanguageGate } from '@/components/language-gate'
import { PendingScreen } from '@/components/pending-screen'
import { AuthProvider } from './context/auth-provider'
import { FontProvider } from './context/font-provider'
import { LanguageProvider } from './context/language-provider'
import { StoreProvider } from './context/store-provider'
import { ThemeProvider } from './context/theme-provider'
// Generated Routes
import { routeTree } from './routeTree.gen'
// Styles
import './styles/index.css'

const queryClient = new QueryClient({
  defaultOptions: {
    queries: {
      retry: (failureCount) => {
        if (import.meta.env.DEV) return false
        return failureCount <= 3
      },
      refetchOnWindowFocus: import.meta.env.PROD,
      staleTime: 10 * 1000,
    },
    mutations: {
      onError: (error) => handleServerError(error),
    },
  },
  queryCache: new QueryCache({
    onError: (error) => {
      const status = (error as { status?: number })?.status
      if (status === 401) {
        toast.error(i18nInstance.t('toasts.sessionExpired'))
        // NOTE: deliberately no signOut() here. From Phase 1 onward a signed-out
        // client would still be holding an outbox of unsent sales; wiping the
        // session on a single 401 is how offline-first apps lose a day's work.
        // Re-authentication is prompted, never forced.
      }
      if (status === 500 && import.meta.env.PROD) {
        toast.error(i18nInstance.t('toasts.internalError'))
      }
    },
  }),
})

const router = createRouter({
  routeTree,
  context: { queryClient },
  defaultPreload: 'intent',
  defaultPreloadStaleTime: 0,
  // While a route's beforeLoad resolves (requireStore on a cold refresh), show
  // a pending UI rather than a blank screen.
  defaultPendingComponent: PendingScreen,
  defaultPendingMs: 100,
  defaultPendingMinMs: 200,
})

declare module '@tanstack/react-router' {
  interface Register {
    router: typeof router
  }
}

const rootElement = document.getElementById('root')!
if (!rootElement.innerHTML) {
  const root = ReactDOM.createRoot(rootElement)
  root.render(
    <StrictMode>
      <QueryClientProvider client={queryClient}>
        {/*
          LanguageProvider sits OUTSIDE LanguageGate: the gate itself calls
          setLanguage, and it needs direction/RTL applied the instant a choice
          is made. AuthProvider sits inside the gate so nothing hits the network
          before the user has told us what language to speak to them in.
        */}
        <LanguageProvider>
          <ThemeProvider>
            <FontProvider>
              <LanguageGate>
                <AuthProvider>
                  <StoreProvider>
                    <RouterProvider router={router} />
                  </StoreProvider>
                </AuthProvider>
              </LanguageGate>
            </FontProvider>
          </ThemeProvider>
        </LanguageProvider>
      </QueryClientProvider>
    </StrictMode>
  )
}
