feat: nKode React + TypeScript SPA scaffold
- React + Vite + Tailwind CSS v4 + React Router - Keypad component: 10-digit pad with dot indicators, keyboard support, haptic feel - Auth pages: Login (email → keypad), Signup (email → method → keypad/key) - Home page: session info, practice keypad - Admin dashboard: placeholder stats + user management - Developer dashboard: OIDC client registration UI placeholder - WASM client wrapper: lazy loads from /wasm/, falls back to mock client - TypeScript type declarations for nkode-client-wasm package - Dark mode with system preference detection - Auth state management with localStorage persistence + auto-expiry - Code splitting: lazy-loaded route pages (~236KB main bundle) - Inter font, clean indigo/slate design system
This commit is contained in:
41
src/App.tsx
Normal file
41
src/App.tsx
Normal file
@@ -0,0 +1,41 @@
|
||||
import { lazy, Suspense } from 'react';
|
||||
import { BrowserRouter, Routes, Route } from 'react-router-dom';
|
||||
import { Layout } from '@/components/Layout';
|
||||
import { AuthContext, useAuthState } from '@/hooks/useAuth';
|
||||
import { ROUTES } from '@/lib/types';
|
||||
|
||||
const HomePage = lazy(() => import('@/pages/HomePage').then((m) => ({ default: m.HomePage })));
|
||||
const LoginPage = lazy(() => import('@/pages/LoginPage').then((m) => ({ default: m.LoginPage })));
|
||||
const SignupPage = lazy(() => import('@/pages/SignupPage').then((m) => ({ default: m.SignupPage })));
|
||||
const AdminPage = lazy(() => import('@/pages/AdminPage').then((m) => ({ default: m.AdminPage })));
|
||||
const DeveloperPage = lazy(() => import('@/pages/DeveloperPage').then((m) => ({ default: m.DeveloperPage })));
|
||||
|
||||
function Loading() {
|
||||
return (
|
||||
<div className="flex items-center justify-center min-h-[50vh]">
|
||||
<div className="w-6 h-6 border-2 border-indigo-500 border-t-transparent rounded-full animate-spin" />
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
export default function App() {
|
||||
const auth = useAuthState();
|
||||
|
||||
return (
|
||||
<AuthContext.Provider value={auth}>
|
||||
<BrowserRouter>
|
||||
<Suspense fallback={<Loading />}>
|
||||
<Routes>
|
||||
<Route element={<Layout />}>
|
||||
<Route path={ROUTES.HOME} element={<HomePage />} />
|
||||
<Route path={ROUTES.LOGIN} element={<LoginPage />} />
|
||||
<Route path={ROUTES.SIGNUP} element={<SignupPage />} />
|
||||
<Route path={ROUTES.ADMIN} element={<AdminPage />} />
|
||||
<Route path={ROUTES.DEVELOPER} element={<DeveloperPage />} />
|
||||
</Route>
|
||||
</Routes>
|
||||
</Suspense>
|
||||
</BrowserRouter>
|
||||
</AuthContext.Provider>
|
||||
);
|
||||
}
|
||||
Reference in New Issue
Block a user