import { defineConfig, loadEnv } from 'vite' import react from '@vitejs/plugin-react' import fs from 'fs' import path, { resolve } from 'path' function injectFirebaseConfig(content: string, env: Record): string { return content .replace('__VITE_FIREBASE_API_KEY__', env.VITE_FIREBASE_API_KEY || '') .replace('__VITE_FIREBASE_AUTH_DOMAIN__', env.VITE_FIREBASE_AUTH_DOMAIN || '') .replace('__VITE_FIREBASE_PROJECT_ID__', env.VITE_FIREBASE_PROJECT_ID || '') .replace('__VITE_FIREBASE_MESSAGING_SENDER_ID__', env.VITE_FIREBASE_MESSAGING_SENDER_ID || '') .replace('__VITE_FIREBASE_APP_ID__', env.VITE_FIREBASE_APP_ID || '') } function swPlugin() { let env: Record = {} return { name: 'sw-plugin', config(_: unknown, { mode }: { mode: string }) { env = loadEnv(mode, process.cwd(), '') }, // Dev server: serve sw.js with injected Firebase config configureServer(server: { middlewares: { use: (path: string, handler: (req: unknown, res: { setHeader: (k: string, v: string) => void; end: (s: string) => void }, next: () => void) => void) => void } }) { server.middlewares.use('/sw.js', (_req, res) => { const swPath = path.resolve(__dirname, 'public/sw.js') if (fs.existsSync(swPath)) { const content = injectFirebaseConfig( fs.readFileSync(swPath, 'utf-8').replace('__BUILD_TIME__', 'dev'), env ) res.setHeader('Content-Type', 'application/javascript') res.end(content) } }) }, closeBundle() { // Cache-bust sw.js and inject Firebase config const swPath = path.resolve(__dirname, 'dist/sw.js') if (fs.existsSync(swPath)) { let content = fs.readFileSync(swPath, 'utf-8') content = content.replace('__BUILD_TIME__', Date.now().toString()) content = injectFirebaseConfig(content, env) fs.writeFileSync(swPath, content) } }, } } // https://vite.dev/config/ export default defineConfig({ plugins: [react(), swPlugin()], server: { port: 8000, strictPort: false, }, optimizeDeps: { include: ['libsodium-wrappers'], }, build: { chunkSizeWarningLimit: 1000, rollupOptions: { input: { main: resolve(__dirname, 'index.html'), about: resolve(__dirname, 'about.html'), privacy: resolve(__dirname, 'privacy.html'), termsofservice: resolve(__dirname, 'termsofservice.html'), }, output: { manualChunks(id) { if (id.includes('node_modules/firebase')) { return 'firebase' } if ( id.includes('node_modules/react/') || id.includes('node_modules/react-dom/') || id.includes('node_modules/react-router-dom/') ) { return 'react-vendor' } if (id.includes('node_modules/libsodium')) { return 'crypto' } if (id.includes('node_modules/driver.js')) { return 'driver' } }, }, }, }, })