237 lines
8.4 KiB
JavaScript
237 lines
8.4 KiB
JavaScript
import { ToCent, ToYuan, ThousandCont } from "oak-domain/lib/utils/money";
|
|
import assert from "assert";
|
|
import { RefundExceedMax } from "../../../types/Exception";
|
|
import { generateNewIdAsync } from "oak-domain/lib/utils/uuid";
|
|
export default OakComponent({
|
|
properties: {
|
|
accountId: '',
|
|
withdrawAccountFilter: {},
|
|
onNewWithdrawAccount: () => undefined,
|
|
onCreateWithdraw: (id) => undefined,
|
|
},
|
|
formData({ features }) {
|
|
const { accountId, withdrawAccountFilter } = this.props;
|
|
const [account] = features.cache.get('account', {
|
|
data: {
|
|
id: 1,
|
|
avail: 1,
|
|
refundable: 1,
|
|
},
|
|
filter: {
|
|
id: accountId,
|
|
}
|
|
});
|
|
const withdrawAccounts = features.cache.get('withdrawAccount', {
|
|
data: {
|
|
id: 1,
|
|
org: 1,
|
|
name: 1,
|
|
code: 1,
|
|
channel: {
|
|
id: 1,
|
|
name: 1,
|
|
lossRatio: 1,
|
|
}
|
|
},
|
|
filter: withdrawAccountFilter
|
|
});
|
|
const { avail, refundable } = account;
|
|
const refundAmount = Math.min(avail, refundable);
|
|
const manualAmount = avail - refundAmount;
|
|
const { value, withdrawData } = this.state;
|
|
const refundData = withdrawData && withdrawData.refund$entity?.map(ele => ele.data).map((refund) => {
|
|
const { meta, price, loss } = refund;
|
|
const { lossExplanation, lossExplanationParams, channel } = meta;
|
|
return {
|
|
lossExp: lossExplanation ? this.t(lossExplanation, lossExplanationParams) : this.t(''),
|
|
channel: this.t(`payChannel::${channel}`),
|
|
priceYuan: ThousandCont(ToYuan(price), 2),
|
|
lossYuan: ThousandCont(ToYuan(loss), 2),
|
|
finalYuan: ThousandCont(ToYuan(price - loss), 2),
|
|
};
|
|
});
|
|
const withdrawExactPrice = ThousandCont(ToYuan(withdrawData ? withdrawData.price - withdrawData.loss : 0), 2);
|
|
return {
|
|
executale: value > 0,
|
|
account,
|
|
withdrawAccounts,
|
|
refundAmount,
|
|
refundAmountYuan: ToYuan(refundAmount),
|
|
manualAmount,
|
|
manualAmountYuan: ToYuan(manualAmount),
|
|
avail,
|
|
availYuan: ToYuan(avail),
|
|
withdrawMethod: refundData && refundData.length ? 'refund' : undefined,
|
|
refundData,
|
|
withdrawExactPrice,
|
|
};
|
|
},
|
|
features: ['cache'],
|
|
lifetimes: {
|
|
ready() {
|
|
const { withdrawAccountFilter } = this.props;
|
|
this.features.cache.refresh('withdrawAccount', {
|
|
data: {
|
|
id: 1,
|
|
org: 1,
|
|
name: 1,
|
|
code: 1,
|
|
channel: {
|
|
id: 1,
|
|
name: 1,
|
|
lossRatio: 1,
|
|
}
|
|
},
|
|
filter: withdrawAccountFilter
|
|
});
|
|
}
|
|
},
|
|
data: {
|
|
value: 0,
|
|
valueYuan: 0,
|
|
showMethodHelp: false,
|
|
showLossHelp: false,
|
|
withdrawData: null,
|
|
t(k, p) {
|
|
return this.t(k, p);
|
|
}
|
|
},
|
|
methods: {
|
|
setValue(valueYuan) {
|
|
let valueYuan2 = typeof valueYuan === 'string' ? parseInt(valueYuan) : valueYuan;
|
|
const value = valueYuan2 ? ToCent(valueYuan2) : null;
|
|
this.setState({ value, valueYuan: valueYuan2 }, () => this.reRender());
|
|
},
|
|
switchHelp(type) {
|
|
switch (type) {
|
|
case 'method': {
|
|
this.setState({
|
|
showMethodHelp: !this.state.showMethodHelp,
|
|
showLossHelp: false,
|
|
});
|
|
break;
|
|
}
|
|
case 'loss': {
|
|
this.setState({
|
|
showMethodHelp: false,
|
|
showLossHelp: !this.state.showLossHelp,
|
|
});
|
|
break;
|
|
}
|
|
}
|
|
},
|
|
async createWithdrawData() {
|
|
const { value, refundAmount, avail, manualAmount } = this.state;
|
|
if (value > avail) {
|
|
this.setMessage({
|
|
type: 'error',
|
|
content: this.t('error.overflow'),
|
|
});
|
|
}
|
|
else if (refundAmount) {
|
|
if (value > refundAmount) {
|
|
this.setMessage({
|
|
type: 'error',
|
|
content: this.t('error.overflowRefundAmount'),
|
|
});
|
|
}
|
|
else {
|
|
try {
|
|
const { result: refundData } = (await this.features.cache.exec('getAccountPayRefunds', {
|
|
accountId: this.props.accountId,
|
|
price: value,
|
|
}));
|
|
let loss = 0;
|
|
(refundData).forEach((ele) => {
|
|
loss += ele.loss || 0;
|
|
});
|
|
this.setState({
|
|
withdrawData: {
|
|
id: await generateNewIdAsync(),
|
|
accountId: this.props.accountId,
|
|
price: value,
|
|
loss,
|
|
refund$entity: await Promise.all(refundData.map(async (data) => ({
|
|
id: await generateNewIdAsync(),
|
|
action: 'create',
|
|
data,
|
|
}))),
|
|
creatorId: this.features.token.getUserId(),
|
|
},
|
|
}, () => this.reRender());
|
|
}
|
|
catch (err) {
|
|
if (err instanceof RefundExceedMax) {
|
|
this.features.cache.refresh('account', {
|
|
data: {
|
|
id: 1,
|
|
avail: 1,
|
|
refundable: 1,
|
|
},
|
|
filter: {
|
|
id: this.props.accountId,
|
|
}
|
|
});
|
|
}
|
|
throw err;
|
|
}
|
|
}
|
|
}
|
|
else {
|
|
assert(manualAmount);
|
|
if (value > manualAmount) {
|
|
this.setMessage({
|
|
type: 'error',
|
|
content: this.t('error.overflowManualAmount'),
|
|
});
|
|
}
|
|
else {
|
|
console.warn('还没实现');
|
|
}
|
|
}
|
|
},
|
|
clearWithdrawData() {
|
|
this.setState({
|
|
withdrawData: null,
|
|
}, () => this.reRender());
|
|
},
|
|
async createWithdraw() {
|
|
const { withdrawData } = this.state;
|
|
assert(withdrawData);
|
|
const id = withdrawData.id;
|
|
await this.features.cache.exec('operate', {
|
|
entity: 'withdraw',
|
|
operation: {
|
|
id: await generateNewIdAsync(),
|
|
data: withdrawData,
|
|
action: 'create',
|
|
}
|
|
});
|
|
const { onCreateWithdraw } = this.props;
|
|
onCreateWithdraw && onCreateWithdraw(id);
|
|
},
|
|
InputValueMp(input) {
|
|
const { detail, } = input;
|
|
const { value } = detail;
|
|
const { availYuan } = this.state;
|
|
if (parseInt(value) > availYuan) {
|
|
this.setValue(availYuan);
|
|
}
|
|
else if (parseInt(value) > 0) {
|
|
this.setValue(value);
|
|
}
|
|
else {
|
|
this.setValue(0);
|
|
}
|
|
},
|
|
setValueMp(e) {
|
|
const value = e.currentTarget.dataset.value;
|
|
this.setValue(value);
|
|
},
|
|
switchHelpMp(e) {
|
|
const value = e.currentTarget.dataset.value;
|
|
this.switchHelp(value);
|
|
},
|
|
}
|
|
});
|