fix(planting-service): improve outbox event confirmation accuracy

- markAsConfirmed now uses aggregateId + eventType for precise matching
- Prevents accidentally confirming multiple events for the same order
- EventAckController passes eventType to markAsConfirmed

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
hailin 2025-12-09 22:16:23 -08:00
parent 8de7a668f0
commit ba5b6141a3
2 changed files with 21 additions and 11 deletions

View File

@ -53,8 +53,11 @@ export class EventAckController {
try {
if (message.success) {
// 标记事件为已确认
const confirmed = await this.outboxRepository.markAsConfirmed(message.eventId);
// 标记事件为已确认(使用 eventId + eventType 精确匹配)
const confirmed = await this.outboxRepository.markAsConfirmed(
message.eventId,
message.eventType,
);
if (confirmed) {
this.logger.log(
@ -62,7 +65,7 @@ export class EventAckController {
);
} else {
this.logger.warn(
`[ACK] Event ${message.eventId} not found or already confirmed`,
`[ACK] Event ${message.eventId} (${message.eventType}) not found or already confirmed`,
);
}
} else {

View File

@ -145,25 +145,32 @@ export class OutboxRepository {
/**
*
* B方案
* 使 aggregateId + eventType
*/
async markAsConfirmed(eventId: string): Promise<boolean> {
// 通过 aggregateId + eventType 查找事件
async markAsConfirmed(eventId: string, eventType?: string): Promise<boolean> {
const whereClause: Prisma.OutboxEventWhereInput = {
aggregateId: eventId,
status: OutboxStatus.SENT,
};
// 如果提供了 eventType则精确匹配
if (eventType) {
whereClause.eventType = eventType;
}
const result = await this.prisma.outboxEvent.updateMany({
where: {
aggregateId: eventId,
status: OutboxStatus.SENT,
},
where: whereClause,
data: {
status: OutboxStatus.CONFIRMED,
},
});
if (result.count > 0) {
this.logger.log(`[OUTBOX] ✓ Event ${eventId} confirmed by consumer`);
this.logger.log(`[OUTBOX] ✓ Event ${eventId} (${eventType || 'all types'}) confirmed by consumer`);
return true;
}
this.logger.warn(`[OUTBOX] Event ${eventId} not found or not in SENT status`);
this.logger.warn(`[OUTBOX] Event ${eventId} (${eventType || 'any'}) not found or not in SENT status`);
return false;
}