DomainEventPublisher consistency











up vote
0
down vote

favorite
1












Having just read Vaughn Vernon's effective aggregate design, I'm wondering about failures related to event publishing.



In the given example at page 9 (page 3 of the PDF), we call DomainEventPublisher.publish(). The event being published allows other aggregates to execute their behaviours.



What I'm wondering is: What happens if DomainEventPublisher.publish() fails ? What happens if DomainEventPublisher.publish() succeeds, but the transaction fails ?



How implementations handle these two cases ?










share|improve this question


















  • 1




    that example is not very resilient/usable in the real world. The most reliable patterns are those from the Event sourcing, when the events are not published at all but are pulled from the Event store and the event consumer (the readmodel or saga) keeps track if the processed events.
    – Constantin Galbenu
    yesterday






  • 1




    it uses transactions; it makes the Aggregate dependent of the infrastructure (which can be mitigated by returning the events instead)
    – Constantin Galbenu
    yesterday






  • 1




    @ConstantinGalbenu Whether you return them or use a static thread-bound synchronous DomainEventPublisher you pretty much get the same exact result with the same testability. The pattern does use database transactions, but the domain is not aware of these in any way. I don't really see your point.
    – plalx
    yesterday






  • 1




    @plalx the Aggregate makes an IO call and I don't like that. I keep my Aggregates pure, with no side effects, with no dependency to Infrastructure or any other Components in fact.
    – Constantin Galbenu
    yesterday






  • 1




    @ConstantinGalbenu Well, they don't make an IO call if there's no registered handler that does IO, which means everything can be unit tested without any IO going on. The ARs themselves have no dependencies on infrastructure components or any other packages.
    – plalx
    yesterday















up vote
0
down vote

favorite
1












Having just read Vaughn Vernon's effective aggregate design, I'm wondering about failures related to event publishing.



In the given example at page 9 (page 3 of the PDF), we call DomainEventPublisher.publish(). The event being published allows other aggregates to execute their behaviours.



What I'm wondering is: What happens if DomainEventPublisher.publish() fails ? What happens if DomainEventPublisher.publish() succeeds, but the transaction fails ?



How implementations handle these two cases ?










share|improve this question


















  • 1




    that example is not very resilient/usable in the real world. The most reliable patterns are those from the Event sourcing, when the events are not published at all but are pulled from the Event store and the event consumer (the readmodel or saga) keeps track if the processed events.
    – Constantin Galbenu
    yesterday






  • 1




    it uses transactions; it makes the Aggregate dependent of the infrastructure (which can be mitigated by returning the events instead)
    – Constantin Galbenu
    yesterday






  • 1




    @ConstantinGalbenu Whether you return them or use a static thread-bound synchronous DomainEventPublisher you pretty much get the same exact result with the same testability. The pattern does use database transactions, but the domain is not aware of these in any way. I don't really see your point.
    – plalx
    yesterday






  • 1




    @plalx the Aggregate makes an IO call and I don't like that. I keep my Aggregates pure, with no side effects, with no dependency to Infrastructure or any other Components in fact.
    – Constantin Galbenu
    yesterday






  • 1




    @ConstantinGalbenu Well, they don't make an IO call if there's no registered handler that does IO, which means everything can be unit tested without any IO going on. The ARs themselves have no dependencies on infrastructure components or any other packages.
    – plalx
    yesterday













up vote
0
down vote

favorite
1









up vote
0
down vote

favorite
1






1





Having just read Vaughn Vernon's effective aggregate design, I'm wondering about failures related to event publishing.



In the given example at page 9 (page 3 of the PDF), we call DomainEventPublisher.publish(). The event being published allows other aggregates to execute their behaviours.



What I'm wondering is: What happens if DomainEventPublisher.publish() fails ? What happens if DomainEventPublisher.publish() succeeds, but the transaction fails ?



How implementations handle these two cases ?










share|improve this question













Having just read Vaughn Vernon's effective aggregate design, I'm wondering about failures related to event publishing.



In the given example at page 9 (page 3 of the PDF), we call DomainEventPublisher.publish(). The event being published allows other aggregates to execute their behaviours.



