portfolio/vite.config.ts

76 lines
2.3 KiB
TypeScript

import { defineConfig } from 'vite';
import react from '@vitejs/plugin-react';
// Custom Vite plugin to parse Gettext .po files into JSON objects at build/bundle time
function poLoader() {
return {
name: 'po-loader',
transform(code: string, id: string) {
if (id.endsWith('.po')) {
const translations: Record<string, string> = {};
const lines = code.split(/\r?\n/);
let currentKey = '';
let currentValue = '';
let readingField: 'msgid' | 'msgstr' | '' = '';
const saveCurrent = () => {
if (currentKey) {
const key = currentKey.replace(/\\n/g, '\n').replace(/\\"/g, '"');
const val = currentValue.replace(/\\n/g, '\n').replace(/\\"/g, '"');
translations[key] = val;
}
currentKey = '';
currentValue = '';
readingField = '';
};
for (let line of lines) {
line = line.trim();
if (line.startsWith('#') || !line) continue;
if (line.startsWith('msgid ')) {
saveCurrent();
readingField = 'msgid';
const match = line.match(/^msgid\s+"(.*)"$/);
currentKey = match ? match[1] : '';
} else if (line.startsWith('msgstr ')) {
readingField = 'msgstr';
const match = line.match(/^msgstr\s+"(.*)"$/);
currentValue = match ? match[1] : '';
} else if (line.startsWith('"') && line.endsWith('"')) {
const match = line.match(/^"(.*)"$/);
if (match) {
const val = match[1];
if (readingField === 'msgid') {
currentKey += val;
} else if (readingField === 'msgstr') {
currentValue += val;
}
}
}
}
saveCurrent();
return {
code: `export default ${JSON.stringify(translations)};`,
map: null
};
}
}
};
}
// https://vite.dev/config/
const buildId = Date.now().toString(36); // unique per build run
export default defineConfig({
plugins: [react(), poLoader()],
css: {
modules: {
// Regenerate class hashes on every build → harder for DOM scrapers to target
generateScopedName: `[hash:base64:5]_${buildId}`
}
}
});