新增 IDE 官网静态资源与 D3 分区域地图布局,构建时复制至 dist/site;同步应收应付、代发打包、订单详情等页面优化。 Co-authored-by: Cursor <cursoragent@cursor.com>
53 lines
1.7 KiB
JavaScript
53 lines
1.7 KiB
JavaScript
const fs = require('fs');
|
|
const path = require('path');
|
|
|
|
const root = path.join(__dirname, '..');
|
|
const js = fs.readFileSync(path.join(root, 'assets/js/main.js'), 'utf8');
|
|
const mapMatch = js.match(/const textMap = \{([\s\S]*?)\n \};/);
|
|
const keys = new Set();
|
|
const re = /^\s*,?'((?:\\'|[^'])*)':/gm;
|
|
let m;
|
|
while ((m = re.exec(mapMatch[1]))) {
|
|
keys.add(m[1].replace(/\\'/g, "'"));
|
|
}
|
|
|
|
const files = [];
|
|
function walk(dir) {
|
|
for (const f of fs.readdirSync(dir)) {
|
|
const p = path.join(dir, f);
|
|
if (fs.statSync(p).isDirectory()) {
|
|
if (f === 'vendor' || f === 'node_modules' || f === 'scripts') continue;
|
|
walk(p);
|
|
} else if (f.endsWith('.html')) files.push(p);
|
|
}
|
|
}
|
|
walk(root);
|
|
|
|
const missingKeys = new Set();
|
|
const missingLeaf = new Set();
|
|
|
|
for (const file of files) {
|
|
const html = fs.readFileSync(file, 'utf8');
|
|
const i18nKeys = [...html.matchAll(/data-i18n-key="([^"]+)"/g)].map((x) => x[1]);
|
|
for (const t of i18nKeys) {
|
|
if (!keys.has(t)) missingKeys.add(t);
|
|
}
|
|
|
|
const stripped = html
|
|
.replace(/<script[\s\S]*?<\/script>/gi, '')
|
|
.replace(/<style[\s\S]*?<\/style>/gi, '');
|
|
const leaf = [...stripped.matchAll(/>([^<>]{2,140})</g)]
|
|
.map((x) => x[1].replace(/\s+/g, ' ').trim())
|
|
.filter((t) => /^[A-Za-z0-9]/.test(t) && !/^\d+$/.test(t));
|
|
|
|
for (const t of new Set(leaf)) {
|
|
if (t.includes('http') || t.includes('assets/') || t.includes('©') || t.includes('@')) continue;
|
|
if (!keys.has(t) && !i18nKeys.includes(t)) missingLeaf.add(t);
|
|
}
|
|
}
|
|
|
|
console.log('=== data-i18n-key not in textMap ===');
|
|
[...missingKeys].sort().forEach((k) => console.log(k));
|
|
console.log('\n=== leaf text not in textMap (sample) ===');
|
|
[...missingLeaf].sort().slice(0, 60).forEach((k) => console.log(k));
|