// https://nuxt.com/docs/api/configuration/nuxt-config /* The desktop build — the same wiki in an app window (Tauri, see src-tauri/). A window has no Nuxt server and no nginx behind it, so the wiki is written out as plain files for the system webview to read off disk and every address it calls has to be absolute. `desktop/build.mjs` sets the flag; the Tauri CLI carries TAURI_ENV_* into its own build hooks, so `tauri build` reaches this branch without anyone remembering to export anything. The web build takes none of it: same config file, different shape of output. */ const desktop = process.env.MATHEW_DESKTOP === '1' || !!process.env.TAURI_ENV_PLATFORM /* Where a desktop build takes its wiki from. Baked in at build — the app has no origin of its own to route `/api` through — and overridable for anyone building against another wiki: NUXT_PUBLIC_API_BASE (a staging wiki, this machine), and NUXT_PUBLIC_LEAN_URL for a Lean server the app can actually reach. Lean's default stays empty on purpose: a window on a random laptop has no localhost:8080 to find, and /lean says so plainly rather than reaching for a server that is not there. */ const apiDefault = desktop ? 'https://mathew.aranroig.com' : 'http://localhost:5000' const leanDefault = desktop ? '' : 'http://localhost:8080' export default defineNuxtConfig({ compatibilityDate: '2025-07-15', devtools: { enabled: true }, modules: ['@nuxtjs/i18n'], css: ['katex/dist/katex.min.css', '~/assets/css/main.scss'], /* The interface language (app -> t('...'), catalogues in i18n/locales/). It is a preference, never part of the address — /wiki// speaks of the *article's* language, so the UI stays unprefixed. On a first load the saved choice comes from the `mathew-locale` cookie (which the server can read, so pages render in the right language before any script runs), then the browser's own. A signed-in account's stored choice is applied over these at startup — see app/plugins/auth.ts. */ i18n: { strategy: 'no_prefix', defaultLocale: 'en', locales: [ { code: 'en', language: 'en-US', name: 'English', file: 'en.json' }, { code: 'es', language: 'es-ES', name: 'Español', file: 'es.json' }, { code: 'ca', language: 'ca-ES', name: 'Català', file: 'ca.json' }, { code: 'fr', language: 'fr-FR', name: 'Français', file: 'fr.json' }, { code: 'de', language: 'de-DE', name: 'Deutsch', file: 'de.json' }, ], // The catalogues are small; bundling them keeps locale switches instant lazy: false, // Messages carry their own markup ( in the API banner, the hero // gradient, demo words in the cheatsheet), rendered with v-html compilation: { strictMessage: false }, detectBrowserLanguage: { useCookie: true, cookieKey: 'mathew-locale', fallbackLocale: 'en', }, }, /* A page of the web is drawn on the server; a window on the machine cannot be — the webview draws these same pages itself, from the bundle. The book, the middleware and the popups all run client-side either way, so nothing but where HTML first comes from changes. */ ssr: !desktop, runtimeConfig: { public: { // Where the UI calls the API. The Docker image sets this to "" so the // browser calls /api on its own origin and nginx routes it to the // backend; dev keeps the absolute localhost address, and the desktop // build the public wiki it ships pointed at. apiBase: process.env.NUXT_PUBLIC_API_BASE ?? apiDefault, // Where the Lean editor server (lean4web — see lean/) lives: /lean // frames this address. It is the browser's own way in, not the // server's — the iframe talks to its own origin from there on. leanUrl: process.env.NUXT_PUBLIC_LEAN_URL ?? leanDefault, }, }, /* The desktop bundle: files under dist-desktop/ and nothing to run. Written there rather than into .output/ so a desktop build never overwrites the server bundle a web build left, and `frontendDist` in tauri.conf.json has a directory of its own to read. */ ...(desktop ? { nitro: { preset: 'static', output: { dir: 'dist-desktop' } } } : {}), // The Nuxt server's own API calls (SSR) are relative once apiBase is "", // and land on this Nitro route, which forwards them to the backend. The // Docker image bakes NUXT_API_PROXY_TARGET=https://mathew.aranroig.com in // at build; nginx routes that address on to the backend. A desktop build has // no Nuxt server to answer this, and no reason for one: the app calls the // API by its own absolute address. routeRules: desktop ? {} : { '/api/**': { proxy: `${process.env.NUXT_API_PROXY_TARGET || 'http://localhost:5000'}/api/**` } }, app: { head: { meta: [ { name: 'description', content: 'A modern, collaborative wiki for mathematical concepts — written in Markdown, rendered with LaTeX.', }, { name: 'theme-color', media: '(prefers-color-scheme: light)', content: '#f7f8fb' }, { name: 'theme-color', media: '(prefers-color-scheme: dark)', content: '#0a0c12' }, ], script: desktop ? [ /* The same pre-paint, from a file: a window is a host one may sensibly hold to a `script-src 'self'` Content Security Policy, and code written into the HTML would not survive one. public/preboot.js carries this exact code — keep the pair in step. (src-tauri/ sets no policy yet; keeping this one in a file is what makes turning it on a config line, not a page rewrite.) */ { tagPosition: 'head', src: '/preboot.js' }, ] : [ { // Apply saved theme & accent before first paint to avoid a flash tagPosition: 'head', innerHTML: "(function(){try{var d=document.documentElement;var s=localStorage.getItem('mathew-theme');var t=s||(window.matchMedia&&window.matchMedia('(prefers-color-scheme: dark)').matches?'dark':'light');d.setAttribute('data-theme',t);var a=localStorage.getItem('mathew-accent');if(a&&a!=='violet')d.setAttribute('data-accent',a);}catch(e){}})();", }, ], }, }, })