feata:微信安全测试

This commit is contained in:
2026-07-24 21:05:21 +08:00
parent 73a7da4804
commit 3eba959b48
6 changed files with 209 additions and 68 deletions
+12
View File
@@ -195,6 +195,18 @@
"router" : { "router" : {
"mode" : "hash", "mode" : "hash",
"base" : "" "base" : ""
},
"devServer" : {
"port" : 5173,
"proxy" : {
"/proxy-api" : {
"target" : "https://api.o.tbmall.xin",
"changeOrigin" : true,
"pathRewrite" : {
"^/proxy-api" : ""
}
}
}
} }
} }
} }
+1 -1
View File
@@ -772,7 +772,7 @@ export default {
left: 0; left: 0;
right: 0; right: 0;
height: 4px; height: 4px;
background: linear-gradient(270deg, #af39c4 0%, #7732ff 100%); //background: linear-gradient(270deg, #af39c4 0%, #7732ff 100%);
pointer-events: none; pointer-events: none;
} }
} }
@@ -216,14 +216,14 @@
{{ selectSpecificationTempl.price }} {{ selectSpecificationTempl.price }}
</text> </text>
<view style="font-size: 50rpx" v-else> <view style="font-size: 50rpx" v-else>
{{ skuBySpecInfo.supplyPrice }} {{ skuBySpecInfo.originalPrice }}
<text v-if="skuBySpecInfo.price">- {{ skuBySpecInfo.price }}</text> <text v-if="skuBySpecInfo.price">- {{ skuBySpecInfo.price }}</text>
</view> </view>
<view class="price_content_coupon_warp" v-if="orderInfo.couponPrice && orderInfo.couponPrice !== 0"> <view class="price_content_coupon_warp" v-if="orderInfo.couponPrice && orderInfo.couponPrice !== 0">
优惠券{{ 优惠券{{
orderInfo.couponPrice }}</view> orderInfo.couponPrice }}</view>
</view> </view>
<view class="oOrice_content_warp" v-if="!isCoupon">¥{{ skuBySpecInfo.supplyPrice }}</view> <view class="oOrice_content_warp" v-if="!isCoupon">¥{{ skuBySpecInfo.originalPrice }}</view>
<view class="coupon_content_warp" v-if="orderInfo.couponPrice && orderInfo.couponPrice !== 0"> <view class="coupon_content_warp" v-if="orderInfo.couponPrice && orderInfo.couponPrice !== 0">
优惠券已优惠¥{{ 优惠券已优惠¥{{
orderInfo.couponPrice }}</view> orderInfo.couponPrice }}</view>
@@ -1224,7 +1224,7 @@ export default {
const skuBySpecBash = this.getSkuBySpecValueIds(this.selectedSpecValueIds) || {}; const skuBySpecBash = this.getSkuBySpecValueIds(this.selectedSpecValueIds) || {};
console.log("----111", skuBySpecBash) console.log("----111", skuBySpecBash)
this.skuBySpecInfo = { ...this.orderInfo, skuImage: skuBySpecBash.skuImage, stock: skuBySpecBash.stock, supplyPrice: skuBySpecBash.supplyPrice, price: skuBySpecBash.price, skuName: skuBySpecBash.skuName } this.skuBySpecInfo = { ...this.orderInfo, skuImage: skuBySpecBash.skuImage, stock: skuBySpecBash.stock, supplyPrice: skuBySpecBash.supplyPrice, price: skuBySpecBash.price, skuName: skuBySpecBash.skuName, originalPrice: skuBySpecBash.originalPrice }
console.log("----222", this.orderInfo) console.log("----222", this.orderInfo)
if (this.selectedSpecValueIds.every((id) => id != null)) { if (this.selectedSpecValueIds.every((id) => id != null)) {
+151 -48
View File
@@ -4,25 +4,21 @@
<Header title="设置" /> <Header title="设置" />
<view class="setting-view"> <view class="setting-view">
<view class="item-list mt-24"> <view class="item-list mt-24">
<view class="flex-r-lr item-box" @click="onHead(index)" <view class="flex-r-lr item-box" @click="onHead(index)" v-for="(item, index) in headList" :key="index"
v-for="(item,index) in headList" :key="index" :style="{ borderWidth: index == headList.length - 1 ? '0' : '2rpx' }">
:style="{borderWidth:index == headList.length - 1 ? '0' : '2rpx'}" <text class="text-gray text-32">{{ item.text }}</text>
>
<text class="text-gray text-32">{{item.text}}</text>
<view class="flex-r-e" style="align-items: center;"> <view class="flex-r-e" style="align-items: center;">
<image v-if="item.type == 'img'" :src="item.value" class="ava-img"></image> <image v-if="item.type == 'img'" :src="item.value" class="ava-img"></image>
<text class="text-zu text-32" v-if="item.type == 'text'">{{item.value}}</text> <text class="text-zu text-32" v-if="item.type == 'text'">{{ item.value }}</text>
<u-icon size="16" name="arrow-right" color="#666" style="margin-left:12rpx"></u-icon> <u-icon size="16" name="arrow-right" color="#666" style="margin-left:12rpx"></u-icon>
</view> </view>
</view> </view>
</view> </view>
<view class="item-list mt-24"> <view class="item-list mt-24">
<view class="flex-r-lr item-box" @click="onBottom(index)" <view class="flex-r-lr item-box" @click="onBottom(index)" v-for="(item, index) in bottomList"
v-for="(item,index) in bottomList" :key="index" :key="index" :style="{ borderWidth: index == bottomList.length - 1 ? '0' : '2rpx' }">
:style="{borderWidth:index == bottomList.length - 1 ? '0' : '2rpx'}" <text class="text-gray text-32">{{ item.text }}</text>
>
<text class="text-gray text-32">{{item.text}}</text>
<view class="flex-r-e" style="align-items: center;"> <view class="flex-r-e" style="align-items: center;">
<u-icon size="16" name="arrow-right" color="#666" style="margin-left:12rpx"></u-icon> <u-icon size="16" name="arrow-right" color="#666" style="margin-left:12rpx"></u-icon>
</view> </view>
@@ -36,34 +32,34 @@
</template> </template>
<script> <script>
import { getUserInfo,uploadAvatar } from '@/api/auth.js'; import { getUserInfo, uploadAvatar } from '@/api/auth.js';
import { uploadImage, uploadImg } from '@/api/common.js'; import { uploadImage, uploadImg } from '@/api/common.js';
import { IMG_TYPE } from '@/utils/enumUtils.js'; import { IMG_TYPE } from '@/utils/enumUtils.js';
import { BASE_URL, Authorization } from '@/utils/config.js'; import { BASE_URL, Authorization } from '@/utils/config.js';
import { getStorageFun, TOKEN_NAME,clear } from '@/utils/auth.js'; import { getStorageFun, TOKEN_NAME, clear } from '@/utils/auth.js';
import Header from '@/components/common/header.vue'; import Header from '@/components/common/header.vue';
import TopSafe from '@/components/common/top-safe.nvue' import TopSafe from '@/components/common/top-safe.nvue'
import MyBtn from '@/components/common/my-btn.vue' import MyBtn from '@/components/common/my-btn.vue'
import func from '@/utils/func.js'; import func from '@/utils/func.js';
export default { export default {
components: { Header, TopSafe,MyBtn }, components: { Header, TopSafe, MyBtn },
data() { data() {
return { return {
type: false, type: false,
userInfo: null, userInfo: null,
headList:[ headList: [
{text:'头像',type:'img',value:''}, { text: '头像', type: 'img', value: '' },
{text:'用户名称',type:'text',value:''}, { text: '用户名称', type: 'text', value: '' },
], ],
bottomList:[ bottomList: [
{text:'账号与安全'}, { text: '账号与安全' },
{text:'我的合同'}, { text: '我的合同' },
{text:'资质照片'}, { text: '资质照片' },
{text:'用户协议'}, { text: '用户协议' },
{text:'隐私协议'}, { text: '隐私协议' },
{text:'售后保障协议'}, { text: '售后保障协议' },
{text:'关于我们'}, { text: '关于我们' },
] ]
}; };
}, },
@@ -77,10 +73,10 @@ export default {
init() { init() {
this.userinfo() this.userinfo()
}, },
onHead(index){ onHead(index) {
console.log('index',index) console.log('index', index)
let that = this; let that = this;
if(index == 0){ if (index == 0) {
uni.chooseImage({ uni.chooseImage({
count: 1, // 默认9,设置图片的数量 count: 1, // 默认9,设置图片的数量
sizeType: ['original', 'compressed'], // 可以指定是原图还是压缩图,默认二者都有 sizeType: ['original', 'compressed'], // 可以指定是原图还是压缩图,默认二者都有
@@ -91,9 +87,9 @@ export default {
that.uploadFile(filePath); that.uploadFile(filePath);
} }
}); });
}else if(index == 1){ } else if (index == 1) {
uni.navigateTo({ uni.navigateTo({
url:'/pages/rwa_package/setName/setName' url: '/pages/rwa_package/setName/setName'
}) })
} }
}, },
@@ -118,7 +114,13 @@ export default {
success: (uploadFileRes) => { success: (uploadFileRes) => {
const data = JSON.parse(uploadFileRes.data); const data = JSON.parse(uploadFileRes.data);
if (data.bizcode === 100) { if (data.bizcode === 100) {
that.setUploadAvatar(data.data.accessUrl); const accessUrl = data.data.accessUrl;
// #ifdef MP-WEIXIN
that.handleWxMediaCheck(accessUrl);
// #endif
// #ifndef MP-WEIXIN
that.setUploadAvatar(accessUrl);
// #endif
} else { } else {
uni.showToast({ uni.showToast({
title: '图片上传失败', title: '图片上传失败',
@@ -142,11 +144,109 @@ export default {
} }
}); });
}, },
setUploadAvatar(img){ // #ifdef MP-WEIXIN
let params = { async handleWxMediaCheck(imgUrl) {
imgUrl:img uni.showLoading({
title: '安全检测中...',
});
try {
const [token, openid] = await Promise.all([
this.getWxAccessToken(),
this.getWxOpenId()
]);
uni.request({
url: `https://api.weixin.qq.com/wxa/media_check_async?access_token=${token}`,
method: 'POST',
data: {
media_url: imgUrl,
media_type: 2,
version: 2,
scene: 1,
openid: openid
},
success: (res) => {
uni.hideLoading();
if (res.data && res.data.errcode === 0) {
this.setUploadAvatar(imgUrl);
} else {
uni.showToast({
title: (res.data && res.data.errmsg) || '图片检测未通过',
icon: 'none',
duration: 3000
});
} }
uploadAvatar(params).then(res=>{ },
fail: (err) => {
uni.hideLoading();
uni.showToast({
title: '安全检测失败',
icon: 'none',
duration: 3000
});
}
});
} catch (err) {
uni.hideLoading();
uni.showToast({
title: '获取微信凭证或OpenID失败',
icon: 'none',
duration: 3000
});
}
},
getWxAccessToken() {
const appid = 'wx376a16a88befe265';
const secret = '0e8fcbf770d72d41b84ea5ebdc427d10';
return new Promise((resolve, reject) => {
uni.request({
url: `https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=${appid}&secret=${secret}`,
method: 'GET',
success: (res) => {
if (res.data && res.data.access_token) {
resolve(res.data.access_token);
} else {
reject(res.data);
}
},
fail: (err) => reject(err)
});
});
},
getWxOpenId() {
const appid = 'wx376a16a88befe265';
const secret = '0e8fcbf770d72d41b84ea5ebdc427d10';
return new Promise((resolve, reject) => {
uni.login({
provider: 'weixin',
success: (loginRes) => {
if (loginRes.code) {
uni.request({
url: `https://api.weixin.qq.com/sns/jscode2session?appid=${appid}&secret=${secret}&js_code=${loginRes.code}&grant_type=authorization_code`,
method: 'GET',
success: (res) => {
if (res.data && res.data.openid) {
resolve(res.data.openid);
} else {
reject(res.data);
}
},
fail: (err) => reject(err)
});
} else {
reject(loginRes);
}
},
fail: (err) => reject(err)
});
});
},
// #endif
setUploadAvatar(img) {
let params = {
imgUrl: img
}
console.log("---", params)
uploadAvatar(params).then(res => {
if (res.bizcode === 100) { if (res.bizcode === 100) {
this.$refs.uToastRef.show({ this.$refs.uToastRef.show({
type: 'success', type: 'success',
@@ -161,15 +261,15 @@ export default {
} }
}) })
}, },
onOutLogin(){ onOutLogin() {
clear(); clear();
uni.navigateTo({ uni.navigateTo({
url: '/pages/login_package/login/login' url: '/pages/login_package/login/login'
}) })
}, },
onBottom(index){ onBottom(index) {
let url = ''; let url = '';
switch(index){ switch (index) {
case 0: case 0:
url = '/pages/rwa_package/accountSafe/accountSafe' url = '/pages/rwa_package/accountSafe/accountSafe'
break; break;
@@ -192,9 +292,9 @@ export default {
url = '/pages/mine_package/mine_about_us/mine_about_us' url = '/pages/mine_package/mine_about_us/mine_about_us'
break; break;
} }
if(url){ if (url) {
uni.navigateTo({ uni.navigateTo({
url:url url: url
}) })
} }
}, },
@@ -223,21 +323,24 @@ export default {
overflow-y: auto; overflow-y: auto;
padding: 0 32rpx; padding: 0 32rpx;
box-sizing: border-box; box-sizing: border-box;
.item-list{
width:100%; .item-list {
width: 100%;
border-radius: 16rpx; border-radius: 16rpx;
display: flex; display: flex;
flex-direction: column; flex-direction: column;
background-color: #fff; background-color: #fff;
.item-box{
min-height:108rpx; .item-box {
min-height: 108rpx;
padding: 0 32rpx; padding: 0 32rpx;
box-sizing: border-box; box-sizing: border-box;
align-items: center; align-items: center;
border-bottom:solid #EAEAEA; border-bottom: solid #EAEAEA;
.ava-img{
width:60rpx; .ava-img {
height:60rpx; width: 60rpx;
height: 60rpx;
border-radius: 30rpx; border-radius: 30rpx;
} }
} }
+11 -1
View File
@@ -2,10 +2,20 @@ export const BASE_URL = "https://api.tbmall.xin"; //生产
export const MILD_BASE_URL = "https://agent.tbmall.xin/"; //中台生产 export const MILD_BASE_URL = "https://agent.tbmall.xin/"; //中台生产
export const kefuBaseUrl = "https://admin.tbmall.xin/api"; export const kefuBaseUrl = "https://admin.tbmall.xin/api";
// export const BASE_URL ='https://api.o.tbmall.xin'; // 本地测试
// export const BASE_URL = baseUrl; // 本地测试
// export const MILD_BASE_URL = "https://agent.o.tbmall.xin/"; //中台测试 // export const MILD_BASE_URL = "https://agent.o.tbmall.xin/"; //中台测试
// export const kefuBaseUrl = "https://admin.o.tbmall.xin/api"; // export const kefuBaseUrl = "https://admin.o.tbmall.xin/api";
// H5 环境且开发模式下使用 '/proxy-api' 代理解决浏览器跨域(注意不能用 '/api',否则会与本地 /api 源码目录冲突)
let baseUrl = 'https://api.o.tbmall.xin';
// #ifdef H5
if (process.env.NODE_ENV === 'development') {
baseUrl = '/proxy-api';
}
// #endif
// https://h.o.tbmall.xin/#/ // https://h.o.tbmall.xin/#/
// 客服接口属于管理后台服务,用户端接口已在后端单独放行。 // 客服接口属于管理后台服务,用户端接口已在后端单独放行。
+16
View File
@@ -0,0 +1,16 @@
import { defineConfig } from 'vite';
import uni from '@dcloudio/vite-plugin-uni';
export default defineConfig({
plugins: [uni()],
server: {
port: 5173,
proxy: {
'/proxy-api': {
target: 'https://api.o.tbmall.xin',
changeOrigin: true,
rewrite: (path) => path.replace(/^\/proxy-api/, '')
}
}
}
});