What I'm wondering is: What happens if DomainEventPublisher.publish() fails ? What happens if DomainEventPublisher.publish() succeeds, but the transaction fails ?



How implementations handle these two cases ?







domain-driven-design aggregateroot






share|improve this question













share|improve this question











share|improve this question




share|improve this question










asked yesterday









arnaud576875

68.9k16169171




68.9k16169171








  • 1




    that example is not very resilient/usable in the real world. The most reliable patterns are those from the Event sourcing, when the events are not published at all but are pulled from the Event store and the event consumer (the readmodel or saga) keeps track if the processed events.
    – Constantin Galbenu
    yesterday






  • 1




    it uses transactions; it makes the Aggregate dependent of the infrastructure (which can be mitigated by returning the events instead)
    – Constantin Galbenu
    yesterday






  • 1




    @ConstantinGalbenu Whether you return them or use a static thread-bound synchronous DomainEventPublisher you pretty much get the same exact result with the same testability. The pattern does use database transactions, but the domain is not aware of these in any way. I don't really see your point.
    – plalx
    yesterday






  • 1




    @plalx the Aggregate makes an IO call and I don't like that. I keep my Aggregates pure, with no side effects, with no dependency to Infrastructure or any other Components in fact.
    – Constantin Galbenu
    yesterday






  • 1




    @ConstantinGalbenu Well, they don't make an IO call if there's no registered handler that does IO, which means everything can be unit tested without any IO going on. The ARs themselves have no dependencies on infrastructure components or any other packages.
    – plalx
    yesterday














  • 1




    that example is not very resilient/usable in the real world. The most reliable patterns are those from the Event sourcing, when the events are not published at all but are pulled from the Event store and the event consumer (the readmodel or saga) keeps track if the processed events.
    – Constantin Galbenu
    yesterday






  • 1




    it uses transactions; it makes the Aggregate dependent of the infrastructure (which can be mitigated by returning the events instead)
    – Constantin Galbenu
    yesterday






  • 1




    @ConstantinGalbenu Whether you return them or use a static thread-bound synchronous DomainEventPublisher you pretty much get the same exact result with the same testability. The pattern does use database transactions, but the domain is not aware of these in any way. I don't really see your point.
    – plalx
    yesterday






  • 1




    @plalx the Aggregate makes an IO call and I don't like that. I keep my Aggregates pure, with no side effects, with no dependency to Infrastructure or any other Components in fact.
    – Constantin Galbenu
    yesterday






  • 1




    @ConstantinGalbenu Well, they don't make an IO call if there's no registered handler that does IO, which means everything can be unit tested without any IO going on. The ARs themselves have no dependencies on infrastructure components or any other packages.
    – plalx
    yesterday








1




1




that example is not very resilient/usable in the real world. The most reliable patterns are those from the Event sourcing, when the events are not published at all but are pulled from the Event store and the event consumer (the readmodel or saga) keeps track if the processed events.
– Constantin Galbenu
yesterday




that example is not very resilient/usable in the real world. The most reliable patterns are those from the Event sourcing, when the events are not published at all but are pulled from the Event store and the event consumer (the readmodel or saga) keeps track if the processed events.
– Constantin Galbenu
yesterday




1




1




it uses transactions; it makes the Aggregate dependent of the infrastructure (which can be mitigated by returning the events instead)
– Constantin Galbenu
yesterday




it uses transactions; it makes the Aggregate dependent of the infrastructure (which can be mitigated by returning the events instead)
– Constantin Galbenu
yesterday




1




1




@ConstantinGalbenu Whether you return them or use a static thread-bound synchronous DomainEventPublisher you pretty much get the same exact result with the same testability. The pattern does use database transactions, but the domain is not aware of these in any way. I don't really see your point.
– plalx
yesterday




@ConstantinGalbenu Whether you return them or use a static thread-bound synchronous DomainEventPublisher you pretty much get the same exact result with the same testability. The pattern does use database transactions, but the domain is not aware of these in any way. I don't really see your point.
– plalx
yesterday




1




1




@plalx the Aggregate makes an IO call and I don't like that. I keep my Aggregates pure, with no side effects, with no dependency to Infrastructure or any other Components in fact.
– Constantin Galbenu
yesterday




