Spring 启动分布式事务
Spring boot Distrubuted transaction
我们需要找到解决微服务架构中分布式事务管理的最佳方法。
这是问题陈述。
我们有一个复合微服务,它应该与底层的其他 2 个原子微服务(显然是为了特定目的)交互,并且有单独的数据库,例如我们可以将这 2 个微服务视为
- STUDENT_SERVICE (STU_DB)
- TEACHER_SERVICE (TEACHR_DB)
在复合服务用例中,用户(管理员)可以为特定课程分配教师给学生等。
我想知道我们如何在一个事务中解决这个问题,因为每个服务(STUDENT_SERVICE 和 TEACHER_SERVICE )都有单独的数据库,所有这些都应该在一个事务中发生,无论是提交还是回滚。
因为这 2 个服务是分开的,我认为 JTA 不会有帮助,因为它意味着将这 2 个应用程序(服务)部署在同一个应用程序服务器上!
如上所述,我已选择退出 JTA
//伪代码
class 复合服务{
AssignStaff(resquest){
//txn Start
updateStudentServiceAPI(request);
UpdateTeacherServiceAPI(request);
//txn End
}
}
系统在 api 执行后应处于一致状态
这是一个棘手的问题,即使乍一看并不明显。
您要求的功能被理解为 anti-pattern 微服务架构。
微服务架构总体上是一个分布式系统。分布式系统中的事务很难(参见 https://martin.kleppmann.com/2015/09/26/transactions-at-strange-loop.html)。您的应用程序由两个服务组成。
JTA 是 Java API 用于 ACID 样式事务的。 ACID 事务通常需要在数据库中建立锁。由于事务跨越多个服务(在您的情况下有两个),因此一个服务的故障可能会阻止另一个服务的处理。在这种情况下,您将失去微服务架构的优势——服务的松散耦合和独立性。您最终可以构建一个分布式单体(参见不错的文章 https://blog.christianposta.com/microservices/the-hardest-part-about-microservices-data/)。
顺便说一句。在 Whosebug 上有几个关于微服务事务主题的讨论。只需搜索或检查例如
- Distributed transactions in microservices
- Transactions in microservices
- Transactions across REST microservices?
你有什么选择
(免责声明:我是 http://narayana.io 的开发人员,所提供的选项是从 Java EE 和 Narayana 的角度出发的。可能还有其他项目提供类似的功能。另外,即使是 Narayana 也能很好地集成对于 Spring,您可能需要处理一些集成问题。)
- 您确实需要 运行 项目中的 ACID 样式事务 - 也就是说您坚持需要您描述的方式的事务行为。然后你需要跨越服务的事务。然后,如果服务通过 REST 进行通信,您可以考虑例如 Narayana REST-AT (http://jbossts.blogspot.com/2011/03/rest-cloud-and-transactions.html, start looking into quickstart here https://github.com/jbosstm/quickstart/tree/master/rts)
- 你放宽了对原子性的要求,然后你可以考虑一些放宽一致性的事务模型(你可以最终保持一致)。您可以考虑例如 LRA (https://github.com/eclipse/microprofile-lra/blob/master/spec/src/main/asciidoc/microprofile-lra-spec.adoc)。 (不幸的是,规范和实施还没有准备好,但 PoC 在当前状态下可能 运行。)
- 您想完全使用不同的方法来处理事务。然后你可以调查事件溯源。您将部署例如Apache Kafka 并将更新事件发送到事件存储。每个服务将读取这些事件并独立更新数据库。
我们需要找到解决微服务架构中分布式事务管理的最佳方法。
这是问题陈述。
我们有一个复合微服务,它应该与底层的其他 2 个原子微服务(显然是为了特定目的)交互,并且有单独的数据库,例如我们可以将这 2 个微服务视为
- STUDENT_SERVICE (STU_DB)
- TEACHER_SERVICE (TEACHR_DB)
在复合服务用例中,用户(管理员)可以为特定课程分配教师给学生等。
我想知道我们如何在一个事务中解决这个问题,因为每个服务(STUDENT_SERVICE 和 TEACHER_SERVICE )都有单独的数据库,所有这些都应该在一个事务中发生,无论是提交还是回滚。
因为这 2 个服务是分开的,我认为 JTA 不会有帮助,因为它意味着将这 2 个应用程序(服务)部署在同一个应用程序服务器上!
如上所述,我已选择退出 JTA //伪代码 class 复合服务{
AssignStaff(resquest){
//txn Start
updateStudentServiceAPI(request);
UpdateTeacherServiceAPI(request);
//txn End
}
}
系统在 api 执行后应处于一致状态
这是一个棘手的问题,即使乍一看并不明显。
您要求的功能被理解为 anti-pattern 微服务架构。
微服务架构总体上是一个分布式系统。分布式系统中的事务很难(参见 https://martin.kleppmann.com/2015/09/26/transactions-at-strange-loop.html)。您的应用程序由两个服务组成。
JTA 是 Java API 用于 ACID 样式事务的。 ACID 事务通常需要在数据库中建立锁。由于事务跨越多个服务(在您的情况下有两个),因此一个服务的故障可能会阻止另一个服务的处理。在这种情况下,您将失去微服务架构的优势——服务的松散耦合和独立性。您最终可以构建一个分布式单体(参见不错的文章 https://blog.christianposta.com/microservices/the-hardest-part-about-microservices-data/)。
顺便说一句。在 Whosebug 上有几个关于微服务事务主题的讨论。只需搜索或检查例如
- Distributed transactions in microservices
- Transactions in microservices
- Transactions across REST microservices?
你有什么选择
(免责声明:我是 http://narayana.io 的开发人员,所提供的选项是从 Java EE 和 Narayana 的角度出发的。可能还有其他项目提供类似的功能。另外,即使是 Narayana 也能很好地集成对于 Spring,您可能需要处理一些集成问题。)
- 您确实需要 运行 项目中的 ACID 样式事务 - 也就是说您坚持需要您描述的方式的事务行为。然后你需要跨越服务的事务。然后,如果服务通过 REST 进行通信,您可以考虑例如 Narayana REST-AT (http://jbossts.blogspot.com/2011/03/rest-cloud-and-transactions.html, start looking into quickstart here https://github.com/jbosstm/quickstart/tree/master/rts)
- 你放宽了对原子性的要求,然后你可以考虑一些放宽一致性的事务模型(你可以最终保持一致)。您可以考虑例如 LRA (https://github.com/eclipse/microprofile-lra/blob/master/spec/src/main/asciidoc/microprofile-lra-spec.adoc)。 (不幸的是,规范和实施还没有准备好,但 PoC 在当前状态下可能 运行。)
- 您想完全使用不同的方法来处理事务。然后你可以调查事件溯源。您将部署例如Apache Kafka 并将更新事件发送到事件存储。每个服务将读取这些事件并独立更新数据库。