265 lines
8.3 KiB
Vue
Raw Normal View History

2025-10-16 21:07:43 +08:00
<script setup>
import { onLaunch, onShow, onError } from '@dcloudio/uni-app';
import { ShoproInit } from './sheep';
2025-10-20 22:41:56 +08:00
import sheep from '@/sheep';
// 防止重复登录的标志
let isLoggingIn = false;
2025-10-16 21:07:43 +08:00
onLaunch(() => {
// 隐藏原生导航栏 使用自定义底部导航
uni.hideTabBar({
fail: () => {},
});
2025-10-21 14:56:48 +08:00
// 初始化移动端调试控制台仅H5环境
// #ifdef H5
initVConsole();
// #endif
2025-10-16 21:07:43 +08:00
// 加载Shopro底层依赖
ShoproInit();
2025-10-20 22:41:56 +08:00
// 检测建行生活登录参数
checkCCBLogin();
2025-10-21 14:56:48 +08:00
// 启动 JSBridge 监控每10秒打印一次
// #ifdef H5
startJSBridgeMonitor();
// #endif
2025-10-16 21:07:43 +08:00
});
2025-10-21 14:56:48 +08:00
/**
* 初始化 vConsole 移动端调试控制台
* 在H5环境下提供类似Chrome DevTools的功能
*/
const initVConsole = () => {
// 动态导入vConsole避免打包到非H5平台
import('vconsole')
.then((module) => {
const VConsole = module.default;
const vConsole = new VConsole({
defaultPlugins: ['system', 'network', 'element', 'storage'],
maxLogNumber: 1000,
disableLogScrolling: false,
});
// 保存实例供后续使用
window.vConsole = vConsole;
})
.catch((err) => {
console.error('[App] vConsole加载失败:', err);
});
};
2025-10-16 21:07:43 +08:00
onError((err) => {
console.log('AppOnError:', err);
});
onShow(() => {
// #ifdef APP-PLUS
// 获取urlSchemes参数
const args = plus.runtime.arguments;
if (args) {
}
// 获取剪贴板
uni.getClipboardData({
success: (res) => {},
});
// #endif
});
2025-10-20 22:41:56 +08:00
2025-10-21 14:56:48 +08:00
/**
* JSBridge 注入情况监控
* 每10秒打印一次所有建行相关 JSBridge 对象的状态打印15次后自动停止
*/
const startJSBridgeMonitor = () => {
let count = 0;
const maxCount = 15;
// 立即执行一次
printJSBridgeStatus(++count, maxCount);
// 每10秒执行一次
const timer = setInterval(() => {
printJSBridgeStatus(++count, maxCount);
// 达到15次后清除定时器
if (count >= maxCount) {
clearInterval(timer);
console.log('[JSBridge] 监控已停止已打印15次');
}
}, 10000);
};
/**
* 打印 JSBridge 注入状态精简版
*/
const printJSBridgeStatus = (count, maxCount) => {
const timestamp = new Date().toLocaleTimeString('zh-CN', { hour12: false });
const isIOS = /iPhone|iPad|iPod/i.test(navigator.userAgent);
const isAndroid = /Android/i.test(navigator.userAgent);
// 检测各个 Bridge 对象
const hasMbspay =
typeof window.mbspay !== 'undefined' && typeof window.mbspay.directpay === 'function';
const hasCCBBridge = typeof window.CCBBridge !== 'undefined';
const hasWebViewBridge = typeof window.WebViewJavascriptBridge !== 'undefined';
const hasAnyBridge = hasMbspay || hasCCBBridge || hasWebViewBridge;
// 支付能力
const canPay = isIOS || (isAndroid && hasMbspay);
// 一行输出所有状态(包含计数)
console.log(
`[JSBridge ${timestamp}] (${count}/${maxCount}) ` +
`设备:${isIOS ? 'iOS' : isAndroid ? 'Android' : 'PC'} | ` +
`mbspay:${hasMbspay ? '✅' : '❌'} | ` +
`CCBBridge:${hasCCBBridge ? '✅' : '❌'} | ` +
`WebViewBridge:${hasWebViewBridge ? '✅' : '❌'} | ` +
`支付能力:${canPay ? '✅' : '❌'} | ` +
`Bridge状态:${hasAnyBridge ? '✅就绪' : '❌未就绪'}`,
);
};
2025-10-20 22:41:56 +08:00
/**
* 检测URL中的建行登录参数并自动登录
* 建行跳转URL格式url?platform=ccblife&channel=mbs&ccbParamSJ=xxx&CITYID=330100&USERCITYID=440100
2025-10-21 14:56:48 +08:00
*
2025-10-20 22:41:56 +08:00
* 逻辑
* 1. 解析URL参数获取ccbParamSJ
* 2. 与本地存储的lastCcbParamSJ比较
* 3. 如果一致则无需重新登录
* 4. 如果不一致则需要切换用户退出当前用户后重新登录
*/
const checkCCBLogin = () => {
// #ifdef H5
try {
let ccbParamSJ = null;
let platform = null;
let cityid = null;
2025-10-21 14:56:48 +08:00
// 优先从search中提取参数建行标准格式url?ccbParamSJ=xxx&CITYID=xxx
2025-10-20 22:41:56 +08:00
if (window.location.search) {
const urlParams = new URLSearchParams(window.location.search);
ccbParamSJ = urlParams.get('ccbParamSJ');
2025-10-21 14:56:48 +08:00
platform = urlParams.get('platform') || 'ccblife';
2025-10-20 22:41:56 +08:00
cityid = urlParams.get('CITYID') || urlParams.get('cityid');
}
// 备用从hash中提取参数UniApp内部跳转可能使用
if (!ccbParamSJ && window.location.hash.includes('?')) {
const hashParts = window.location.hash.split('?');
if (hashParts.length > 1) {
const hashParams = new URLSearchParams(hashParts[1]);
ccbParamSJ = hashParams.get('ccbParamSJ');
2025-10-21 14:56:48 +08:00
platform = hashParams.get('platform') || 'ccblife';
2025-10-20 22:41:56 +08:00
cityid = hashParams.get('CITYID') || hashParams.get('cityid');
}
}
// 获取上次保存的ccbParamSJ
const lastCcbParamSJ = uni.getStorageSync('lastCcbParamSJ') || null;
2025-10-21 14:56:48 +08:00
2025-10-20 22:41:56 +08:00
// 判断参数是否变化
2025-10-21 14:56:48 +08:00
const isParamChanged = ccbParamSJ && lastCcbParamSJ !== ccbParamSJ;
2025-10-20 22:41:56 +08:00
const isFirstTime = ccbParamSJ && !lastCcbParamSJ;
2025-10-21 14:56:48 +08:00
// 如果有建行参数固定建行生活环境只要有ccbParamSJ就执行登录
if (ccbParamSJ) {
2025-10-20 22:41:56 +08:00
// 如果参数未变化,无需重新登录
if (!isParamChanged && !isFirstTime) {
2025-10-21 14:56:48 +08:00
console.log('[CCB] 参数未变化,跳过登录');
const cleanUrl = window.location.origin + '/pages/index/index';
2025-10-20 22:41:56 +08:00
window.history.replaceState({}, '', cleanUrl);
return;
}
2025-10-21 14:56:48 +08:00
console.log(`[CCB] ${isParamChanged ? '切换用户' : '首次登录'}`);
// 防止重复调用
2025-10-20 22:41:56 +08:00
if (isLoggingIn) {
2025-10-21 14:56:48 +08:00
console.log('[CCB] 登录进行中,跳过');
2025-10-20 22:41:56 +08:00
return;
}
isLoggingIn = true;
2025-10-21 14:56:48 +08:00
2025-10-20 22:41:56 +08:00
// 延迟执行登录,确保依赖已初始化
setTimeout(async () => {
try {
// 如果是切换用户,先退出当前用户
const userStore = sheep.$store('user');
if (isParamChanged && userStore && userStore.isLogin) {
await userStore.logout();
uni.removeStorageSync('token');
uni.removeStorageSync('userInfo');
}
// 显示loading
const loadingTitle = isParamChanged ? '切换用户中...' : '建行登录中...';
uni.showLoading({
title: loadingTitle,
2025-10-21 14:56:48 +08:00
mask: true,
2025-10-20 22:41:56 +08:00
});
2025-10-21 14:56:48 +08:00
// 调用建行登录API
2025-10-20 22:41:56 +08:00
const result = await sheep.$api.third.ccbLogin({
ccbParamSJ: ccbParamSJ,
cityid: cityid || '360100',
2025-10-21 14:56:48 +08:00
CITYID: cityid || '360100',
2025-10-20 22:41:56 +08:00
});
uni.hideLoading();
if (result.code === 1) {
2025-10-21 14:56:48 +08:00
console.log('[CCB] 登录成功');
2025-10-20 22:41:56 +08:00
// 设置token和用户信息
sheep.$store('user').setToken(result.data.token);
uni.setStorageSync('userInfo', result.data.user_info);
uni.setStorageSync('lastCcbParamSJ', ccbParamSJ);
// 显示欢迎提示
uni.showToast({
title: `登录成功`,
icon: 'success',
2025-10-21 14:56:48 +08:00
duration: 2000,
2025-10-20 22:41:56 +08:00
});
2025-10-21 14:56:48 +08:00
// 清除URL中的敏感参数
const cleanUrl = window.location.origin + '/pages/index/index';
2025-10-20 22:41:56 +08:00
window.history.replaceState({}, '', cleanUrl);
} else {
throw new Error(result.msg || '登录失败');
}
} catch (error) {
2025-10-21 14:56:48 +08:00
console.error('[CCB] 登录失败:', error.message || error.msg);
2025-10-20 22:41:56 +08:00
uni.hideLoading();
2025-10-21 14:56:48 +08:00
2025-10-20 22:41:56 +08:00
uni.showModal({
title: isParamChanged ? '切换用户失败' : '登录失败',
content: error.message || error.msg || '请检查网络连接',
showCancel: false,
complete: () => {
2025-10-21 14:56:48 +08:00
const cleanUrl = window.location.origin + '/pages/index/index';
2025-10-20 22:41:56 +08:00
window.history.replaceState({}, '', cleanUrl);
2025-10-21 14:56:48 +08:00
},
2025-10-20 22:41:56 +08:00
});
} finally {
isLoggingIn = false;
}
2025-10-21 14:56:48 +08:00
}, 1200);
2025-10-20 22:41:56 +08:00
}
} catch (error) {
2025-10-21 14:56:48 +08:00
console.error('[CCB] 参数解析错误:', error);
2025-10-20 22:41:56 +08:00
}
// #endif
};
2025-10-16 21:07:43 +08:00
</script>
<style lang="scss">
@import '@/sheep/scss/index.scss';
</style>