@plalx the Aggregate makes an IO call and I don't like that. I keep my Aggregates pure, with no side effects, with no dependency to Infrastructure or any other Components in fact.
– Constantin Galbenu
yesterday




1




1




@ConstantinGalbenu Well, they don't make an IO call if there's no registered handler that does IO, which means everything can be unit tested without any IO going on. The ARs themselves have no dependencies on infrastructure components or any other packages.
– plalx
yesterday




@ConstantinGalbenu Well, they don't make an IO call if there's no registered handler that does IO, which means everything can be unit tested without any IO going on. The ARs themselves have no dependencies on infrastructure components or any other packages.
– plalx
yesterday












2 Answers
2






active

oldest

votes

















up vote
1
down vote



accepted










DomainEventPublisher.publish() is synchronous. You'd setup a generic handler (handles all events) which stores the events in the same database transaction as the business process, which means your event storage must have the ability to be transactionnal with whatever other storage mechanism you rely on to store the state of your aggregates.



Once events have been written on disk transactionnaly, you can then put them on a message queue for asynchronous delivery.




Are there other known ways to do it?




Well, rather than using a static DomainEventPublisher you could record events in a collection on the AR, just like in event sourcing and then implement a centralised mechanism to store them (e.g. transaction hooks, using aspects, etc.).






share|improve this answer























  • Thanks. I like this solution. Are there other known ways to do it ?
    – arnaud576875
    yesterday


















up vote
0
down vote














What happens if DomainEventPublisher.publish() succeeds, but the
transaction fails?




In this case I am against Vernon aproach. I prefer to return the events to the application service. This way I can persist the changes performed by the aggregate using a transacion (if needed) and, if everything is Ok, I will publish the event. This also helps to keep the business layer entirely clean and pure.



In a few words; if the transaction fails then no event is raised.




What happens if DomainEventPublisher.publish() fails?




A domain event never fails, by business ruels, because it's a notification of things that happened. If an aggregate said Yes to the operation and return a event expresing the bussines changes; then nothing in the world should say that this operation can not be done or has to be undone.



If the event fails by infrastructure then you need to have the tools to re-raise it (automatically or manualy) when the outage is fixed and eventualy archive the consistency in your system. Take a look at NServiceBus. It provides retries, error queues, logs and so on to never loose the events.
If the message system is down you have at least event logs that you can use to re-reise them into the message system.






share|improve this answer























  • Thanks. I think that my question was not clear enough about the things that can fail: The first thing is that we can fail to pulish an event (e.g. the messaging system is down temporarily). The second thing is that after publishing an event, the ongoing transaction can fail to commit; as a result, we have published an event, but the thing didn't really happen since the transaction failed.
    – arnaud576875
    yesterday










  • But I am answering that 2 things. What do you do not understand in my answer that drives you to think that I misunderstood your question?
    – jlvaquero
    yesterday










  • I'm speaking about publishing events, not about handling them :)
    – arnaud576875
    yesterday












  • And my answer is that changing Vernon strategy allows you to publish the events when the transaction commits or not publish them when transaction fails.
    – jlvaquero
    yesterday











Your Answer






StackExchange.ifUsing("editor", function () {
StackExchange.using("externalEditor", function () {
StackExchange.using("snippets", function () {
StackExchange.snippets.init();
});
});
}, "code-snippets");

StackExchange.ready(function() {
var channelOptions = {
tags: "".split(" "),
id: "1"
};
initTagRenderer("".split(" "), "".split(" "), channelOptions);

StackExchange.using("externalEditor", function() {
// Have to fire editor after snippets, if snippets enabled
if (StackExchange.settings.snippets.snippetsEnabled) {
StackExchange.using("snippets", function() {
createEditor();
});
}
else {
createEditor();
}
});

function createEditor() {
StackExchange.prepareEditor({
heartbeatType: 'answer',
convertImagesToLinks: true,
noModals: true,
showLowRepImageUploadWarning: true,
reputationToPostImages: 10,
bindNavPrevention: true,
postfix: "",
imageUploader: {
brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
allowUrls: true
},
onDemand: true,
discardSelector: ".discard-answer"
,immediatelyShowMarkdownHelp:true
});


}
});














 

