I have a workflow that has an email form. The requirements are the following: A user completes the form that contains email fields and submits it. If everything goes well then an email model object is created and stored in the database, and then the data are sent to a rabbit queue. When the queue gets processed an email is generated (this is a different with html body and everything) and gets send to the SMTP server to send it and then another database model is created which I call note and gets stored in the database as well (this will appear as an action item in the history). If it fails at some point I rollback and put the message back to the queue for a retry.


The system is a preexisting one and I am required to add an email integration so if some stuff feel unnecessary or round about it's what me and the client have decided so I can't anything more about it and honestly in the larger context of the business they make sense.

Actual Question

As you can see there are a lot of stuff happening and I am bit unsure about where everything should happen and what concerns are grouped together. My initial thoughts are that there are two transactions. First the initial email db model. I feel like I should process the form and save it to the database and then send it to its merry way to the queue to be processed successfully hopefully at a later point. Then when the queue gets processed another transaction is happening - email html gets generated, sent to SMTP and if SMTP returns success then a note gets created and stored in the db and the transaction gets committed. Otherwise rollback, put it back in the queue, retry and after 3 retries put it in a dead letter queue.

I think that makes sense but I wanted to get another POV.

  • @DocBrown I guess I was just looking for confirmation. To be fair I was feeling confused but as I was writing this it started making sense and debated not posting it but since I took the time I thought why the heck not... May 18, 2019 at 9:23

1 Answer 1


What you wrote sounds reasonable to me.

In asynchronous scenarios like this one, it is a good idea (actually, it is probably the only thing which makes sense) to split database transactions to the different, asynchronous tasks. That means in case of a failure communicated by an asynchronous event, it will become necessary to implement a compensating transaction, as a DB transaction of its own. But I guess that is exactly what you have in mind when you wrote "rollback" above.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.