Spring Data的Domain Event的用法详解
程序员文章站
2022-06-30 23:49:41
1.ddd与spring data
ddd: domain-driven design(领域驱动设计)是复杂需求下软件开发的实现方式。有时间我将专门来讲解一下ddd。...
1.ddd与spring data
ddd: domain-driven design(领域驱动设计)是复杂需求下软件开发的实现方式。有时间我将专门来讲解一下ddd。
spring data在很多地方都是按照ddd原则进行的设计(如repository), 这里spring data主要是实现了ddd的aggregate和domain event:
- aggregate:一系列可以看成单一单元的领域对象的组合。如订单(order)和购物清单(line-items)都是单独的对象,但是将他们当成一个独立的单元(aggregate)。每个aggregate都有一个aggregate root,任何和外部交互应该只能通过aggregate root,这样aggregate root就可以确保aggregate的完整性。一个aggregate内部具有事务(数据一致性)边界。
- domain event: aggregate之间为了保证数据的一致性,使用事件驱动架构(event-driven architecture)来实现数据的最终一致性(eventual consistency)。而这些事件是通过aggregate root发布的domain events。
下面我们演示一个当person这个aggregate root 保存成功后,通过person的gender属性对统计实体genderstat更新男女性别的统计数量。
2.演示
2.1 person aggregate root
person作为aggregate root具备发布domain event的能力,在spring data 下可以有两种实现方式:
- – 继承abstractaggregateroot,并使用其registerevent()方法注册发布事件
- – 使用@domainevents注解方法发布事件
如:
@entity @data @allargsconstructor @noargsconstructor @tostring(exclude = "domainevents") public class person { @id @generatedvalue private long id; private string name; private integer gender;//1:male;2:female @domainevents collection<object> domainevents() { list<object> events= new arraylist<object>(); events.add(new personsavedevent(this.id,this.gender)); return events; } @afterdomaineventpublication void callbackmethod() { // } }
或
@entity @data @allargsconstructor @noargsconstructor @tostring(exclude = "domainevents") public class person extends abstractaggregateroot{ @id @generatedvalue private long id; private string name; private integer gender;//1:male;2:female public person afterpersonsavedcompleted(){ registerevent(new personsavedevent(this.id,this.gender)); return this; } }
2.2 监听事件处理
@component public class genderstatprocessor { @autowired genderrepository genderrepository; @async @transactionaleventlistener public void handleafterpersonsavedcomplete(personsavedevent event){ genderstat genderstat = genderrepository.findone(1l); if(event.getgender()==1){ genderstat.setmalecount(genderstat.getmalecount()+1); }else { genderstat.setfemalecount(genderstat.getfemalecount()+1); } genderrepository.save(genderstat); } }
3 源码地址:
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持。
推荐阅读
-
详解Spring Cloud负载均衡重要组件Ribbon中重要类的用法
-
详解Spring data 定义默认时间与日期的实例
-
详解Spring Data JPA系列之投影(Projection)的用法
-
Content-Type中application/x-www-form-urlencoded和multipart/form-data的区别及用法详解
-
Spring data jpa的使用与详解(复杂动态查询及分页,排序)
-
Spring AOP里的静态代理和动态代理用法详解
-
Spring Data Specification的用法,group by,order by及复杂情况和Pageable的注意事项
-
Spring Data的Domain Event的用法详解
-
Spring Data Jpa 中原生查询 REGEXP 的使用详解
-
详解Spring data 定义默认时间与日期的实例