draft saved


draft discarded


















StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53409319%2fdomaineventpublisher-consistency%23new-answer', 'question_page');
}
);

Post as a guest















Required, but never shown

























2 Answers
2






active

oldest

votes








2 Answers
2






active

oldest

votes









active

oldest

votes






active

oldest

votes








up vote
1
down vote



accepted










DomainEventPublisher.publish() is synchronous. You'd setup a generic handler (handles all events) which stores the events in the same database transaction as the business process, which means your event storage must have the ability to be transactionnal with whatever other storage mechanism you rely on to store the state of your aggregates.



Once events have been written on disk transactionnaly, you can then put them on a message queue for asynchronous delivery.




Are there other known ways to do it?




Well, rather than using a static DomainEventPublisher you could record events in a collection on the AR, just like in event sourcing and then implement a centralised mechanism to store them (e.g. transaction hooks, using aspects, etc.).






share|improve this answer























  • Thanks. I like this solution. Are there other known ways to do it ?
    – arnaud576875
    yesterday















up vote
1
down vote



accepted










DomainEventPublisher.publish() is synchronous. You'd setup a generic handler (handles all events) which stores the events in the same database transaction as the business process, which means your event storage must have the ability to be transactionnal with whatever other storage mechanism you rely on to store the state of your aggregates.



Once events have been written on disk transactionnaly, you can then put them on a message queue for asynchronous delivery.




Are there other known ways to do it?




Well, rather than using a static DomainEventPublisher you could record events in a collection on the AR, just like in event sourcing and then implement a centralised mechanism to store them (e.g. transaction hooks, using aspects, etc.).






share|improve this answer























  • Thanks. I like this solution. Are there other known ways to do it ?
    – arnaud576875
    yesterday













up vote
1
down vote



accepted







up vote
1
down vote



accepted






DomainEventPublisher.publish() is synchronous. You'd setup a generic handler (handles all events) which stores the events in the same database transaction as the business process, which means your event storage must have the ability to be transactionnal with whatever other storage mechanism you rely on to store the state of your aggregates.



Once events have been written on disk transactionnaly, you can then put them on a message queue for asynchronous delivery.




Are there other known ways to do it?




Well, rather than using a static DomainEventPublisher you could record events in a collection on the AR, just like in event sourcing and then implement a centralised mechanism to store them (e.g. transaction hooks, using aspects, etc.).






share|improve this answer














DomainEventPublisher.publish() is synchronous. You'd setup a generic handler (handles all events) which stores the events in the same database transaction as the business process, which means your event storage must have the ability to be transactionnal with whatever other storage mechanism you rely on to store the state of your aggregates.



Once events have been written on disk transactionnaly, you can then put them on a message queue for asynchronous delivery.




Are there other known ways to do it?




Well, rather than using a static DomainEventPublisher you could record events in a collection on the AR, just like in event sourcing and then implement a centralised mechanism to store them (e.g. transaction hooks, using aspects, etc.).







share|improve this answer














share|improve this answer



share|improve this answer








edited yesterday

























answered yesterday









plalx

32k44770




32k44770












  • Thanks. I like this solution. Are there other known ways to do it ?
    – arnaud576875
    yesterday


















  • Thanks. I like this solution. Are there other known ways to do it ?
    – arnaud576875
    yesterday
















Thanks. I like this solution. Are there other known ways to do it ?
– arnaud576875
yesterday




Thanks. I like this solution. Are there other known ways to do it ?
– arnaud576875
yesterday












up vote
0
down vote














What happens if DomainEventPublisher.publish() succeeds, but the
transaction fails?




In this case I am against Vernon aproach. I prefer to return the events to the application service. This way I can persist the changes performed by the aggregate using a transacion (if needed) and, if everything is Ok, I will publish the event. This also helps to keep the business layer entirely clean and pure.



In a few words; if the transaction fails then no event is raised.




What happens if DomainEventPublisher.publish() fails?




