微服务和隔离持久性 - 如何存储/获取数据?

时间:2018-01-26 12:01:03

标签: microservices

在我的公司,我们即将转向微服务架构。我读了很多关于它的内容,并且有很多模糊不清的领域,它们是专门针对项目构建的,但是有一个领域似乎让每个人都同意,微服务需要有孤立的持久性或其他说法,他们需要拥有它们自己的数据库。

现在我喜欢这个想法,这意味着每个微服务都有自己的数据库模式,自己的域对象,并且100%独立于任何其他微服务数据结构。

有些事情我不太明白。

“客户服务”显然是应用程序的核心,我们可以看到基本上任何其他微服务在某些时候都需要一些关于用户的数据。是用户的信用额度,ID还是名称。

但由于其他微服务无法直接读入客户服务数据库,因此他们需要一遍又一遍地查询此服务。对于获取当前登录用户的名称等简单的东西,这很好(我猜),但是当我们需要在页面上显示60个用户并且我们无法进行任何SQL连接时,感觉就像我们遗漏了一些东西。当微服务依赖于大量的微服务时,情况会更糟。

所以我发现有些人实际上每天要查询微服务X次,以便将数据存入他们自己的微服务中。

因此,如果微服务“搜索”需要来自“产品”,“客户”的数据,它实际上会查询这些微服务,并将使用自己的数据结构保存数据。

我的问题是查询“产品”和“客户”应该是“搜索”,还是应该“产品”和“客户”将数据发送到“搜索”?

第一个选项看起来更容易,我们只需要在一侧有这个逻辑,那就是需要数据的地方。但是我们只会获得非常智能的静态数据,但绝对可行。 第二个选项看起来有点困难,但也更具可扩展性,因为我们可以在需要时获得非常新鲜的数据,因为数据在发送的地方发生了变化,也可能更加精细。

2 个答案:

答案 0 :(得分:1)

我认为您正确地确定了微服务方法的缺点!对这些具体问题没有优雅的解决方案。你将不得不吃掉这带来的额外工作和架构恶化。

现在具体解决您的问题:

  

我的问题应该是"搜索"查询"产品"和"客户"或应该"产品"和"客户"将数据发送到"搜索" ?

您似乎在寻找数据同步服务。你想在推拉之间做出决定。您担心数据新鲜度和逻辑重复。

这里的关键点是源服务无法了解其消费者。这是为了防止不必要的反向依赖。这会打破架构隔离。保持这一点的任何数据同步过程都很好。你可以做最方便的事。

例如,您可以使数据源公开两个API:

  1. 获取整个数据集的API。这将由目的地周期性地调用(例如,每晚)。它还可以用于随意播种目的地并修复那里的数据错误。
  2. 源数据库中的更改源,由更改发生的日期和时间键入。目的地现在可以非常频繁地轮询该更改订阅源(例如,每隔几秒或几分钟)并应用发生的小增量。
  3. 您甚至可以通过发布 - 订阅中间件构建实时更改Feed。许多消息队列软件都可以做到这一点。源代码只会发送对中间件的更改。

    构建所有这些在概念上很简单,但需要做很多工作。它还会创建大量正在进行的工作,并增加了漏洞的可能性。调试变得更加困难。我曾经在这样的系统上工作过。

    我要添加一个主观说明:很多团队都不太了解微服务。缺点往往被忽略。你正确地发现了一些缺点,它们很讨厌!鉴于我在网上看到的内容,我相信很多团队都没有意识到他们正在陷入困境。管理不同的数据存储可能是一场噩梦。这不是一次性的混乱"但是正在进行中。

    作为替代方案,我建议使用通用数据存储和构建服务,就像生活在同一进程中的类或项目一样。这为您提供了微服务代码结构,方便了正常开发。它还在桌面上留下了一些微服务的好处。

答案 1 :(得分:1)

您对问题的识别是正确的。

但问题的解决方案将取决于用例的用例。

在您的搜索服务示例中,产品服务和客户服务应该在kafka或类似的消息和搜索服务上发布他们的事件,听取他们并更新它。

如果让我们在为客户创建订单时说服务,您想要检查客户是否存在,那么您可以通过调用客户服务的同步API来实现,但为此也有其他方法,我在这里回答linking Microservices and allowing for one to be unavailable

从我的角度来看,应该避免服务之间的同步通信,并且有办法解决这个问题,上面的链接会有所帮助

您可以使用域驱动的设计理念来正确破坏您的服务及其合同