58

If you go for a microservices architecture in your organization, they can share configuration via zookeeper or its equivalent. However, how should the various services share a common db schema? common constants? and common utilities?

One way would be to place all the microservices in the same code repository, but that would contradict the decoupling that comes with microservices...

Another way would be to have each microservice be completely independent, however that would cause code duplication and data duplication in the separate databases each microservice would have to hold.

Yet another way would be to implement functional microservices with no context\state, but that's usually not realistic and would push the architecture to having a central hub that maintains the context\state and a lot of traffic from\to it.

What would be a scalable, efficient practical and hopefully beautiful way to share code and schema between microservices?

4

4 回答 4

34

关于通用代码,最好的做法是使用打包系统。因此,如果您使用 Java,则使用 maven,如果使用 Ruby,则使用 Gems,如果使用 python,则使用 pypi 等。理想情况下,打包系统几乎不会增加摩擦,因此您可能有一个(例如 git)存储库用于一个公共库(或几个公共-不同主题的库)并通过工件存储库(例如私有 maven/gems/pypi)发布其工件。然后在微服务中添加对所需库的依赖。因此代码重用很容易。在某些情况下,打包系统确实会增加一些摩擦(一个是 maven),所以人们可能更喜欢使用单个 git repo 来处理所有内容和多模块项目设置。这不像第一种方法那么干净,但效果也不错,而且还不错。

关于模式 - 如果您想按书行事,那么每个微服务都有自己的数据库。他们不会接触彼此的数据。这是一种非常模块化的方法,起初似乎会给您的流程增加一些摩擦,但最终我想您会感谢我的。它将允许对您的微服务进行快速迭代,例如,您可能希望将一个数据库实现替换为一个特定服务的另一个数据库实现。想象一下,当您的所有服务都使用同一个数据库时这样做!祝你好运......但是如果每个服务都使用它自己的数据库,那么服务会正确地抽象数据库(例如,它不接受 SQL 查询作为 API 调用;-))然后将 mysql 更改为 Cassandra 突然变得可行。拥有完全隔离的数据库还有其他好处,

所以简而言之 - 通用代码(实用程序,常量等) - 使用打包系统或一些源代码链接,如 git-tree

数据库——你不碰我的,我不碰你的。这是解决这个问题的更好方法。

HTH,冉。

于 2014-09-01T07:45:10.840 回答
19

“最纯粹”的方法,即耦合最少的方法,是不共享任何代码

如果您发现两个服务(称为 A 和 B)需要相同的功能,您的选择是:

  • split if off 作为单独的服务 C,所以 A 和 B 可以使用 C
  • 咬紧牙关复制代码

虽然这听起来很尴尬,但您避免了(并不少见)创建每个人都依赖的“实用程序”或“通用”或“基础设施”库的问题,然后真的很难升级和更改(即间接耦合服务)。

在实践中,像往常一样,这是一种权衡。

  • 如果共享功能很重要,我会选择单独的服务。
  • 如果它只是常量,那么共享库可能是最好的解决方案。不过,您需要非常小心向后兼容性。
  • 对于配置数据,您还可以实现特定服务,可能使用一些现有技术,例如 LDAP。
  • 最后,对于可能独立发展的简单代码,复制可能是最好的解决方案。

但是,最好的方法取决于您的具体情况和问题。

于 2014-11-18T10:51:26.927 回答
4

根据我的项目经验

使用 SOAP 时共享 WSDL(不是服务模型代码,因为它们应该从 WSDL 生成)。使用 REST 时,客户端和服务器具有不同的模型(复制是但不共享)。一旦第二个或第三个消费者开始发挥作用,你就会遇到麻烦。保持它们解耦。在我过去,服务的操作和使用比数据结构更频繁地发生变化。另一个客户想要使用您的服务,或者必须同时运行第二个版本。

一些额外的想法

共享与可扩展性部分矛盾。Share-nothing 和 share-some/share-all 各有利弊。不共享任何内容可让您随时拥有充分的灵活性。微服务是提供特定领域服务的独立组件。

共享业务领域数据模型是一种常见的模式 ( http://www.ivarjacobson.com/resources/resources/books/#object%20orient%20software ),它可以防止重复。由于微服务划分并征服了业务部分,因此可能很难共享业务领域数据模型的某些内容。

微服务相互通信,所以我理解共享这些通信数据模型(主要基于 HTTP)的需要。如果您在服务提供者和消费者之间有一对一的映射,那么共享这些数据模型可能是可以的。一旦一个服务有多个消费者需要模型中的不同模型/字段,它就会变得很困难。

于 2014-09-01T07:36:16.050 回答
1

至于 ISP 原则(接口隔离原则),客户端应该依赖于接口而不是实现。我建议是否可以通过这种方式共享接口而不是实现,最好使系统与实现分离。

于 2015-08-27T11:12:11.083 回答