diff --git a/.changeset/good-crews-pull.md b/.changeset/good-crews-pull.md new file mode 100644 index 0000000000..da496a6ec4 --- /dev/null +++ b/.changeset/good-crews-pull.md @@ -0,0 +1,5 @@ +--- +"@medusajs/medusa": patch +--- + +Fix(medusa): All payment sessions should be removed if cart total reach 0 diff --git a/.changeset/pink-emus-drum.md b/.changeset/pink-emus-drum.md new file mode 100644 index 0000000000..afa8032684 --- /dev/null +++ b/.changeset/pink-emus-drum.md @@ -0,0 +1,5 @@ +--- +"@medusajs/medusa": patch +--- + +feat(medusa): Use Bull `jobId` option to identify duplicates diff --git a/packages/medusa/src/services/__tests__/cart.js b/packages/medusa/src/services/__tests__/cart.js index 74c7ed0c46..c2d83132f2 100644 --- a/packages/medusa/src/services/__tests__/cart.js +++ b/packages/medusa/src/services/__tests__/cart.js @@ -1706,8 +1706,8 @@ describe("CartService", () => { expect(paymentSessionRepositoryMock.create).toHaveBeenCalledTimes(1) expect(paymentSessionRepositoryMock.save).toHaveBeenCalledTimes(2) // create and update - expect(paymentSessionRepositoryMock.delete).toHaveBeenCalledTimes(1) - expect(paymentSessionRepositoryMock.delete).toHaveBeenCalledWith({ + expect(paymentSessionRepositoryMock.remove).toHaveBeenCalledTimes(1) + expect(paymentSessionRepositoryMock.remove).toHaveBeenCalledWith({ provider_id: "not_in_region", }) }) @@ -1715,12 +1715,12 @@ describe("CartService", () => { it("removes if cart total === 0", async () => { await cartService.setPaymentSessions(IdMap.getId("cart-remove")) - expect(paymentSessionRepositoryMock.delete).toHaveBeenCalledTimes(2) + expect(paymentSessionRepositoryMock.remove).toHaveBeenCalledTimes(2) - expect(paymentSessionRepositoryMock.delete).toHaveBeenCalledWith({ + expect(paymentSessionRepositoryMock.remove).toHaveBeenCalledWith({ provider_id: provider1Id, }) - expect(paymentSessionRepositoryMock.delete).toHaveBeenCalledWith({ + expect(paymentSessionRepositoryMock.remove).toHaveBeenCalledWith({ provider_id: provider2Id, }) }) @@ -1728,12 +1728,12 @@ describe("CartService", () => { it("removes if cart total < 0", async () => { await cartService.setPaymentSessions(IdMap.getId("cart-negative")) - expect(paymentSessionRepositoryMock.delete).toHaveBeenCalledTimes(2) + expect(paymentSessionRepositoryMock.remove).toHaveBeenCalledTimes(2) - expect(paymentSessionRepositoryMock.delete).toHaveBeenCalledWith({ + expect(paymentSessionRepositoryMock.remove).toHaveBeenCalledWith({ provider_id: provider1Id, }) - expect(paymentSessionRepositoryMock.delete).toHaveBeenCalledWith({ + expect(paymentSessionRepositoryMock.remove).toHaveBeenCalledWith({ provider_id: provider2Id, }) }) diff --git a/packages/medusa/src/services/cart.ts b/packages/medusa/src/services/cart.ts index 01d9bfca2b..b14259c5c6 100644 --- a/packages/medusa/src/services/cart.ts +++ b/packages/medusa/src/services/cart.ts @@ -1846,7 +1846,7 @@ class CartService extends TransactionBaseService { return paymentProviderServiceTx.deleteSession(session) } - return psRepo.delete(session) + return psRepo.remove(session) } // In the case of a cart that has a total <= 0 we can return prematurely. diff --git a/packages/medusa/src/services/event-bus.ts b/packages/medusa/src/services/event-bus.ts index 457d150a54..fc548c45af 100644 --- a/packages/medusa/src/services/event-bus.ts +++ b/packages/medusa/src/services/event-bus.ts @@ -1,4 +1,4 @@ -import Bull from "bull" +import Bull, { JobOptions } from "bull" import Redis from "ioredis" import { isDefined } from "medusa-core-utils" import { EntityManager } from "typeorm" @@ -40,14 +40,16 @@ type SubscriberDescriptor = { subscriber: Subscriber } -type EmitOptions = { +export type EmitOptions = { delay?: number attempts: number backoff?: { type: "fixed" | "exponential" delay: number } -} +} & JobOptions + +const COMPLETED_JOB_TTL = 10000 /** * Can keep track of multiple subscribers to different events and run the @@ -225,10 +227,13 @@ export default class EventBusService { data: T, options: Record & EmitOptions = { attempts: 1 } ): Promise { - const opts: { removeOnComplete: boolean } & EmitOptions = { - removeOnComplete: true, - attempts: 1, + const opts: EmitOptions = { + removeOnComplete: { + age: COMPLETED_JOB_TTL, + }, + ...options, } + if (typeof options.attempts === "number") { opts.attempts = options.attempts if (isDefined(options.backoff)) { @@ -295,7 +300,7 @@ export default class EventBusService { this.queue_ .add( { eventName: job.event_name, data: job.data }, - job.options ?? { removeOnComplete: true } + { jobId: job.id, ...job.options } ) .then(async () => { await stagedJobRepo.remove(job)