[英]Reusing NServiceBus messages saga data
是否有任何理由不在传奇数据中重用 NServiceBus 消息( IMessage
)? 我的意思是有这样的消息:
public class Order : IMessage
{
public virtual List<TillOrderLine> OrderLines { get; set; }
}
public class TillOrderLine : IMessage { ... }
然后也在 saga 和 saga 数据中使用它,如下所示:
public class OrderProcessingSaga :
Saga<OrderProcessingSagaData>,
IAmStartedByMessages<Order> { ... }
public class OrderProcessingSagaData : ISagaEntity
{
public virtual Guid Id { get; set; }
public virtual string Originator { get; set; }
public virtual string OriginalMessageId { get; set; }
// The message data is stored by the saga here.
public virtual Order Order { get; set; }
}
我意识到消息是由传输层(MSMQ)存储的,而 saga 数据与 saga 一起保存到 DB 中。 它适用于我当前的用例,重用 class 似乎更优雅,而不是为消息创建一个,另一个用于 saga 存储。
我想知道这种方法是否有任何问题?
我同意 mookid8000 所说的一切,但是我还有一个细节要补充。
您的 saga 存储通常会有很多争用。 为了保证一致性,saga 存储提供者通常会对数据设置更新锁,以保证来自同一 saga 的另一条消息不能同时改变 state。
如果您使用默认的 NHibernate saga 持久化器(并且您的虚拟属性向我表明您是),那么 NHibernate 使用一些假设来保存您的数据:
在任何情况下,saga 持久化器需要将数据拆分成的表中的行越多,就越难用细粒度的行锁来锁定所涉及的行。 如果有足够的争用,行锁将开始升级为页锁和表锁,然后你就真的遇到了问题。
这就是文档数据库真正适合 saga 存储的原因,这也是为什么在 NServiceBus 3.0 中他们将 RavenDB 设为默认的 saga 持久化器的原因。
在那之前,看看我写的基于 XML 序列化的 Saga Persister ,它可以为您今天的应用程序带来即将到来的 RavenDB 风格的 saga 持久化器的一些好处。
如果您必须坚持使用 NHibernate,我强烈建议您将消息与您的 saga 持久性解决方案紧密结合。 我几乎保证它会回来困扰你。
如果您当前的 saga 持久化者坚持数据而不抱怨,我想不出这种方法有什么问题 - 只要您意识到您将 class 用于两个目的,从而引入 saga 数据之间的耦合(这是私有的到服务)和消息(本质上是公开的)关于存在的字段、命名等。
然后,当您需要偏离消息的结构方式时,您可以为所有 saga 数据构建类。
PS: TillOrderLine
的唯一目的是在Order
中聚合,则不需要将其标记为IMessage
。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.