205 lines
7.5 KiB
TypeScript
205 lines
7.5 KiB
TypeScript
import { CreateTriggerInTxn, Trigger, UpdateTriggerInTxn } from 'oak-domain/lib/types/Trigger';
|
||
import { generateNewIdAsync } from 'oak-domain/lib/utils/uuid';
|
||
import { DATA_SUBSCRIBER_KEYS } from '../config/constants';
|
||
import { EntityDict } from '../oak-app-domain';
|
||
import { BRC } from '../types/RuntimeCxt';
|
||
import assert from 'assert';
|
||
|
||
const triggers: Trigger<EntityDict, 'order', BRC>[] = [
|
||
{
|
||
name: '订单全部支付后对关联的settlement执行preSettle,更新settlement关联的type为preSettle的accountOper',
|
||
entity: 'order',
|
||
action: 'payAll',
|
||
when: 'commit',
|
||
asRoot: true,
|
||
fn: async ({ ids }, context, option) => {
|
||
for (const id of ids) {
|
||
const [order] = await context.select('order', {
|
||
data: {
|
||
id: 1,
|
||
price: 1,
|
||
paid: 1,
|
||
}, filter: {
|
||
id,
|
||
}
|
||
}, {
|
||
forUpdate: true,
|
||
})
|
||
const settlements = await context.select('settlement', {
|
||
data: {
|
||
id: 1,
|
||
price: 1,
|
||
accountId: 1,
|
||
orderId: 1,
|
||
iState: 1,
|
||
},
|
||
filter: {
|
||
orderId: id,
|
||
iState: 'unsettled',
|
||
}
|
||
}, {
|
||
forUpdate: true,
|
||
});
|
||
assert(settlements && settlements.length > 0);
|
||
|
||
let amount = 0;
|
||
for (const settlement of settlements) {
|
||
const { id: settlementId, price, accountId } = settlement;
|
||
amount += price!;
|
||
//创建对应的accountOper
|
||
await context.operate('settlement', {
|
||
id: await generateNewIdAsync(),
|
||
action: 'preSettle',
|
||
data: {
|
||
accountOper$entity: [{
|
||
id: await generateNewIdAsync(),
|
||
action: 'create',
|
||
data: {
|
||
id: await generateNewIdAsync(),
|
||
totalPlus: price,
|
||
availPlus: 0,
|
||
accountId: accountId,
|
||
type: 'preSettle',
|
||
}
|
||
}]
|
||
},
|
||
filter: {
|
||
id: settlementId,
|
||
}
|
||
}, {})
|
||
}
|
||
assert(order.price === amount);
|
||
}
|
||
return;
|
||
}
|
||
},
|
||
{
|
||
name: '订单执行settle前,对关联的settlement执行settle,更新settlement关联的type为settle的accountOper',
|
||
entity: 'order',
|
||
action: 'settle',
|
||
when: 'before',
|
||
asRoot: true,
|
||
priority: 99,
|
||
fn: async ({ operation }, context, option) => {
|
||
const { filter } = operation;
|
||
|
||
let cnt = 0;
|
||
const orders = await context.select('order', {
|
||
data: {
|
||
id: 1,
|
||
settlement$order: {
|
||
$entity: 'settlement',
|
||
data: {
|
||
id: 1,
|
||
price: 1,
|
||
accountId: 1,
|
||
orderId: 1,
|
||
iState: 1,
|
||
},
|
||
filter: {
|
||
iState: 'unsettled',
|
||
}
|
||
}
|
||
},
|
||
filter,
|
||
}, {
|
||
forUpdate: true,
|
||
dontCollect: true,
|
||
});
|
||
|
||
for (const order of orders) {
|
||
const { settlement$order: settlements } = order || {};
|
||
assert(settlements && settlements.length > 0);
|
||
//将关联的settlement执行settle
|
||
for (const settlement of settlements) {
|
||
const { id: settlementId, price, accountId } = settlement;
|
||
|
||
await context.operate('settlement',
|
||
{
|
||
id: await generateNewIdAsync(),
|
||
action: 'settle',
|
||
data: {
|
||
accountOper$entity: [{
|
||
id: await generateNewIdAsync(),
|
||
action: 'create',
|
||
data: {
|
||
id: await generateNewIdAsync(),
|
||
totalPlus: 0,
|
||
availPlus: price,
|
||
accountId: accountId,
|
||
type: 'settle',
|
||
}
|
||
}]
|
||
},
|
||
filter: {
|
||
id: settlementId,
|
||
}
|
||
},
|
||
{}
|
||
);
|
||
cnt += settlements.length;
|
||
}
|
||
}
|
||
return cnt;
|
||
},
|
||
},
|
||
{
|
||
name: '订单状态改变时,向订阅者发送消息',
|
||
entity: 'order',
|
||
action: ['startPaying', 'payAll', 'payPartially', 'payNone', 'timeout', 'cancel', 'startRefunding', 'refundAll', 'refundPartially', 'refundNone'],
|
||
when: 'after',
|
||
fn: async ({ operation }, context, option) => {
|
||
const { filter, id } = operation as EntityDict['order']['Update'];
|
||
|
||
if (filter!.id!) {
|
||
context.saveOperationToEvent(id, `${DATA_SUBSCRIBER_KEYS.orderStateChanged}-${filter!.id!}`);
|
||
return 1;
|
||
}
|
||
|
||
return 0;
|
||
}
|
||
} as UpdateTriggerInTxn<EntityDict, 'order', BRC>,
|
||
/* {
|
||
name: '订单开始提货流程后,创建类型为pickup的ship',
|
||
entity: 'order',
|
||
action: 'startTaking',
|
||
when: 'after',
|
||
asRoot: true,
|
||
fn: async ({ operation }, context) => {
|
||
const { filter } = operation;
|
||
const orders = await context.select('order', {
|
||
data: {
|
||
id: 1,
|
||
receivingMethod: 1,
|
||
},
|
||
filter,
|
||
}, {
|
||
forUpdate: true,
|
||
dontCollect: true,
|
||
});
|
||
for (const order of orders) {
|
||
assert(order.receivingMethod === 'pickup');
|
||
await context.operate('shipOrder', {
|
||
id: await generateNewIdAsync(),
|
||
action: 'create',
|
||
data: {
|
||
id: await generateNewIdAsync(),
|
||
orderId: order.id,
|
||
ship: {
|
||
id: await generateNewIdAsync(),
|
||
action: 'create',
|
||
data: {
|
||
id: await generateNewIdAsync(),
|
||
type: 'pickup'
|
||
}
|
||
}
|
||
},
|
||
}, {});
|
||
}
|
||
|
||
return orders?.length;
|
||
},
|
||
} */
|
||
];
|
||
|
||
export default triggers; |