什么可能导致ITransaction.CommitAsync调用需要很长时间(24小时)?

时间:2016-08-03 07:44:08

标签: azure-service-fabric

我们在ITransaction.CommitAsync中遇到了一些奇怪的行为。有时,对CommitAsync的调用需要24小时才能完成。

在我们的场景中,我们每5分钟从硬件设备读取仪表数据,并将检查点存储在可靠的字典中。所以每隔5分钟左右运行以下代码:

var profileCheckpoints = await StateManager.GetOrAddAsync<IReliableDictionary<string, DateTime>>(StateNameProfileCheckpoints);

using (var tx = StateManager.CreateTransaction())
{
    // Dictionary key is a device guid + device register id,
    // e.g.: 13cdaad8-9b8b-4fba-b336-e72e06c047ab-1.0.99.1.0.255
    var key = GetCheckpointKey(context);

    // checkpoint is a DateTime
    await profileCheckpoints.SetAsync(tx, key, checkpoint);

    // this call will sometimes take 24h to complete
    await tx.CommitAsync();
}

我们在有状态服务中运行了多个后台任务。每个后台任务与单个硬件设备通信并运行上述代码。所有任务都使用相同的可靠字典,但只更新特定于设备的密钥。

某些任务运行良好,并且CommitAsync调用快速返回。对于其他任务,CommitAsync调用可能会突然需要24小时才能完成。抛出没有异常,代码继续像往常一样。一旦发生这种情况,除非我们重新启动服务,否则此任务的所有其他CommitAsync调用也将需要24小时才能完成。

在门户网站中报告群集和所有应用程序都是健康的。但是,当我在不同节点上查看事件查看器时,我看到记录了以下警告(大约每5秒一次):

dropping message <some guid>, Actor = Transport, Action = ‘’, fault = FABRIC_E_CONNECTION_CLOSED_BY_REMOTE_END

知道可能是什么原因造成的?

1 个答案:

答案 0 :(得分:0)

GetCheckpointKey是否与设备通信?可能是因为这占用了一个线程和阻塞,这意味着线程池已经用尽了。

可能紧紧抓着稻草,但GetCheckpointKey缺乏等待让我有点怀疑。