// plugin/etc/pages/activeDes/activeDes.js import { configPluginData, failPluginData } from "../../../config.js" import { ActiveDevice, DisConnectDevice, EquipmentDetection, ObuSystemInfo } from "../../../utils/active-tools/active-device-tools.js" import { starSearch, stopSearch } from "../../../utils/blue-related-tools/blue_tool.js" import { formatCardNumber } from "../../../utils/obj-tools.js" import { HOME_DIRECTORY, OBU_SYSTEM_FILE, RANDOM_NUMBER, APPLICATION_DIRECTORY, CMD_READBINARY, CMD_GETBALANCE } from '../../../utils/cmdConfig' import { transCmd, transCmdArrAfter, transCmdAfter } from '../../../utils/etc-sdk-tool/etc-sdk-tool' import { API } from '../../../network/etcApi' Page({ /** * 页面的初始数据 */ data: { orderNo: "", type: 1, devList: [{ device: { name: "ETC-JL-01" }, is_select: false, }, { device: { name: "ETC-JL-02" }, is_select: false, }], showPopDevice: false, obuIdStr: "xxxx xxxx xxxx xxxx", cardIdStr: "xxxx xxxx xxxx xxxx", searchFailMsg: "请检查手机蓝牙、ETC蓝牙是否均已打开,连接过程中将手机和ETC设备尽量靠近", searchFailTitle: "未检测到ETC设备", activeFail: false, activeFailMsg: "不可发行/设备未入库", showType: 1, obuInfo: { version: '', obuId: '', chipSn: '' }, cardInfo: { version: '', cardId: '' } }, /** * 生命周期函数--监听页面加载 */ onLoad(options) { this.configData(options) }, onUnload() { this.configStop() }, /// -------------- 工具类型 ---------------- /// // 配置默认参数 configData(options) { configPluginData() const orderNo = options?.orderNo if (orderNo) { this.setData({ orderNo }) } }, /// 新版激活 -------- 触发方法 /// 停止一切与设备相关的操作 async configStop(isStop = true) { console.log('configStop') console.log("这个方法里执行断开设备") await DisConnectDevice() stopSearch(isStop) }, // 点击开始搜索 tapStar() { this.configNavTitle() this.setData({ showPopDevice: false, devList: [], showType: 1, }) wx.showLoading({ title: '正在搜索设备...', }) let self = this; starSearch((DevResult) => { console.log(DevResult); wx.hideLoading() if (DevResult.code == 0) { self.configNavTitle("验证设备") self.setData({ devList: DevResult.data, showPopDevice: true, }); } else { self.configSearchFail(DevResult.code) } }, false, "", false); }, /// 配置导航栏标题 configNavTitle(title = "设备搜索") { wx.setNavigationBarTitle({ title: title, }) }, async tapOwner(e) { console.log(e) stopSearch(false); let device = e.detail; const res = await this.configActive(device); await DisConnectDevice() wx.hideLoading() if (res.code == 0) { this.configActiveSuccess(); } else if (res.code == 250) { this.configSearchFail(res.code) } else { this.setData({ activeFail: true, devName: device.name || "", activeFailMsg: res.msg || '请检查ETC硬件是否处于通电并开启蓝牙的状态' }) } }, async configActive(device) { const that = this; const rt = await EquipmentDetection({ device, disconnectCallback: () => { that.configSearchFail(250) }, }) if (rt.code !== 0) { return rt } else { this.configEtcNumber(rt.data); // 激活前先查看是否需要升级设备 await this.getObjDetail() await this.getCardId() if (this.data.obuInfo.version == '48' || this.data.obuInfo.version == '49' || this.data.cardInfo.version == '48' || this.data.cardInfo.version == '49') { await this.devideUpgrade() // 升级以后需要重新更新一下设备信息 await ObuSystemInfo() } // 激活逻辑 const res = await ActiveDevice({ device, params: { orderNo: this.data.orderNo, }, disconnectCallback: () => { that.configSearchFail(250) }, isNeedContect: false, isNeedReadDevice: false }) return res } }, configActiveSuccess() { wx.redirectTo({ url: 'plugin://issuer-plugin/activeStatus' + "?obu=" + this.data.obuIdStr + "&card=" + this.data.cardIdStr + "&type=1", }) }, // 格式化obu号 configEtcNumber(data) { this.setData({ obuIdStr: formatCardNumber(data.serialNumber), cardIdStr: formatCardNumber(data.faceCardNum), }) }, // 配置搜索失败 configSearchFail(code) { let failMsg = "请检查手机蓝牙、ETC蓝牙是否均已打开,连接过程中将手机和ETC设备尽量靠近" let failTitle = "未检测到ETC设备" if (code == -111 || code == -112) { failMsg = code == -111 ? "手机蓝牙权限未授权,无法读取蓝牙是否开启状态,请打开蓝牙" : "手机定位权限获取失败,请前往手机系统设置开启手机定位服务" failTitle = "蓝牙状态异常" } this.setData({ showType: 2, searchFailMsg: failMsg, searchFailTitle: failTitle, }) }, tapActiveFailSure() { failPluginData(this.data.activeFailMsg); this.setData({ activeFail: false, }); wx.navigateBack() }, // 获取Obu设备详情 async getObjDetail () { let cmdArr = [HOME_DIRECTORY, OBU_SYSTEM_FILE, RANDOM_NUMBER] let res = await transCmd(cmdArr, '20') console.log('设备卡签信息:1111') console.log(res) let cmdResult = res.cmdResult ? res.cmdResult.split(',') : [] if (cmdResult && cmdResult.length) { var status = cmdResult[1].substring(cmdResult[1].length - 4, cmdResult[1].length); //第一次获取随机数 if (status == "9000") { this.data.obuInfo.obuId = cmdResult[1].substring(20, 36); this.data.obuInfo.version = cmdResult[1].substring(18, 20); this.data.obuInfo.chipSn = cmdResult[1].substring(0, 8) console.log(this.data.obuInfo) } else { wx.showToast('获取设备信息错误!') } } else { wx.showToast('获取设备信息错误!') } return true }, // 获取卡信息 async getCardId () { let cmdArr = [HOME_DIRECTORY, APPLICATION_DIRECTORY, CMD_READBINARY, CMD_GETBALANCE]; let res = await transCmd(cmdArr, '10') let cmdResult = res.cmdResult ? res.cmdResult.split(',') : [] let str = cmdResult[2].substring(cmdResult[2].length - 4, cmdResult[2].length); //判断是否为9000 let str3 = cmdResult[3].substring(cmdResult[3].length - 4, cmdResult[3].length); //判断是否为9000 if (str == "9000" || str3 == "9000") { if (cmdResult[2].length > 86 || cmdResult[3] >= 12) { this.data.cardInfo.cardId = cmdResult[2].substring(20, 40); this.data.cardInfo.version = cmdResult[2].substring(18, 20) console.log(this.data.cardInfo) } else { wx.showModal({ title: '提示', content: "CMD_READBINARY指令长度不符" + cmdResult }) } return; } else { return true } return true }, // 设备升级 async devideUpgrade () { return new Promise(async resolve => { let params = { contractSN: this.data.obuInfo.obuId, //OBU合同序列号 16位 chipSn: this.data.obuInfo.chipSn, //OBU晶片序列号 8位 issueMode: 'UPG', //发行模式 issueType: 'SCOBU', //发行发行类型 cardVersion: this.data.cardInfo.version, //卡版本号 obuVersion: this.data.obuInfo.version //OBU版本号 } let applyData = await API.ETC.getVfjApply4Upgrade(params) console.log('9999 获取设备升级指令') console.log(applyData) if (!applyData || (applyData && applyData.code !== 0)) { // this.showModals('获取升级指令失败') return false } let applyDataRes = applyData.data if (this.data.obuInfo.version == '48' || this.data.obuInfo.version == '49') { const updateEsDat = await this.updateEs('GEN_OBEIC_UPG', applyDataRes); if (!updateEsDat) return false; } if (this.data.cardInfo.version == '48' || this.data.cardInfo.version == '49') { const updateEsDatTwo = await this.updateEs('GEN_OBESAM_UPG', applyDataRes); if (!updateEsDatTwo) return false; } const upgradeDoneData = await API.ETC.vfjUpgradeDone({ issueSerialNo: applyDataRes.issueSerialNo, //发行订单号 }); if (!upgradeDoneData || (upgradeDoneData && upgradeDoneData.code !== 0)) return false; // 升级完成后完成后重新写入 const cardres = await this.getCardIdAfter(); if(!cardres) return false; const obures = await this.getObuIdAfter(); if(!obures) return false; resolve(true) }) // wx.showModal({ // title: '提示', // content: '设备升级完成', // showCancel: false, // complete: (res) => { // if (res.confirm) { // wx.navigateBack() // } // } // }) }, // 获取发行指令脚本 async updateEs (type, applyData) { wx.showLoading({ title: '设备升级中' }) let getCommanData = await API.ETC.getVfjGetCommands({ cardNo: applyData.cardNo, //卡片序列号 wareId: type, //OBU的物料代码 OBE-SAM通道 GEN_OBESAM_UPG OBE-IC通道 GEN_OBEIC_UPG issueSerialNo: applyData.issueSerialNo, //发行订单号 }) if (!getCommanData || (getCommanData && getCommanData.code !== 0)) { // this.showModals('获取发行脚本指令失败') return false }; let getCommanDataRes = getCommanData.data //指令解析 const result = getCommanDataRes.commands; const array = result.split('~'); let cmdType = type == 'GEN_OBESAM_UPG' ? '20' : '10'; for (const element of array) { console.log('updateEs', element, cmdType); // 让出主线程,确保UI更新 await new Promise(resolve => setTimeout(resolve, 0)); console.log("进来了", element.charAt(0), ) if (element.charAt(0) === 'D' || element.charAt(0) === 'R') { await this.processDirectCommand(element, cmdType); } else if (element.charAt(0) === 'K') { await this.processKeyExchange(element, cmdType, applyData); } else if (element.charAt(0) === 'E') { await this.processExtAuth(element, cmdType, applyData); } else if (element === 'SESAM') { cmdType = '20'; } else { cmdType = '10'; } } return true; }, processDirectCommand(element, cmdType) { // 添加随机延迟,避免连续请求 return transCmdArrAfter(element.substring(1), cmdType); }, async processKeyExchange(element, cmdType, applyData) { const ranData = await transCmdArrAfter('0084000004', cmdType); console.log("ranData", ranData) const exchangeKeyData = await API.ETC.vfjExchangeKey({ key: element.substring(1), random: ranData['0084000004'][0].substring(0, 8), issueSerialNo: applyData.issueSerialNo }); if (!exchangeKeyData) throw new Error('密钥置换失败'); console.log("exchangeKeyData", exchangeKeyData) let exchangeKeyDataRes = exchangeKeyData.data return transCmdArrAfter(exchangeKeyDataRes.apdu, cmdType); }, async processExtAuth(element, cmdType, applyData) { const ranData = await transCmdArrAfter('0084000004', cmdType); const extAuth4IssData = await API.ETC.vfjExtAuth4Iss({ keyType: element.substring(1), random: ranData['0084000004'][0].substring(0, 8), issueSerialNo: applyData.issueSerialNo, }); console.log("extAuth4IssData", extAuth4IssData) if (!extAuth4IssData) throw new Error('外部认证失败'); let extAuth4IssDataRes = extAuth4IssData.data return transCmdArrAfter(extAuth4IssDataRes.apdu, cmdType); }, // 读卡 async getCardIdAfter () { return new Promise(async (resolve, reject) =>{ try{ let cmdArr = [HOME_DIRECTORY, APPLICATION_DIRECTORY, CMD_READBINARY, CMD_GETBALANCE]; const res = await transCmdAfter(cmdArr, "10"); let cmdResult = res.cmdResult ? res.cmdResult.split(',') : [] let str = cmdResult[2].substring(cmdResult[2].length - 4, cmdResult[2].length); //判断是否为9000 let str3 = cmdResult[3].substring(cmdResult[3].length - 4, cmdResult[3].length); //判断是否为9000 if (str == "9000" || str3 == "9000") { if (cmdResult[2].length > 86 || cmdResult[3] >= 12) { // card.cardId = cmdResult[2].substring(20, 40); // card.cardId = '52012511110201724155'; this.data.cardInfo.cardId = cmdResult[2].substring(20, 40); this.data.cardInfo.version = cmdResult[2].substring(18, 20); console.log(9999999) console.log(this.data.cardInfo) wx.hideLoading() resolve(true); return } else { console.log("CMD_READBINARY指令长度不符" + cmdResult[2]); this.showModals("CMD_READBINARY指令长度不符" + cmdResult[2]) resolve(false); return } } console.log("CMD_READBINARY指令长度不符" + cmdResult[2]); this.showModals("CMD_READBINARY指令长度不符" + cmdResult[2]) resolve(false); return } catch (e) { //TODO handle the exception console.log('错误错误', e); reject(e); } }) }, // 读取签 getObuIdAfter(){ return new Promise(async (resolve, reject) =>{ try{ let cmdArray = [HOME_DIRECTORY, OBU_SYSTEM_FILE, RANDOM_NUMBER]; const res = await transCmdAfter(cmdArray, "20"); let cmdResult = res.cmdResult ? res.cmdResult.split(',') : [] var status = cmdResult[1].substring(cmdResult[1].length - 4, cmdResult[1].length); console.log('获取OBU号执行结果' + status, cmdResult) //第一次获取随机数 if (status == "9000") { this.data.obuInfo.obuId = cmdResult[1].substring(20, 36); this.data.obuInfo.version = cmdResult[1].substring(18, 20); this.data.obuInfo.chipSn = cmdResult[1].substring(0, 8) resolve(true); console.log("success") return } else { this.showModals('获取设备信息错误!') resolve(false); return } } catch (e) { //TODO handle the exception console.log('错误错误', e); reject(e); } }) }, showModals (content) { wx.showModal({ title: '提示', content: content, showCancel: false }) }, })