You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

700 lines
19 KiB

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

import md5 from "./md5.min";
const HOSTARR = {
// 'development':'https://gb-test.ali251.langye.net',
// 'production': 'https://gb-test.ali251.langye.net',
'development':'https://gbyuyue.szgmbwg.org.cn',
'production': 'https://gbyuyue.szgmbwg.org.cn',
// https://gbyuyue.szgmbwg.org.cn/
}; // 审核状态
const HOST = HOSTARR[process.env
.NODE_ENV]; //"https://tiantianxinye.365care.langye.net/";//HOSTARR[process.env.NODE_ENV];//
const replaceImgUrl = (str,before,after)=>{
if(str.indexOf(before) != -1){
return str.replace(new RegExp(before, 'g'),after)
}else{
return str
}
}
const splitTime = (start,end)=> {
let arrStart = start.substring(0, 10).split("-")
let year = parseInt(arrStart[0])
let month = parseInt(arrStart[1]) < 10 ? parseInt(arrStart[1]) : parseInt(arrStart[1])
let day = parseInt(arrStart[2]) < 10 ? parseInt(arrStart[2]) : parseInt(arrStart[2])
if (end) {
// 判断end 是否为时间格式
if(isNaN(end)&&!isNaN(Date.parse(end))){
let arrEnd = end.substring(0, 10).split("-")
let yearEnd = parseInt(arrEnd[0])
let monthEnd = parseInt(arrEnd[1]) < 10 ? parseInt(arrEnd[1]) : parseInt(arrEnd[1])
let dayEnd = parseInt(arrEnd[2]) < 10 ? parseInt(arrEnd[2]) : parseInt(arrEnd[2])
if(year == yearEnd){
return year + '年' + month + '月' + day + '日' + '至' + monthEnd + '月' + dayEnd + '日'
}else{
return year + '年' + month + '月' + day + '日' + '至' + yearEnd + '年'+monthEnd + '月' + dayEnd + '日'
}
}else{
return year + '年' + month + '月' + day + '日' + '至' + end
}
} else {
return year + '年' + month + '月' + day + '日' + '起'
}
}
const formatTime = date => {
const year = date.getFullYear();
const month = date.getMonth() + 1;
const day = date.getDate();
return [year, month, day].map(formatNumber).join('-');
};
const user_info_key = "userInfo_token";
const user_key = "userInfo";
const getUserInfo = (cb, refresh) => {
cb = cb || function() {}
refresh = refresh || false
if (!refresh) {
let user_info = uni.getStorageSync(user_key)
if (!isNull(user_info)) {
cb(user_info)
return
}
}
request({
api: '/api/mobile/user/show',
utilSuccess: function(res) {
uni.setStorageSync(user_key, res)
cb(res)
},
utilFail: function(res) {}
})
}
const getOpenidInfo = (cb, refresh) => {
// cb = cb || function() {}
// refresh = refresh || false
// console.log("getOpenidInfo", refresh)
// if (!refresh) {
// let user_info = uni.getStorageSync(user_info_key)
// if (!isNull(user_info)) {
// cb(user_info)
// return
// }
// }
let user_info = uni.getStorageSync(user_info_key)
if (!isNull(user_info)) {
uni.showToast({ title: '已经有用户信息,故不进行登录', icon: 'success' })
cb(user_info)
return
}
// 判断运行环境H5还是小程序
const isH5 = typeof window !== 'undefined' && window.location
const isWeixinBrowser = isH5 && /MicroMessenger/i.test(navigator.userAgent)
// uni.showToast({ title: 'isH5:'+isH5, icon: 'success' })
// uni.showToast({ title: 'isWeixinBrowser:'+isWeixinBrowser, icon: 'success' })
if (isH5 && isWeixinBrowser) {
// H5环境下的微信授权登录
wxH5AuthLogin(cb)
} else {
// 小程序环境下的微信登录
uni.login({
provider: 'weixin',
success: (res) => {
console.log(res.code);
let url = HOST + '/api/mobile/user/login?code=' + res.code;
uni.request({
url: url,
method: 'GET',
success: result => {
let user_info = result.data
uni.setStorageSync(user_info_key, user_info)
cb(user_info)
}
});
}
});
}
}
// H5环境下的微信授权登录
const wxH5AuthLogin = (cb) => {
let link = window.location.href;
if (/code=/.test(link) || link.indexOf("code") > -1) {
// 已经获取到授权码,直接登录
let temp = decodeURIComponent((new RegExp('[?|&]' + 'code' + '=' + '([^&;]+?)(&|#|;|$)').exec(
link) || [, ''])[1].replace(/\+/g, '%20')) || null;
console.log("code", temp)
// uni.showToast({ title: '授权码:'+temp, icon: 'success' })
// 上传 code 到服务器获取 token
request({
api: `/api/mobile/user/wx-login?code=${temp}`,
method: 'GET',
utilSuccess: (res) => {
if (res.token && res.token.trim() !== '') {
uni.showToast({ title: '登录成功', icon: 'success' })
// 保持与小程序登录一致的存储方式
const userInfo = {
token: res.token,
// 可以根据需要添加其他字段,如 WeChatOpenID 等
}
uni.setStorageSync(user_info_key, userInfo)
cb(userInfo)
} else {
console.error('登录失败: token为空')
uni.showToast({ title: '登录失败,请重试', icon: 'none' })
}
},
utilFail: (err) => {
console.error('获取 token 失败:', err)
uni.showToast({ title: '登录失败,请重试', icon: 'none' })
}
})
} else {
// 未获取授权码,跳转到微信授权页面
const appId = 'wx90acb6e2aa676977'
const currentUrl = window.location.href
const redirectUri = encodeURIComponent(currentUrl.replace(/#\//, ""));
const scope = 'snsapi_userinfo'
const state = 'STATE'
console.log(redirectUri)
const authUrl = `https://open.weixin.qq.com/connect/oauth2/authorize?appid=${appId}&redirect_uri=${redirectUri}&response_type=code&scope=${scope}&state=${state}#wechat_redirect`
// 重定向到微信授权页面
window.location.href = authUrl
}
}
const getUserProfile = (cb) => {
cb = cb || function() {}
// 判断运行环境H5还是小程序
const isH5 = typeof window !== 'undefined' && window.location
const isWeixinBrowser = isH5 && /MicroMessenger/i.test(navigator.userAgent)
if (isH5 && isWeixinBrowser) {
// H5环境下通过后端接口获取用户信息
// 微信公众号H5无法直接调用wx.getUserProfile
request({
api: '/api/mobile/user/profile',
method: 'GET',
utilSuccess: (res) => {
uni.setStorageSync('user_profile', res)
cb(res)
},
utilFail: (err) => {
console.error('获取用户信息失败:', err)
cb(null)
}
})
} else {
// 小程序环境下使用wx.getUserProfile
wx.getUserProfile({
desc: '用于完善会员资料',
success: (res) => {
uni.setStorageSync('user_profile', res.userInfo)
cb(res.userInfo)
},
fail: (err) => {
console.error('获取用户信息失败:', err)
cb(null)
}
})
}
}
const formatTimeAll = date => {
const year = date.getFullYear();
const month = date.getMonth() + 1;
const day = date.getDate();
const hour = date.getHours();
const minute = date.getMinutes();
const second = date.getSeconds();
return [year, month, day].map(formatNumber).join('-') + ' ' + [hour, minute, second].map(formatNumber).join(
':');
};
const formatNumber = n => {
n = n.toString();
return n[1] ? n : '0' + n;
}; // 快捷显示alert
const alert = msg => {
uni.showModal({
title: '',
content: msg,
showCancel: false
});
}; // 订单状态
const toast = msg => {
// setTimeout(function() {
// uni.showToast({
// icon: "none",
// title: msg,
// duration: 2000
// })
// }, 2000)
uni.showModal({
title: '',
content: msg,
showCancel: false
});
}; // 订单状态
const orderStatusDic = {
'0': '待确认',
'10': '待派单',
'20': '进行中',
'100': '已完成'
}; // 审核状态
const auditStatusDic = {
'0': '待审核',
'1': '已审核',
'-1': '已拒绝'
}; // 请求封装
const request = options => {
if (!options.customLoading) {
uni.showLoading({
title: '正在加载'
});
} else {
// 当前页面请求数量+1
// if (options.bindThis) {
// options.bindThis.setData({
// //loadingCount: options.bindThis.data.loadingCount + 1
// });
// }
}
options.url = HOST + options.api;
options.header = {
...options.header,
//'Accept': 'application/json',
//'Connection': 'keep-alive'
//'content-type': 'application/json'
}; // 如果已登录,请求中拼openId
var access_token = uni.getStorageSync(user_info_key).token;
if (isLogin()) {
options.data = {
...options.data,
'token': access_token
};
} // 如果是POST方法
if (options.method == 'POST' && !isNull(access_token)) {
// 拼时间戳
options.data.ts = new Date().getTime();
}
uni.request({
...options,
success: function(res) {
uni.hideLoading();
if (res.statusCode != 200) {
if (options.utilFail != undefined) {
if (res.statusCode == 401) {
uni.clearStorageSync();
uni.navigateTo({
url: '/pages/login/login'
});
} else {
options.utilFail('TODO: 特殊处理非200错误(' + res.statusCode + ')');
}
}
// 清除所有缓存,如果发生错误.
uni.clearStorageSync();
} else {
if (res.data.hasOwnProperty("errcode")) {
if (options.utilFail != undefined) {
options.utilFail(res.data.errmsg || '接口发生未知错误');
} else {
options.utilFail(res.data.errmsg);
}
// 清除所有缓存,如果发生错误.
uni.clearStorageSync();
} else {
if (options.utilSuccess != undefined) {
options.utilSuccess(res.data);
}
}
}
},
fail: options.utilFail,
complete: function(res) {
if (!options.customLoading) {
uni.hideNavigationBarLoading();
} else {
// 当前页面请求数量-1
// if (options.bindThis) {
// options.bindThis.setData({
// loadingCount: options.bindThis.data.loadingCount - 1
// });
// }
}
}
});
}; // 提交formID封装
const payOrder = (orderID, orderType, success, fail) => {
uni.request({
url: HOST + 'WxPay/ToPay?openId=' + uni.getStorageSync(user_info_key).WeChatOpenID +
'&orderId=' +
orderID + '&OrderType=' + orderType,
method: 'GET',
header: {
'content-type': 'application/json'
},
success: function(res) {
// 内容为空, 代表失败
if (res.data == '') {
fail('当前网络状况不好');
return;
} // 去掉转义字符
var pureStr = res.data.replace(/\\/g, '');
res.data = JSON.parse(pureStr);
var index = res.data.package.indexOf('=') + 1;
var prepayId = res.data.package.substring(index); // wxpay
uni.requestPayment({
timeStamp: res.data.timeStamp,
nonceStr: res.data.nonceStr,
package: res.data.package,
signType: res.data.signType,
paySign: res.data.paySign,
success: function(res) {
success(res); // 发送成功通知
request({
api: 'WxPay/PayTemplateMsg',
data: {
prepay_id: prepayId,
orderId: orderID,
isSuccess: 1,
failMsg: '',
xType: orderType
}
});
},
fail: function(res) {
fail(res);
var errMsg = res == 'requestPayment:fail cancel' ? '用户取消支付' :
res; // 发送失败通知
request({
api: 'WxPay/PayTemplateMsg',
data: {
prepay_id: prepayId,
orderId: orderID,
isSuccess: 0,
failMsg: errMsg,
xType: orderType
}
});
}
});
},
fail: function(err) {
fail('当前网络状况不好');
}
});
}; // 判断是否已登录同时有open-id和PhoneNum, 则认为已登录)
const isLogin = () => {
var userInfo = uni.getStorageSync(user_info_key);
return !isNull(userInfo.token);
}; // 判断是否为空
const isNull = p => {
return p == '' || p == undefined || p == null || p == 'undefined' || p == 'null';
}; // 正则
const phoneRegex = /^1[3456789]\d{9}$/;
const idCardRegex = /^\d{17}([0-9]|X)$/; // 去掉特殊字符
const filterSpecialChars = str => {
return str.replace(/[^\u4e00-\u9fa5a-zA-Z0-9\w]/g, '');
}; // 生成随机字符串
const randomStr = length => {
var ret = '';
var arr = ['0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h',
'i', 'j',
'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z', 'A', 'B', 'C',
'D', 'E',
'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X',
'Y', 'Z'
];
for (var i = 0; i < length; i++) {
var randomIndex = Math.round(Math.random() * (arr.length - 1));
ret += arr[randomIndex];
}
return ret;
}; // proType对应的中文描述
const weekdayArr = ['周日', '周一', '周二', '周三', '周四', '周五', '周六']; // 是否合法的身份证
const isValidCardID = cardID => {
// Step1: 先判断格式
if (!idCardRegex.test(cardID)) return false; // Step2: 校验最后一位
var code = cardID.split(''); //加权因子
var factor = [7, 9, 10, 5, 8, 4, 2, 1, 6, 3, 7, 9, 10, 5, 8, 4, 2]; //校验位
var parity = [1, 0, 'X', 9, 8, 7, 6, 5, 4, 3, 2];
var sum = 0;
var ai = 0;
var wi = 0;
for (var i = 0; i < 17; i++) {
ai = code[i];
wi = factor[i];
sum += ai * wi;
}
var last = parity[sum % 11];
return parity[sum % 11] == code[17];
};
const shareInfo = {
title:"",
imageUrl:"/static/share.jpg"
}
/**
* UTF16和UTF8转换对照表
* U+00000000 U+0000007F 0xxxxxxx
* U+00000080 U+000007FF 110xxxxx 10xxxxxx
* U+00000800 U+0000FFFF 1110xxxx 10xxxxxx 10xxxxxx
* U+00010000 U+001FFFFF 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx
* U+00200000 U+03FFFFFF 111110xx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
* U+04000000 U+7FFFFFFF 1111110x 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
*/
var Base64 = {
// 转码表
table: ['A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S',
'T', 'U',
'V', 'W', 'X', 'Y', 'Z', 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n',
'o', 'p',
'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z', '0', '1', '2', '3', '4', '5', '6', '7', '8',
'9', '+',
'/'
],
UTF16ToUTF8: function(str) {
var res = [],
len = str.length;
for (var i = 0; i < len; i++) {
var code = str.charCodeAt(i);
if (code > 0x0000 && code <= 0x007F) {
// 单字节这里并不考虑0x0000因为它是空字节
// U+00000000 U+0000007F 0xxxxxxx
res.push(str.charAt(i));
} else if (code >= 0x0080 && code <= 0x07FF) {
// 双字节
// U+00000080 U+000007FF 110xxxxx 10xxxxxx
// 110xxxxx
var byte1 = 0xC0 | code >> 6 & 0x1F; // 10xxxxxx
var byte2 = 0x80 | code & 0x3F;
res.push(String.fromCharCode(byte1), String.fromCharCode(byte2));
} else if (code >= 0x0800 && code <= 0xFFFF) {
// 三字节
// U+00000800 U+0000FFFF 1110xxxx 10xxxxxx 10xxxxxx
// 1110xxxx
var byte1 = 0xE0 | code >> 12 & 0x0F; // 10xxxxxx
var byte2 = 0x80 | code >> 6 & 0x3F; // 10xxxxxx
var byte3 = 0x80 | code & 0x3F;
res.push(String.fromCharCode(byte1), String.fromCharCode(byte2), String.fromCharCode(
byte3));
} else if (code >= 0x00010000 && code <= 0x001FFFFF) { // 四字节
// U+00010000 U+001FFFFF 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx
} else if (code >= 0x00200000 && code <= 0x03FFFFFF) { // 五字节
// U+00200000 U+03FFFFFF 111110xx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
} else
/** if (code >= 0x04000000 && code <= 0x7FFFFFFF)*/
{ // 六字节
// U+04000000 U+7FFFFFFF 1111110x 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
}
}
return res.join('');
},
UTF8ToUTF16: function(str) {
var res = [],
len = str.length;
var i = 0;
for (var i = 0; i < len; i++) {
var code = str.charCodeAt(i); // 对第一个字节进行判断
if ((code >> 7 & 0xFF) == 0x0) {
// 单字节
// 0xxxxxxx
res.push(str.charAt(i));
} else if ((code >> 5 & 0xFF) == 0x6) {
// 双字节
// 110xxxxx 10xxxxxx
var code2 = str.charCodeAt(++i);
var byte1 = (code & 0x1F) << 6;
var byte2 = code2 & 0x3F;
var utf16 = byte1 | byte2;
res.push(Sting.fromCharCode(utf16));
} else if ((code >> 4 & 0xFF) == 0xE) {
// 三字节
// 1110xxxx 10xxxxxx 10xxxxxx
var code2 = str.charCodeAt(++i);
var code3 = str.charCodeAt(++i);
var byte1 = code << 4 | code2 >> 2 & 0x0F;
var byte2 = (code2 & 0x03) << 6 | code3 & 0x3F;
utf16 = (byte1 & 0x00FF) << 8 | byte2;
res.push(String.fromCharCode(utf16));
} else if ((code >> 3 & 0xFF) == 0x1E) { // 四字节
// 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx
} else if ((code >> 2 & 0xFF) == 0x3E) { // 五字节
// 111110xx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
} else
/** if (((code >> 1) & 0xFF) == 0x7E)*/
{ // 六字节
// 1111110x 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
}
}
return res.join('');
},
encode: function(str) {
if (!str) {
return '';
}
var utf8 = this.UTF16ToUTF8(str); // 转成UTF8
var i = 0; // 遍历索引
var len = utf8.length;
var res = [];
while (i < len) {
var c1 = utf8.charCodeAt(i++) & 0xFF;
res.push(this.table[c1 >> 2]); // 需要补2个=
if (i == len) {
res.push(this.table[(c1 & 0x3) << 4]);
res.push('==');
break;
}
var c2 = utf8.charCodeAt(i++); // 需要补1个=
if (i == len) {
res.push(this.table[(c1 & 0x3) << 4 | c2 >> 4 & 0x0F]);
res.push(this.table[(c2 & 0x0F) << 2]);
res.push('=');
break;
}
var c3 = utf8.charCodeAt(i++);
res.push(this.table[(c1 & 0x3) << 4 | c2 >> 4 & 0x0F]);
res.push(this.table[(c2 & 0x0F) << 2 | (c3 & 0xC0) >> 6]);
res.push(this.table[c3 & 0x3F]);
}
return res.join('');
},
decode: function(str) {
if (!str) {
return '';
}
var len = str.length;
var i = 0;
var res = [];
while (i < len) {
var code1 = this.table.indexOf(str.charAt(i++));
var code2 = this.table.indexOf(str.charAt(i++));
var code3 = this.table.indexOf(str.charAt(i++));
var code4 = this.table.indexOf(str.charAt(i++));
var c1 = code1 << 2 | code2 >> 4;
var c2 = (code2 & 0xF) << 4 | code3 >> 2;
var c3 = (code3 & 0x3) << 6 | code4;
res.push(String.fromCharCode(c1));
if (code3 != 64) {
res.push(String.fromCharCode(c2));
}
if (code4 != 64) {
res.push(String.fromCharCode(c3));
}
}
return this.UTF8ToUTF16(res.join(''));
}
};
module.exports = {
HOST: HOST,
formatTime: formatTime,
formatTimeAll: formatTimeAll,
formatNumber: formatNumber,
alert: alert,
getOpenidInfo: getOpenidInfo,
wxH5AuthLogin: wxH5AuthLogin,
request: request,
payOrder: payOrder,
isLogin: isLogin,
isNull: isNull,
phoneRegex: phoneRegex,
idCardRegex: idCardRegex,
filterSpecialChars: filterSpecialChars,
randomStr: randomStr,
weekdayArr: weekdayArr,
Base64: Base64,
orderStatusDic: orderStatusDic,
auditStatusDic: auditStatusDic,
getUserProfile: getUserProfile,
getUserInfo: getUserInfo,
toast: toast,
isValidCardID:isValidCardID,
shareInfo:shareInfo,
replaceImgUrl:replaceImgUrl,
splitTime:splitTime
};