feat: 新增多语言文案、优化导航及工具函数,修复部分业务逻辑

1. 新增多语言资源文件,覆盖文章、预约日期、会员信息、优惠券、表单、购物车、积分商城、分销、AI聊天等多个模块
2. 优化底部导航组件,使用多语言配置替代硬编码文案
3. 重构工具函数,新增从后端数据提取多语言文案的工具方法
4. 修复邀请好友页面的保存提示文案,替换为多语言版本
5. 修复商品SKU组件的提示文案,使用多语言配置
6. 重构AI聊天页面的帮助文档和回复模板,使用多语言配置
7. 优化空状态组件,支持多语言默认文案
8. 修复跳转逻辑,补全参数传递
9. 新增本地开发环境配置
This commit is contained in:
2026-06-25 18:15:31 +08:00
parent ca4e7fd170
commit 2d8846c64c
82 changed files with 3497 additions and 1062 deletions

View File

@@ -168,7 +168,7 @@ function main() {
}
// ---- 检查 1: 文件结构一致性 ----
console.log('【1/2】文件结构检查\n');
console.log('【1/3】文件结构检查\n');
const zhFiles = localeFiles['zh-cn'];
const enFiles = localeFiles['en-us'];
@@ -198,7 +198,7 @@ function main() {
}
// ---- 检查 2: key 一致性 ----
console.log('\n【2/2】Key 一致性检查\n');
console.log('\n【2/3】Key 一致性检查\n');
let totalZhKeys = 0;
let totalEnKeys = 0;
@@ -262,6 +262,118 @@ function main() {
console.log(' ✅ 所有共同文件的 key 完全一致');
}
// ---- 检查 3: 硬编码中文扫描 ----
console.log('\n【3/3】硬编码中文扫描\n');
// 跳过的目录
const SKIP_DIRS = new Set([
'node_modules', 'unpackage', 'static', 'lang',
'uni_modules', '.git', '.hbuilderx', 'dist', 'build',
'stub-app-projects', 'docs', 'hybrid', 'wxcomponents'
]);
// 跳过的文件
const SKIP_FILE_PATTERNS = [
/vendor\.js$/,
/\.min\.js$/,
/\.pack\.js$/,
/manifest\.json\.js$/,
];
// 扫描所有 vue / js 文件
const srcFiles = [];
function scanSrcDir(dir, rel) {
const entries = fs.readdirSync(dir, { withFileTypes: true });
for (const entry of entries) {
const fullPath = path.join(dir, entry.name);
const relPath = rel ? path.join(rel, entry.name) : entry.name;
if (entry.isDirectory()) {
if (SKIP_DIRS.has(entry.name)) continue;
scanSrcDir(fullPath, relPath);
} else if (entry.name.endsWith('.vue') || entry.name.endsWith('.js')) {
// 跳过 vendor / min / pack 等非源码文件
let skip = false;
for (const pat of SKIP_FILE_PATTERNS) {
if (pat.test(entry.name)) { skip = true; break; }
}
if (!skip) {
srcFiles.push({ fullPath, relPath: relPath.replace(/\\/g, '/') });
}
}
}
}
scanSrcDir(ROOT, '');
// 中文正则(基本汉字区)
const CN_RE = /[\u4e00-\u9fa5]+/g;
// 判断一行是否是注释行(粗略)
function isCommentLine(line) {
const t = line.trim();
if (t.startsWith('//')) return true;
if (t.startsWith('/*')) return true;
if (t.startsWith('*')) return true;
if (t.startsWith('<!--')) return true;
if (t.startsWith('* ')) return true;
return false;
}
// 判断一行是否是 $lang 调用(已经国际化)
function isLangCall(line) {
// 匹配 $lang(' 或 $lang("
return /\$lang\(\s*['"]/.test(line);
}
const hardcodeResults = [];
let totalCnHits = 0;
for (const { fullPath, relPath } of srcFiles) {
try {
const content = fs.readFileSync(fullPath, 'utf-8');
const lines = content.split('\n');
let fileHits = 0;
for (let i = 0; i < lines.length; i++) {
const line = lines[i];
if (isCommentLine(line)) continue;
if (isLangCall(line)) continue;
const matches = line.match(CN_RE);
if (matches) {
fileHits += matches.length;
}
}
if (fileHits > 0) {
totalCnHits += fileHits;
hardcodeResults.push({ file: relPath, count: fileHits });
}
} catch (e) {
// 跳过读不了的文件
}
}
// 按命中数排序
hardcodeResults.sort((a, b) => b.count - a.count);
console.log(` 扫描文件数: ${srcFiles.length}`);
console.log(` 含中文的文件数: ${hardcodeResults.length}`);
console.log(` 中文字符串命中数: ${totalCnHits}`);
if (hardcodeResults.length > 0) {
console.log(`\n ⚠️ 疑似硬编码中文 TOP 20:`);
const topN = hardcodeResults.slice(0, 20);
for (const r of topN) {
console.log(` ${String(r.count).padStart(4)} ${r.file}`);
}
if (hardcodeResults.length > 20) {
console.log(` ... 还有 ${hardcodeResults.length - 20} 个文件`);
}
console.log(`\n 💡 提示:这是粗略扫描,包含注释/默认值等误报,仅供参考`);
} else {
console.log(' ✅ 未发现硬编码中文(粗略扫描)');
}
// ---- 总结 ----
console.log('\n========================================');
console.log(' 检查完成');