我对微服务社区有疑问。我将从教育领域给出一个例子,但它适用于每个微服务架构。
假设我有学生服务和许可服务,其业务要求是学生数量受许可限制。因此,每次创建学生时都必须进行许可检查。有多种类型的许可证,因此许可证的类型必须包含在操作中。
我的问题是你发现哪种方法在实践中更好:
人们谈论微服务体系结构更像是图形而不是层次结构,而选项1 有点将其转变为层次结构,在这种层次结构中,复合材料越来越粗糙。其他缺点是它会对服务客户端应该实际使用的内容产生混淆,并且会出现一些重复,因为复合API必须包含调用下游服务所需的所有参数。 它确实有很大的好处,因为它为您提供了处理故障,编排和处理一致性的自然场所。
选项2 似乎也有缺点:
许可API必须泄漏到学生API中,以便您可以指定许可限制。
它给学生服务带来了很大的负担,因为它必须处理所有相关服务的一致性
选项3 虽然正在脱离天堂,但我认为这不会起作用,因为这一切都是从用户界面触发的,人们并不习惯“在这个新学生之前做其他事情”显示“方法。
谢谢
答案 0 :(得分:2)
应用许可和创建学生是正交的,因此选项2没有意义。
选项1更明智,但我会尽量不建立另一项服务。相反,我会尝试通过许可中间件“过滤”对学生服务的调用。
通过这种方式,您可以将此中间件用于其他服务调用(例如,类服务),并且许可和学生的API的更改可以独立完成,因为这些内容实际上是独立的。事实上,许可证正在使用许多学生,但这很容易改变。
我不确定选项3,基于事件的方法如何在这里提供帮助。它可以解决其他问题。
答案 1 :(得分:2)
是的,将使用许可证服务API。您可以将其称为泄漏(有人必须使用它)或封装,以便请求学生服务的客户端不必担心许可。
有些服务必须承担这个负担。但我会有机地管理它。我们正在谈论需要另一个服务的1项服务。如果这种情况增长并变得具体麻烦,那么就可以进行重构。如果学生服务所需的服务数量增长,我认为它可以优雅地重构,并且学生服务可能成为组合服务,并且如果需要,可以将独立使用的服务组合并到新服务中。但是,如果学生服务使用的依赖服务列表仅供学生服务使用,那么我不知道是否值得将它们分组到自己的服务中。我认为不是负担和泄漏,你可以将其视为封装和所有权......学生服务是该负担的所有者,因此不需要泄露给其他客户/服务。
替代方案是各种复合服务。就像我对前一个要点的回答一样,如果它表面上是一个真正的问题,那么就可以优雅地解决这个问题。
如果强迫您的每个选项都可以变成可行的解决方案。我正在为备选方案2提出一个自以为是的案例。
答案 2 :(得分:1)
选项1和2创建紧密耦合,应尽可能避免,因为您希望让您的服务独立。所以问题就变成了:
我们如何使用基于事件的架构来实现这一目标?
使用事件来跟踪学生服务中许可证服务的许可信息,实际上是数据重复。这里的缺点是:您只有最终的一致性,因为数据重复是异步的。
使用异步事件触发最终触发学生创建的事件链。从您的问题来看,看起来您已经有了这个想法,但是在处理UI方面存在问题。这里有两个可能的选项:等待学生创建(或失败)事件,少量超时,或(事件更好),让你的系统完全被动(使用UI的服务器 - 客户端推送机制)。
答案 3 :(得分:0)
我知道这个问题已经被问过了,但我想我有话要说,这可能是有价值的。
首先,您的方法将取决于最终产品的总体规模。我倾向于遵循经验法则:如果我在各个微服务之间存在太多依赖关系,我倾向于使用一些可以简化并可能删除这些依赖关系的东西。我不希望最终得到蜘蛛网服务!这里有一个好处是消息队列,例如RabbitMQ
但是,如果我只有几个相互通信的服务,我会让它们直接相互调用,作为任何替代解决方案,同时简化架构,增加一些计算和基础设施开销。
无论您决定采用哪种方法,都要考虑Hexagonal architecture设计您的服务!当您决定从一个解决方案迁移到另一个解决方案时,这将为您省去麻烦。我倾向于将我的DAO设计为"适配器",因此调用服务A的DAO将直接或通过消息队列调用它,独立于业务逻辑。当我需要更改它时,我可以将此DAO更改为另一个DAO,而无需触及任何业务逻辑(最终业务逻辑并不关心它是如何获取数据的)。六边形架构非常适合微服务,TDD和黑盒测试。
答案 4 :(得分:0)
我建议选择3。您必须在可用性和一致性之间进行选择-在微服务体系结构中,最经常需要可用性。
您的“学生”汇总应具有“ LicenseStatus”属性。创建学生后,其许可证状态将设置为“未验证”,并发布事件“ StudentCreated”。然后,LicenseService应对此事件做出反应,并尝试为该学生保留许可证。然后,它将相应地发布“保留”或“拒绝”事件。学生服务将通过订阅这些事件来更新学生的身份。
当UI调用您的API网关创建学生时,网关将简单地调用Student服务进行创建并返回202 Accepted或200 OK响应,而不必等待学生获得适当的许可。当学生通过异步通信(例如通过长轮询或Web套接字)获得许可时,UI可以通知用户。
如果许可服务出现故障或速度缓慢,则仅会影响许可。学生服务将仍然可用,并将继续成功处理请求。一旦许可证服务再次正常运行,服务总线就会从队列中推送所有未决的“ StudentCreated”事件(最终一致性)。
此方法还鼓励扩展。将来添加的新微服务可以订阅这些事件,而无需对学生或许可微服务进行任何更改(去耦)。
使用选项1或选项2,您将无法获得任何这些好处,并且由于一种不健康的微服务,许多微服务将停止工作。