farmcontrol-ui/vite.config.js
Tom Butcher 24959ce9d8
Some checks failed
farmcontrol/farmcontrol-ui/pipeline/head There was a failure building this commit
Update package.json and Vite config for @lezer/common compatibility
- Changed the version of @lezer/common in package.json to a fixed version (1.5.0) for consistency.
- Updated Vite config to resolve @lezer/common directly from node_modules, ensuring compatibility with CodeMirror parsers and preventing issues with version mismatches.
- Enhanced the fcTemplateLang parser to support XML overlay across Text regions, improving EJS template handling.
2026-08-10 03:24:08 +01:00

178 lines
5.3 KiB
JavaScript

import { createRequire } from 'node:module'
import react from '@vitejs/plugin-react'
import { defineConfig } from 'vite'
import eslintPlugin from 'vite-plugin-eslint'
import svgr from 'vite-plugin-svgr'
import path from 'path'
import { fileURLToPath } from 'url'
import { visualizer } from 'rollup-plugin-visualizer'
const require = createRequire(import.meta.url)
const svgo = require('vite-plugin-svgo')
const __filename = fileURLToPath(import.meta.url)
const __dirname = path.dirname(__filename)
const isCloudflare = process.env.VITE_DEPLOY_TARGET === 'cloudflare'
/** Resolve a package's ESM entry to an absolute path (pnpm-safe single instance). */
function esmEntry(id) {
const cjs = require.resolve(id)
const root = path.dirname(path.dirname(cjs)) // .../pkg/dist → .../pkg
const pkg = require(path.join(root, 'package.json'))
const rel =
(typeof pkg.exports?.['.'] === 'object' && pkg.exports['.'].import) ||
(typeof pkg.exports === 'object' && pkg.exports.import) ||
pkg.module ||
pkg.exports?.['.'] ||
'dist/index.js'
return path.join(root, rel)
}
const codemirrorSingletons = {
'@codemirror/state': esmEntry('@codemirror/state'),
'@codemirror/view': esmEntry('@codemirror/view'),
'@codemirror/language': esmEntry('@codemirror/language'),
'@codemirror/commands': esmEntry('@codemirror/commands'),
'@codemirror/autocomplete': esmEntry('@codemirror/autocomplete'),
// Must match the @lezer/common used by @codemirror/lang-* parsers (1.5.0).
// 1.5.2 breaks parseMixed tree walking across nested language mounts.
'@lezer/common': path.resolve(__dirname, 'node_modules/@lezer/common/dist/index.js'),
'@lezer/lr': esmEntry('@lezer/lr'),
'@lezer/highlight': esmEntry('@lezer/highlight')
}
export default defineConfig({
base: isCloudflare ? '/' : './', // Cloudflare Pages needs absolute paths; Electron needs relative for file://
resolve: {
alias: {
three: path.resolve(__dirname, 'node_modules/three'),
...codemirrorSingletons
},
dedupe: Object.keys(codemirrorSingletons)
},
optimizeDeps: {
// Do not prebundle CodeMirror — pnpm + esbuild duplicates @codemirror/state
// and breaks FacetProvider instanceof checks.
include: ['@ant-design/icons'],
exclude: [
'@uiw/react-codemirror',
'codemirror',
'@codemirror/state',
'@codemirror/view',
'@codemirror/language',
'@codemirror/commands',
'@codemirror/autocomplete',
'@codemirror/theme-one-dark',
'@codemirror/lang-javascript',
'@codemirror/lang-xml',
'@codemirror/lang-json',
'@codemirror/lang-html',
'@codemirror/lang-css',
'@codemirror/lang-python',
'@codemirror/lang-markdown',
'@codemirror/lang-sql',
'@codemirror/lang-java',
'@codemirror/lang-cpp',
'@codemirror/lang-rust',
'@codemirror/lang-go',
'@codemirror/lang-php',
'@codemirror/lang-yaml',
'@lezer/common',
'@lezer/lr',
'@lezer/highlight',
'@lezer/javascript',
'@lezer/xml'
]
},
plugins: [
react(),
svgo(),
svgr(),
eslintPlugin(),
visualizer(),
// Transform index.html paths to absolute when building for Cloudflare Pages
isCloudflare && {
name: 'cloudflare-html-paths',
transformIndexHtml(html) {
return html
.replace(/href="\.\//g, 'href="/')
.replace(/src="\.\//g, 'src="/')
}
}
].filter(Boolean),
build: {
outDir: 'build',
chunkSizeWarningLimit: 2000,
rollupOptions: {
output: {
manualChunks(id) {
// --- CodeMirror
if (id.includes('node_modules/@codemirror')) {
return 'codemirror'
}
// --- Lezer
if (id.includes('node_modules/@lezer')) {
return 'lezer'
}
// --- Core Vendor (Ant Design, React, etc.)
if (
id.includes('node_modules/antd') ||
id.includes('node_modules/@ant-design') ||
id.includes('node_modules/rc-') ||
id.includes('node_modules/antd-style') ||
id.includes('node_modules/@rc-component') ||
id.includes('node_modules/dayjs') ||
id.includes('node_modules/react') ||
id.includes('node_modules/react-dom') ||
id.includes('node_modules/react-router-dom')
) {
return 'antd'
}
// --- Lodash
if (id.includes('node_modules/lodash')) {
return 'lodash'
}
// --- Three.js
if (id.includes('node_modules/three')) {
return 'three'
}
// --- GCode Preview
if (id.includes('node_modules/gcode-preview')) {
return 'gcode-preview'
}
// --- Online 3D Viewer
if (id.includes('node_modules/online-3d-viewer')) {
return 'online-3d-viewer'
}
// --- tsparticles
if (
id.includes('node_modules/@tsparticles') ||
id.includes('node_modules/tsparticles')
) {
return 'tsparticles'
}
// --- Tiptap
if (id.includes('node_modules/@tiptap')) {
return 'tiptap'
}
}
}
}
},
server: {
allowedHosts: ['dev.tombutcher.work'],
host: '0.0.0.0',
port: 5173,
open: false
}
})