有没有一种方法可以将int编号分配给不同的无状态服务实例?

时间:2018-12-19 10:40:28

标签: azure-service-fabric service-fabric-stateless

我正在构建一个解决方案,其中将一个(服务结构)无状态服务部署到K个实例。该服务的任务是处理一些工作负载(例如查询),我想尽可能地在它们之间平均分配工作负载-我想使它成为一个动态解决方案,这意味着我明天决定从K个实例迁移到N个实例,我希望工作负载拆分的方式是现在可以自动在N个实例之间分配负载。我没有为此服务指定任何分区。

例如-

比方说,我想查询数据库以检索特定的记录块。我有5个节点。我希望这5个节点检索记录集的不同1/5。这可以通过某些查询逻辑来实现,例如(row_id%N == K),其中N是实例总数,K是唯一的instance_number

我希望利用FabricRuntime.GetNodeContext().NodeId-但这会返回一个不太有用的向导。

我正在寻找一种方法,可以确定地说出实例编号N中的实例编号M(我需要能够通过1..N命名实例)-因此我可以根据此设置查询逻辑。要求之一是如果该实例关闭/崩溃等...当SF自动重新启动它时,它仍应标识为相同的实例ID-以便2个或更多节点不会查询相同的结果集。

解决此问题的最佳方法是什么?是否有涉及通过ApplicationManifest.xmlServiceManifest.xml进行纯配置的解决方案?

1 个答案:

答案 0 :(得分:0)

没有针对您的问题的现成解决方案,但是可以通过许多不同的方式轻松完成。

最简单的方法是将Queue-Based Load Leveling patternCompeting Consumers pattern结合使用。 它由创建队列组成,将工作添加到队列中,每个实例都会收到一条消息来处理此工作,如果一个实例发生故障并且未处理该消息,它将返回到队列另一个实例来接它。

通过这种方式,您不必担心实例的数量,失败等。

关于正在排队的工作,这取决于您要进行批处理还是逐项处理。

逐项,您将每个正在处理的项目放入一条消息的队列中,这是处理工作的简单方法,每个实例一次处理一条消息,或者并行处理多条消息

批处理,您可以放置​​一条消息,该消息表示要处理的项目的列表以及该批处理直到完成的每个实例过程的列表,这有点棘手,因为您可能必须处理进度。完成工作,以防万一失败,下次您可以从停止的地方继续。

队列方法是一种反应性设计,在这种情况下,需要将工作放入队列中以触发处理。如果您需要一种主动方法,并且需要跟踪哪些工作归谁处理,您可能是最好使用Leasing mechanism之类的其他方法,在该方法中,每个实例都获得一个属于该实例的租约,直到释放该租约为止,这在处理分区数据或其他可以轻松拆分的机制时更适合负载。

关于ID的问题,一个选项是您所在副本的InstanceId,您可以通过StatelessService.Context.InstanceId进行访问,它不是顺序ID,而是随机数。这比使用节点ID更好,因为您可能在同一节点上有多个分区,并且ID会彼此冲突。 如果决定使用命名分区,则可以在分区名称中使用order,因此每个分区都有一个顺序名称。

值得一提的是,服务结构的局限性是 doesn't allow services to have multiple replicas on same node ,由于这一局限性,您可能必须牢记这一点来设计服务,否则将无法扩展一旦达到限制。另外,同一线程还讨论了处理多个分布式项目的方法,这些方法可能会给您一些想法。