Tau.Acuvim/portal/frontend/vite.config.ts
Diseri Pearson b5ceedc097 Portal frontend: tests, code splitting, 401 interceptor, lint/format tooling
Items 1-5 of the agreed frontend upgrades. The one-time Prettier
reformatting of files not touched here is in the FOLLOW-UP commit so this
one stays reviewable.

Testing (vitest + @testing-library)
- vitest 3 + @testing-library/react + jsdom. test / test:watch / test:ui
  scripts; setup.ts stubs matchMedia + ResizeObserver for AntD under jsdom.
- 15 tests, 4 files: RequireRole, LoginPage, measurements API client,
  extractApiError.

Route-level code splitting
- Every page converted to React.lazy() behind a Suspense boundary in
  App.tsx. Main bundle 1490 KB -> 714 KB; ECharts isolated in the
  DashboardPage chunk and only fetched when a dashboard is opened.

Global 401 handling
- api/client.ts response interceptor redirects any 401 from a non-/auth
  path to /login?returnTo=<current>; LoginPage honours the param.
- Shared extractApiError replaces four near-identical per-page copies
  (UsersPage, AdminCustomersPage, MyProfilePage, TariffDrawer).

Query devtools
- @tanstack/react-query-devtools, lazy + import.meta.env.DEV-gated so a
  production build dead-code-eliminates it. Verified: no devtools code in
  any shipped .js chunk.

ESLint + Prettier
- ESLint 9 flat config (js + typescript-eslint + react-hooks +
  react-refresh, eslint-config-prettier last). Prettier config tuned to
  the existing style. lint / lint:fix / format / format:check scripts +
  lint-staged config.
- Fixed one real react-hooks/exhaustive-deps warning (useMemo on
  DashboardsPage's `dashboards`).
- End state: eslint 0 problems, tsc clean, 15/15 tests pass.

Pre-commit hook (lint-staged) is installed locally in .git/hooks/ -- not
version-controlled, see follow-up note. Husky was deliberately not used:
it needs a core.hooksPath change and the monorepo layout makes it awkward.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-19 23:46:54 +02:00

35 lines
981 B
TypeScript

// defineConfig from vitest/config is a superset of vite's — it accepts the
// `test` block. Importing it here keeps vite.config.ts the single source of
// truth for both the dev/build config and the test config.
import { defineConfig } from 'vitest/config';
import react from '@vitejs/plugin-react';
export default defineConfig({
plugins: [react()],
server: {
port: 5174,
proxy: {
'/api': {
target: 'http://localhost:8080',
changeOrigin: false,
},
'/health': {
target: 'http://localhost:8080',
changeOrigin: false,
},
},
},
build: {
outDir: 'dist',
sourcemap: true,
},
test: {
environment: 'jsdom',
setupFiles: ['./src/test/setup.ts'],
css: false,
// AntD's reset.css is imported in main.tsx — skip it for tests.
// No `globals: true` — test files import describe/it/expect/vi from 'vitest'
// explicitly. Less magic, no tsconfig types array required.
},
});