import App from './App' import { orderMonitor } from './utils/orderMonitor.js' import { createSSRApp } from 'vue' import { createI18n } from 'vue-i18n' import zhCN from './locale/zh-CN.js' import enUS from './locale/en-US.js' import idID from './locale/id-ID.js' import uView from '@climblee/uv-ui' import { initConsoleControl } from './config/console.js' import { getSystemConfig } from './config/api/system.js' // #ifdef H5 // 兼容部分依赖/构建产物在浏览器环境访问 process.env 的场景 if (typeof globalThis !== 'undefined' && typeof globalThis.process === 'undefined') { globalThis.process = { env: {} } } if (typeof globalThis !== 'undefined' && globalThis.process && !globalThis.process.env) { globalThis.process.env = {} } // #endif // 初始化 console 控制 initConsoleControl() const LANGUAGE_STORAGE_KEY = 'language' const SUPPORTED_LANGUAGES = ['zh-CN', 'en-US', 'id-ID'] const LANGUAGE_ALIASES = { zh: 'zh-CN', 'zh-cn': 'zh-CN', 'zh_cn': 'zh-CN', en: 'en-US', 'en-us': 'en-US', 'en_us': 'en-US', id: 'id-ID', 'id-id': 'id-ID', 'id_id': 'id-ID', in: 'id-ID', 'in-id': 'id-ID', 'in_id': 'id-ID' } const normalizeLanguage = (lang) => { if (!lang || typeof lang !== 'string') return '' const cleaned = lang.trim() if (!cleaned) return '' const lower = cleaned.toLowerCase() if (LANGUAGE_ALIASES[lower]) return LANGUAGE_ALIASES[lower] if (SUPPORTED_LANGUAGES.includes(cleaned)) return cleaned return '' } // 检测是否为 H5 环境 const isH5Platform = () => { try { const systemInfo = uni.getSystemInfoSync() return systemInfo.platform === 'web' || systemInfo.uniPlatform === 'web' || (typeof window !== 'undefined' && typeof document !== 'undefined') } catch (e) { // 如果获取系统信息失败,尝试通过全局对象判断 return typeof window !== 'undefined' && typeof document !== 'undefined' } } // 获取系统语言 const getSystemLanguage = () => { let language = 'zh-CN' try { const systemInfo = uni.getSystemInfoSync() || {} const systemLanguage = normalizeLanguage(systemInfo.language) if (systemLanguage) { language = systemLanguage } else if (isH5Platform() && typeof navigator !== 'undefined') { const browserLanguage = normalizeLanguage(navigator.language || '') if (browserLanguage) language = browserLanguage } } catch (e) { console.error('获取系统语言失败:', e) language = 'zh-CN' } return language } const extractLanguageFromConfig = (data) => { if (!data) return '' if (typeof data === 'string') { return normalizeLanguage(data) } if (Array.isArray(data)) { for (const item of data) { const fromItem = extractLanguageFromConfig(item) if (fromItem) return fromItem } return '' } if (typeof data === 'object') { const direct = normalizeLanguage( data.language || data.lang || data.locale || data.defaultLanguage || data.defaultLang ) if (direct) return direct for (const [key, value] of Object.entries(data)) { const keyLower = String(key).toLowerCase() if (keyLower.includes('lang') || keyLower.includes('locale')) { const parsed = extractLanguageFromConfig(value) if (parsed) return parsed } } } return '' } // 获取用户选择的语言 const getSavedLanguage = () => { try { const savedLang = normalizeLanguage(uni.getStorageSync(LANGUAGE_STORAGE_KEY)) if (savedLang) { return savedLang } const systemLang = getSystemLanguage() uni.setStorageSync(LANGUAGE_STORAGE_KEY, systemLang) return systemLang } catch (e) { console.error('语言设置出错:', e) return 'zh-CN' } } // 创建 i18n 实例(Vue 3) let i18nInstance = null function getI18nInstance() { // 每次都重新读取当前语言 const currentLang = getSavedLanguage() // 检查是否需要更新语言 if (i18nInstance && i18nInstance.global.locale !== currentLang) { console.log('=== 检测到语言变化,强制更新 ===') console.log('旧语言:', i18nInstance.global.locale) console.log('新语言:', currentLang) // 直接更新 locale(这应该会触发所有组件重新渲染) i18nInstance.global.locale = currentLang return i18nInstance } // 首次创建实例 if (!i18nInstance) { i18nInstance = createI18n({ legacy: true, // 使用 Legacy API 模式,支持全局 $t locale: currentLang, fallbackLocale: 'zh-CN', messages: { 'zh-CN': zhCN, 'en-US': enUS, 'id-ID': idID }, silentTranslationWarn: true, silentFallbackWarn: true }) } return i18nInstance } const syncLanguageFromRemoteConfig = async (i18n) => { if (!isH5Platform()) return try { const res = await getSystemConfig() if (!res || res.code !== 200) return const remoteLang = extractLanguageFromConfig(res.data) if (!remoteLang) return const current = normalizeLanguage(i18n?.global?.locale || '') if (current !== remoteLang) { uni.setStorageSync(LANGUAGE_STORAGE_KEY, remoteLang) i18n.global.locale = remoteLang console.log('H5 语言已按系统配置更新为:', remoteLang) } } catch (e) { console.warn('读取系统配置语言失败,使用本地语言设置:', e) } } export function createApp() { const app = createSSRApp(App) // 使用 uView app.use(uView) // 获取或更新 i18n 实例 const i18n = getI18nInstance() // 使用 i18n app.use(i18n) // H5 端通过系统配置同步语言(异步,不阻塞应用启动) syncLanguageFromRemoteConfig(i18n) // 手动注入 $i18n 到全局属性(确保组件可以访问) app.config.globalProperties.$i18n = i18n.global // 注册全局订单监控服务 app.config.globalProperties.$orderMonitor = orderMonitor // 注册全局语言切换方法(注意:建议使用 reLaunch 来切换语言以确保完全刷新) app.config.globalProperties.$setLanguage = (lang) => { console.log('$setLanguage 被调用,语言:', lang) uni.setStorageSync('language', lang) // 更新 i18n 实例的语言 if (i18n && i18n.global) { i18n.global.locale = lang console.log('i18n.global.locale 已更新为:', i18n.global.locale) } } return { app } }