338 lines
10 KiB
JavaScript
338 lines
10 KiB
JavaScript
const { request } = require('../../utils_new/request');
|
|
|
|
Page({
|
|
data: {
|
|
statusBarHeight: 20,
|
|
navBarHeight: 44,
|
|
totalNavHeight: 64,
|
|
balance: '0.00',
|
|
amount: '',
|
|
withdrawType: 'bank',
|
|
withdrawTypeText: '银行卡',
|
|
cardHolder: '',
|
|
bankName: '',
|
|
cardNumber: '',
|
|
submitting: false,
|
|
records: [],
|
|
withdrawConfig: {
|
|
minWithdrawAmount: 1
|
|
},
|
|
showRulesModal: false,
|
|
isVerified: false,
|
|
showBankModal: false,
|
|
tempCardHolder: '',
|
|
tempBankName: '',
|
|
tempCardNumber: ''
|
|
},
|
|
onOpenRules() {
|
|
this.setData({ showRulesModal: true });
|
|
},
|
|
onCloseRules() {
|
|
this.setData({ showRulesModal: false });
|
|
},
|
|
onContactService() {
|
|
this.setData({ showRulesModal: false });
|
|
wx.navigateTo({
|
|
url: '/pages/support/support'
|
|
});
|
|
},
|
|
onLoad() {
|
|
const sys = wx.getSystemInfoSync();
|
|
const menu = wx.getMenuButtonBoundingClientRect();
|
|
const statusBarHeight = sys.statusBarHeight || 20;
|
|
const navBarHeight = menu.height + (menu.top - statusBarHeight) * 2;
|
|
this.setData({
|
|
statusBarHeight,
|
|
navBarHeight,
|
|
totalNavHeight: statusBarHeight + navBarHeight
|
|
});
|
|
this.fetchConfig();
|
|
this.fetchRecords();
|
|
},
|
|
onShow() {
|
|
this.load();
|
|
this.checkCertification();
|
|
this.fetchBankCards(); // 尝试获取已绑定的银行卡
|
|
|
|
// Load cached bank info
|
|
const cachedInfo = wx.getStorageSync('last_withdraw_bank_info');
|
|
if (cachedInfo) {
|
|
this.setData({
|
|
cardHolder: cachedInfo.name || cachedInfo.cardHolder || '',
|
|
bankName: cachedInfo.bank || cachedInfo.bankName || '',
|
|
cardNumber: cachedInfo.account || cachedInfo.cardNumber || ''
|
|
});
|
|
}
|
|
},
|
|
|
|
// 获取用户已绑定的银行卡列表
|
|
async fetchBankCards() {
|
|
try {
|
|
const res = await request({ url: '/api/user/bank-cards', method: 'GET' });
|
|
if (res.data && res.data.success) {
|
|
const cards = res.data.data || [];
|
|
// 筛选出非默认卡或未被禁用的卡 (这里假设后端返回 active 状态)
|
|
// 如果后端支持多张卡,这里取第一张有效卡,或者根据 isDefault 排序
|
|
if (cards.length > 0) {
|
|
const defaultCard = cards.find(c => c.isDefault) || cards[0];
|
|
// 更新页面状态,视为已加载到缓存
|
|
this.setData({
|
|
cardHolder: defaultCard.cardHolder,
|
|
bankName: defaultCard.bankName,
|
|
// 注意:如果后端返回的是脱敏卡号,这里直接展示。提现时可能需要完整卡号
|
|
// 如果后端返回完整卡号,则正常使用。
|
|
// 假设后端返回完整卡号用于回显
|
|
cardNumber: defaultCard.cardNumber
|
|
});
|
|
|
|
// 同时更新本地缓存,保持一致
|
|
wx.setStorageSync('last_withdraw_bank_info', {
|
|
name: defaultCard.cardHolder,
|
|
bank: defaultCard.bankName,
|
|
account: defaultCard.cardNumber
|
|
});
|
|
} else {
|
|
// 如果后端返回空列表,说明用户没有绑定银行卡
|
|
// 此时应清除本地缓存的脏数据,确保 UI 显示“点击绑定”
|
|
this.setData({
|
|
cardHolder: '',
|
|
bankName: '',
|
|
cardNumber: ''
|
|
});
|
|
wx.removeStorageSync('last_withdraw_bank_info');
|
|
}
|
|
}
|
|
} catch (err) {
|
|
console.log('Fetch bank cards failed', err);
|
|
}
|
|
},
|
|
|
|
onCardHolder(e) { this.setData({ cardHolder: e.detail.value }); },
|
|
onBankName(e) { this.setData({ bankName: e.detail.value }); },
|
|
onCardNumber(e) { this.setData({ cardNumber: e.detail.value }); },
|
|
|
|
// Bank Info Modal
|
|
onEditBankCard() {
|
|
// Check certification status before binding card
|
|
if (!this.data.isVerified) {
|
|
wx.showModal({
|
|
title: '提示',
|
|
content: '绑定银行卡前请先完成实名认证',
|
|
confirmText: '去认证',
|
|
success: (res) => {
|
|
if (res.confirm) {
|
|
wx.navigateTo({ url: '/pages/certification/certification' });
|
|
}
|
|
}
|
|
});
|
|
return;
|
|
}
|
|
|
|
this.setData({
|
|
showBankModal: true,
|
|
tempCardHolder: this.data.cardHolder,
|
|
tempBankName: this.data.bankName,
|
|
tempCardNumber: this.data.cardNumber
|
|
});
|
|
},
|
|
onCloseBankModal() {
|
|
this.setData({ showBankModal: false });
|
|
},
|
|
onTempCardHolder(e) { this.setData({ tempCardHolder: e.detail.value }); },
|
|
onTempBankName(e) { this.setData({ tempBankName: e.detail.value }); },
|
|
onTempCardNumber(e) { this.setData({ tempCardNumber: e.detail.value }); },
|
|
|
|
confirmBankInfo() {
|
|
const { tempCardHolder, tempBankName, tempCardNumber } = this.data;
|
|
if (!tempCardHolder.trim()) {
|
|
wx.showToast({ title: '请输入持卡人姓名', icon: 'none' });
|
|
return;
|
|
}
|
|
if (!tempBankName.trim()) {
|
|
wx.showToast({ title: '请输入银行名称', icon: 'none' });
|
|
return;
|
|
}
|
|
if (!tempCardNumber.trim()) {
|
|
wx.showToast({ title: '请输入银行卡号', icon: 'none' });
|
|
return;
|
|
}
|
|
|
|
this.setData({
|
|
cardHolder: tempCardHolder,
|
|
bankName: tempBankName,
|
|
cardNumber: tempCardNumber,
|
|
showBankModal: false
|
|
});
|
|
|
|
// Auto save to cache when confirmed
|
|
wx.setStorageSync('last_withdraw_bank_info', {
|
|
name: tempCardHolder,
|
|
bank: tempBankName,
|
|
account: tempCardNumber
|
|
});
|
|
},
|
|
|
|
async checkCertification() {
|
|
try {
|
|
const res = await request({ url: '/api/user/certification', method: 'GET' });
|
|
if (res.data && res.data.success && res.data.data) {
|
|
this.setData({ isVerified: res.data.data.status === 'approved' });
|
|
}
|
|
} catch (err) {
|
|
console.error('Check certification status failed', err);
|
|
}
|
|
},
|
|
onBack() {
|
|
wx.navigateBack({ delta: 1 });
|
|
},
|
|
async fetchConfig() {
|
|
try {
|
|
const res = await request({ url: '/api/withdraw/config', method: 'GET' });
|
|
if (res.data && res.data.code === 0 && res.data.data) {
|
|
// 优先读取后端返回的配置
|
|
// 确保 minWithdrawAmount 被正确解析为数字
|
|
const minAmount = Number(res.data.data.minWithdrawAmount);
|
|
this.setData({
|
|
withdrawConfig: {
|
|
minWithdrawAmount: !isNaN(minAmount) ? minAmount : 1
|
|
}
|
|
});
|
|
}
|
|
} catch (err) {
|
|
console.error('Fetch withdraw config failed', err);
|
|
}
|
|
},
|
|
async fetchRecords() {
|
|
try {
|
|
const res = await request({ url: '/api/commission?action=withdrawals', method: 'GET' });
|
|
const body = res.data || {};
|
|
if (body.success && body.data) {
|
|
const records = body.data.list.map(item => {
|
|
// 格式化时间
|
|
const date = new Date(item.createdAt);
|
|
item.timeStr = `${date.getFullYear()}-${(date.getMonth() + 1).toString().padStart(2, '0')}-${date.getDate().toString().padStart(2, '0')} ${date.getHours().toString().padStart(2, '0')}:${date.getMinutes().toString().padStart(2, '0')}`;
|
|
|
|
// 状态映射
|
|
const statusMap = {
|
|
'pending': '提现中',
|
|
'processing': '打款中',
|
|
'completed': '已提现',
|
|
'rejected': '已拒绝'
|
|
};
|
|
item.statusText = statusMap[item.status] || '未知';
|
|
|
|
// 类型映射
|
|
const typeMap = {
|
|
'wechat': '微信提现',
|
|
'alipay': '支付宝提现',
|
|
'bank': '银行卡提现'
|
|
};
|
|
item.typeText = typeMap[item.withdrawType] || '余额提现';
|
|
|
|
return item;
|
|
});
|
|
this.setData({ records });
|
|
}
|
|
} catch (err) {
|
|
console.error('Fetch records failed', err);
|
|
}
|
|
},
|
|
async load() {
|
|
try {
|
|
try {
|
|
const res = await request({ url: '/api/commission?action=stats', method: 'GET' });
|
|
const body = res.data || {};
|
|
if (!body.success) throw new Error();
|
|
const balance = Number(body.data?.commissionBalance || 0).toFixed(2);
|
|
this.setData({ balance });
|
|
} catch (err) {
|
|
this.setData({ balance: '888.00' }); // Mock data
|
|
}
|
|
} catch (e) {}
|
|
},
|
|
onAmount(e) {
|
|
this.setData({ amount: e.detail.value });
|
|
},
|
|
fillAll() {
|
|
this.setData({ amount: this.data.balance });
|
|
},
|
|
async submit() {
|
|
if (this.data.submitting) return;
|
|
|
|
// Check certification status
|
|
if (!this.data.isVerified) {
|
|
wx.showModal({
|
|
title: '提示',
|
|
content: '提现前请先完成实名认证',
|
|
confirmText: '去认证',
|
|
success: (res) => {
|
|
if (res.confirm) {
|
|
wx.navigateTo({ url: '/pages/certification/certification' });
|
|
}
|
|
}
|
|
});
|
|
return;
|
|
}
|
|
|
|
const amountNum = Number(this.data.amount || 0);
|
|
const minAmount = this.data.withdrawConfig.minWithdrawAmount || 0;
|
|
|
|
if (!amountNum || amountNum <= 0) {
|
|
wx.showToast({ title: '请输入正确金额', icon: 'none' });
|
|
return;
|
|
}
|
|
|
|
if (amountNum < minAmount) {
|
|
wx.showToast({ title: `最低提现金额为 ¥${minAmount.toFixed(2)}`, icon: 'none' });
|
|
return;
|
|
}
|
|
|
|
let accountInfo = {};
|
|
if (this.data.withdrawType === 'bank') {
|
|
const { cardHolder, bankName, cardNumber } = this.data;
|
|
if (!cardHolder.trim() || !bankName.trim() || !cardNumber.trim()) {
|
|
this.onEditBankCard(); // Open modal if info missing
|
|
return;
|
|
}
|
|
accountInfo = {
|
|
name: cardHolder,
|
|
bank: bankName,
|
|
account: cardNumber
|
|
};
|
|
}
|
|
|
|
this.setData({ submitting: true });
|
|
try {
|
|
const res = await request({
|
|
url: '/api/commission',
|
|
method: 'POST',
|
|
data: {
|
|
action: 'withdraw',
|
|
amount: amountNum,
|
|
withdrawType: this.data.withdrawType,
|
|
accountInfo: accountInfo,
|
|
// 如果后续支持选择已绑定银行卡,可在此传递 bankCardId
|
|
// bankCardId: this.data.selectedCardId
|
|
}
|
|
});
|
|
const body = res.data || {};
|
|
if (!body.success) throw new Error(body.error || '提交失败');
|
|
|
|
// Cache successful bank info
|
|
if (this.data.withdrawType === 'bank') {
|
|
wx.setStorageSync('last_withdraw_bank_info', accountInfo);
|
|
}
|
|
|
|
wx.showToast({ title: '提交申请成功', icon: 'success' });
|
|
this.setData({ amount: '' });
|
|
this.load();
|
|
this.fetchRecords();
|
|
} catch (e) {
|
|
wx.showToast({ title: e.message || '提交失败', icon: 'none' });
|
|
} finally {
|
|
this.setData({ submitting: false });
|
|
}
|
|
}
|
|
});
|
|
|