In modern web applications, transactions and background jobs play an important role to ensure consistency and performance. But sometimes if not used wisely and carefully can end up creating bugs that are difficult to identify in a big application.
While identifying such an issue in an application where we were sending a webhook to an external third party app to cancel an order and update item quantities. But somehow the wrong status was being sent for order along with the wrong quantities.
We identified the discrepancy between the expected and actual data and after crossing off other reasons from our list we realized it was due to the fact that the background jobs were invoked in the transaction.
... # some code
cancel_order_and_send_webhook # invokes background job
... # some more code
Now when the method was executed it enqueued a couple of background jobs to send webhooks. So, by the time the jobs ran the transaction wasn’t committed to the database and it used old values for the order and item quantities and hence sending the wrong values in the payload.
Moving background jobs out of the transaction did the thing and correct values were picked up.