A domain event never fails, by business ruels, because it's a notification of things that happened. If an aggregate said Yes to the operation and return a event expresing the bussines changes; then nothing in the world should say that this operation can not be done or has to be undone.



If the event fails by infrastructure then you need to have the tools to re-raise it (automatically or manualy) when the outage is fixed and eventualy archive the consistency in your system. Take a look at NServiceBus. It provides retries, error queues, logs and so on to never loose the events.
If the message system is down you have at least event logs that you can use to re-reise them into the message system.






share|improve this answer























  • Thanks. I think that my question was not clear enough about the things that can fail: The first thing is that we can fail to pulish an event (e.g. the messaging system is down temporarily). The second thing is that after publishing an event, the ongoing transaction can fail to commit; as a result, we have published an event, but the thing didn't really happen since the transaction failed.
    – arnaud576875
    yesterday










  • But I am answering that 2 things. What do you do not understand in my answer that drives you to think that I misunderstood your question?
    – jlvaquero
    yesterday










  • I'm speaking about publishing events, not about handling them :)
    – arnaud576875
    yesterday












  • And my answer is that changing Vernon strategy allows you to publish the events when the transaction commits or not publish them when transaction fails.
    – jlvaquero
    yesterday















up vote
0
down vote














What happens if DomainEventPublisher.publish() succeeds, but the
transaction fails?




In this case I am against Vernon aproach. I prefer to return the events to the application service. This way I can persist the changes performed by the aggregate using a transacion (if needed) and, if everything is Ok, I will publish the event. This also helps to keep the business layer entirely clean and pure.



In a few words; if the transaction fails then no event is raised.




What happens if DomainEventPublisher.publish() fails?




A domain event never fails, by business ruels, because it's a notification of things that happened. If an aggregate said Yes to the operation and return a event expresing the bussines changes; then nothing in the world should say that this operation can not be done or has to be undone.



If the event fails by infrastructure then you need to have the tools to re-raise it (automatically or manualy) when the outage is fixed and eventualy archive the consistency in your system. Take a look at NServiceBus. It provides retries, error queues, logs and so on to never loose the events.
If the message system is down you have at least event logs that you can use to re-reise them into the message system.






share|improve this answer























  • Thanks. I think that my question was not clear enough about the things that can fail: The first thing is that we can fail to pulish an event (e.g. the messaging system is down temporarily). The second thing is that after publishing an event, the ongoing transaction can fail to commit; as a result, we have published an event, but the thing didn't really happen since the transaction failed.
    – arnaud576875
    yesterday










  • But I am answering that 2 things. What do you do not understand in my answer that drives you to think that I misunderstood your question?
    – jlvaquero
    yesterday










  • I'm speaking about publishing events, not about handling them :)
    – arnaud576875
    yesterday












  • And my answer is that changing Vernon strategy allows you to publish the events when the transaction commits or not publish them when transaction fails.
    – jlvaquero
    yesterday













up vote
0
down vote










up vote
0
down vote










What happens if DomainEventPublisher.publish() succeeds, but the
transaction fails?




In this case I am against Vernon aproach. I prefer to return the events to the application service. This way I can persist the changes performed by the aggregate using a transacion (if needed) and, if everything is Ok, I will publish the event. This also helps to keep the business layer entirely clean and pure.



In a few words; if the transaction fails then no event is raised.




What happens if DomainEventPublisher.publish() fails?




A domain event never fails, by business ruels, because it's a notification of things that happened. If an aggregate said Yes to the operation and return a event expresing the bussines changes; then nothing in the world should say that this operation can not be done or has to be undone.



If the event fails by infrastructure then you need to have the tools to re-raise it (automatically or manualy) when the outage is fixed and eventualy archive the consistency in your system. Take a look at NServiceBus. It provides retries, error queues, logs and so on to never loose the events.
If the message system is down you have at least event logs that you can use to re-reise them into the message system.






share|improve this answer















What happens if DomainEventPublisher.publish() succeeds, but the
transaction fails?




In this case I am against Vernon aproach. I prefer to return the events to the application service. This way I can persist the changes performed by the aggregate using a transacion (if needed) and, if everything is Ok, I will publish the event. This also helps to keep the business layer entirely clean and pure.



