【问题标题】:Can I get an item without lock from reliableDictionary in service fabric我可以从服务结构中的可靠字典中获取没有锁的项目吗
【发布时间】:2019-05-12 19:06:14
【问题描述】:

使用 TryGetValueAsync 从可靠字典中获取项目要么有一个默认锁,我假设它是共享锁,要么有一个写锁,它会阻止其他事务中的写入,有没有办法从可靠字典中获取一个没有锁的项目?

【问题讨论】:

  • 您是在尝试读取值以供将来修改还是对简单的读取操作感兴趣?
  • @Oleg 简单读没问题,目前我只看到 createAsyncEnumerable 可以无锁读

标签: locking azure-service-fabric reliable-dictionary


【解决方案1】:

根据documentation Service Fabric 自动管理事务级别并查找您(这基本上意味着您无法更改它们)。

事务有两个隔离级别:

  • 可重复读取:指定语句不能读取已被其他事务修改但尚未提交的数据,并且在当前事务完成之前没有其他事务可以修改当前事务已读取的数据。
  • 快照:指定事务中任何语句读取的数据是事务开始时存在的数据的事务一致版本。事务只能识别在事务开始之前提交的数据修改。当前事务开始后其他事务所做的数据修改对于当前事务中执行的语句是不可见的。效果就好像事务中的语句获得了事务开始时已提交数据的快照。快照在 Reliable Collections 中是一致的。

文档指出 primary 副本上的所有 SER(单实体读取)始终是 Repeatable Read 隔离级别(TryGetValueAsync 是 SER 操作),因此没有为 primary 副本更改此设置的方法。同时对于 secondary 副本,所有类型的读取始终具有 Snapshot 隔离级别。


所以我可以提出的解决方案是从 secondary 副本中读取数据。这就是使用ServicePartitionResolver 类获取次要副本地址的方式:

var partition = await ServicePartitionResolver.GetDefault().ResolveAsync(
    tuple.serviceName,
    new ServicePartitionKey(tuple.partitionName),
    cancellationToken);

var address = partition.Endpoints
    .Single(e => e.Role == ServiceEndpointRole.StatefulSecondary)?.Address;

这种方法的缺点是,由于复制延迟,次要副本数据可能会稍微过时。

【讨论】:

    猜你喜欢
    • 2016-07-25
    • 1970-01-01
    • 1970-01-01
    • 2023-01-24
    • 2017-04-16
    • 1970-01-01
    • 2016-12-04
    • 2020-10-23
    • 1970-01-01
    相关资源
    最近更新 更多