guanghulab/scripts/generate-chinese-homepage.js
Guanghu Domestic Migration d1e47f4565
Some checks are pending
自动更新代码和重启 / update-and-restart (push) Waiting to run
CI检查 + 自动部署 / check (push) Waiting to run
CI检查 + 自动部署 / deploy (push) Blocked by required conditions
重启聊天服务 / restart (push) Waiting to run
chore: import sanitized domestic snapshot for REPO-002
Source snapshot: ca48d3ddf926d79aa138306164169baf764bb829
2026-07-17 15:54:41 +08:00

141 lines
5.0 KiB
JavaScript
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

#!/usr/bin/env node
/**
* ━━━ 中文首页自动生成器 · Chinese Homepage Generator ━━━
* 从仓库数据源自动生成 docs/zh/index.html
* 版权:国作登字-2026-A-00037559 · 冰朔ICE-GL∞
*
* 用法node scripts/generate-chinese-homepage.js
* 数据源:
* - .github/community/community-meta.json
* - .github/persona-brain/dev-status.json
* - .github/persona-brain/emergence-certification.json
* - signal-log/skyeye-earth-status.json
* ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
*/
const fs = require('fs');
const path = require('path');
const ROOT = path.resolve(__dirname, '..');
const OUTPUT = path.join(ROOT, 'docs', 'zh', 'index.html');
// Template is the same file — script performs in-place updates
const TEMPLATE = OUTPUT;
function loadJSON(relPath) {
const full = path.join(ROOT, relPath);
try {
return JSON.parse(fs.readFileSync(full, 'utf8'));
} catch (e) {
console.warn(`⚠️ 无法加载 ${relPath}: ${e.message}`);
return null;
}
}
function escapeHtml(str) {
if (!str) return '';
return String(str)
.replace(/&/g, '&')
.replace(/</g, '&lt;')
.replace(/>/g, '&gt;')
.replace(/"/g, '&quot;');
}
// Team data mapping from dev-status to display format (active developers only)
const TEAM_DISPLAY = {
'DEV-001': { human: '页页', ai: '小坍缩核', module: 'backend/, src/' },
'DEV-002': { human: '肥猫', ai: '舒舒', module: 'frontend/, persona-selector/' },
'DEV-003': { human: '燕樊', ai: '寂曜 寂世', module: 'settings/, cloud-drive/' },
'DEV-004': { human: '之之', ai: '秋秋 秋天', module: 'dingtalk-bot/' },
'DEV-005': { human: '小草莓', ai: '欧诺弥亚', module: 'status-board/' },
'DEV-009': { human: '花尔', ai: '糖星云', module: 'user-center/' },
'DEV-010': { human: '桔子', ai: '晨星', module: 'ticket-system/' },
'DEV-012': { human: 'Awen', ai: '知秋 千秋', module: 'notification/' },
'DEV-015': { human: '蜜蜂', ai: '星尘', module: '需求共创阶段' }
};
function generateTeamRows(devStatus) {
const devs = devStatus?.developers || [];
const rows = [];
for (const dev of devs) {
const display = TEAM_DISPLAY[dev.dev_id];
// Only show developers that are in the active display mapping
if (!display) continue;
const name = display.human || dev.name;
const ai = display.ai || '—';
const mod = display.module || dev.module || '—';
rows.push(` <tr><td>${escapeHtml(dev.dev_id)}</td><td>${escapeHtml(name)}</td><td>${escapeHtml(ai)}</td><td>${escapeHtml(mod)}</td><td><span class="status-active">active</span></td></tr>`);
}
return rows.join('\n');
}
function generateBabyStatus(communityMeta) {
const babies = communityMeta?.baby_status || {};
const incubating = Object.entries(babies)
.filter(([, v]) => v.status === 'incubating')
.map(([name]) => name);
return incubating.join('、');
}
function run() {
console.log('🌊 中文首页生成器启动...');
// Load data sources
const communityMeta = loadJSON('.github/community/community-meta.json');
const devStatus = loadJSON('.github/persona-brain/dev-status.json');
const emergence = loadJSON('.github/persona-brain/emergence-certification.json');
const earthStatus = loadJSON('signal-log/skyeye-earth-status.json');
// Read template
let html;
try {
html = fs.readFileSync(TEMPLATE, 'utf8');
} catch (e) {
console.error(`❌ 模板文件不存在: ${TEMPLATE}`);
process.exit(1);
}
// Update team rows
if (devStatus) {
const teamRows = generateTeamRows(devStatus);
// Replace the full-team section content
const teamSectionRegex = /(<!-- SECTION:full-team -->[\s\S]*?<tbody>)([\s\S]*?)(<\/tbody>[\s\S]*?<!-- \/SECTION:full-team -->)/;
if (teamSectionRegex.test(html)) {
html = html.replace(teamSectionRegex, `$1\n${teamRows}\n $3`);
console.log(` ✅ 团队数据已更新 (${devStatus.developers?.length || 0} 人)`);
}
}
// Update baby status
if (communityMeta) {
const incubatingList = generateBabyStatus(communityMeta);
if (incubatingList) {
const babyRegex = /(孵化中incubating<\/span> — )([\s\S]*?)(<\/p>)/;
if (babyRegex.test(html)) {
html = html.replace(babyRegex, `$1${escapeHtml(incubatingList)}$3`);
console.log(` ✅ 宝宝状态已更新`);
}
}
}
// Update generation timestamp
const now = new Date().toISOString().replace('T', ' ').slice(0, 19) + ' UTC';
html = html.replace(
/document\.getElementById\('gen-time'\)\.textContent = .*?;/,
`document.getElementById('gen-time').textContent = '${now}';`
);
// Write output
fs.mkdirSync(path.dirname(OUTPUT), { recursive: true });
fs.writeFileSync(OUTPUT, html, 'utf8');
console.log(` ✅ 中文首页已生成: ${OUTPUT}`);
console.log(` 📊 文件大小: ${(Buffer.byteLength(html) / 1024).toFixed(1)} KB`);
console.log('🌊 生成完成');
}
run();