In a few words; if the transaction fails then no event is raised.




What happens if DomainEventPublisher.publish() fails?




A domain event never fails, by business ruels, because it's a notification of things that happened. If an aggregate said Yes to the operation and return a event expresing the bussines changes; then nothing in the world should say that this operation can not be done or has to be undone.



If the event fails by infrastructure then you need to have the tools to re-raise it (automatically or manualy) when the outage is fixed and eventualy archive the consistency in your system. Take a look at NServiceBus. It provides retries, error queues, logs and so on to never loose the events.
If the message system is down you have at least event logs that you can use to re-reise them into the message system.







share|improve this answer














share|improve this answer



share|improve this answer








edited yesterday

























answered yesterday









jlvaquero

6,50211836




6,50211836












  • Thanks. I think that my question was not clear enough about the things that can fail: The first thing is that we can fail to pulish an event (e.g. the messaging system is down temporarily). The second thing is that after publishing an event, the ongoing transaction can fail to commit; as a result, we have published an event, but the thing didn't really happen since the transaction failed.
    – arnaud576875
    yesterday










  • But I am answering that 2 things. What do you do not understand in my answer that drives you to think that I misunderstood your question?
    – jlvaquero
    yesterday










  • I'm speaking about publishing events, not about handling them :)
    – arnaud576875
    yesterday












  • And my answer is that changing Vernon strategy allows you to publish the events when the transaction commits or not publish them when transaction fails.
    – jlvaquero
    yesterday


















  • Thanks. I think that my question was not clear enough about the things that can fail: The first thing is that we can fail to pulish an event (e.g. the messaging system is down temporarily). The second thing is that after publishing an event, the ongoing transaction can fail to commit; as a result, we have published an event, but the thing didn't really happen since the transaction failed.
    – arnaud576875
    yesterday










  • But I am answering that 2 things. What do you do not understand in my answer that drives you to think that I misunderstood your question?
    – jlvaquero
    yesterday










  • I'm speaking about publishing events, not about handling them :)
    – arnaud576875
    yesterday












  • And my answer is that changing Vernon strategy allows you to publish the events when the transaction commits or not publish them when transaction fails.
    – jlvaquero
    yesterday
















Thanks. I think that my question was not clear enough about the things that can fail: The first thing is that we can fail to pulish an event (e.g. the messaging system is down temporarily). The second thing is that after publishing an event, the ongoing transaction can fail to commit; as a result, we have published an event, but the thing didn't really happen since the transaction failed.
– arnaud576875
yesterday




Thanks. I think that my question was not clear enough about the things that can fail: The first thing is that we can fail to pulish an event (e.g. the messaging system is down temporarily). The second thing is that after publishing an event, the ongoing transaction can fail to commit; as a result, we have published an event, but the thing didn't really happen since the transaction failed.
– arnaud576875
yesterday












But I am answering that 2 things. What do you do not understand in my answer that drives you to think that I misunderstood your question?
– jlvaquero
yesterday




But I am answering that 2 things. What do you do not understand in my answer that drives you to think that I misunderstood your question?
– jlvaquero
yesterday












I'm speaking about publishing events, not about handling them :)
– arnaud576875
yesterday






I'm speaking about publishing events, not about handling them :)
– arnaud576875
yesterday














And my answer is that changing Vernon strategy allows you to publish the events when the transaction commits or not publish them when transaction fails.
– jlvaquero
yesterday




And my answer is that changing Vernon strategy allows you to publish the events when the transaction commits or not publish them when transaction fails.
– jlvaquero
yesterday


















 

draft saved


draft discarded



















































 


draft saved


draft discarded














StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53409319%2fdomaineventpublisher-consistency%23new-answer', 'question_page');
}
);

Post as a guest















Required, but never shown





















































Required, but never shown














Required, but never shown












Required, but never shown







Required, but never shown

































Required, but never shown














Required, but never shown












Required, but never shown







Required, but never shown







Popular posts from this blog

A CLEAN and SIMPLE way to add appendices to Table of Contents and bookmarks

Calculate evaluation metrics using cross_val_predict sklearn

Insert data from modal to MySQL (multiple modal on website)