in src/Microsoft.ServiceFabric.Services/Client/ServicePartitionResolver.cs [537:642]
private async Task<ResolvedServicePartition> ResolveHelperAsync(
Func<FabricClient, ResolvedServicePartition,
TimeSpan,
CancellationToken,
Task<ResolvedServicePartition>> resolveFunc,
ResolvedServicePartition previousRsp,
TimeSpan resolveTimeout,
TimeSpan maxRetryInterval,
CancellationToken cancellationToken,
Uri serviceUri)
{
while (true)
{
if (cancellationToken.IsCancellationRequested)
{
throw new OperationCanceledException();
}
var totaltime = new TimeoutHelper(resolveTimeout);
var client = this.GetClient();
ResolvedServicePartition rsp = null;
// resolve and get the rsp
try
{
rsp = await resolveFunc.Invoke(
client,
previousRsp,
totaltime.GetRemainingTime(),
CancellationToken.None);
}
catch (AggregateException ae)
{
ae.Handle(
x =>
{
if ((x is FabricTransientException) ||
(x is TimeoutException) ||
(x is OperationCanceledException))
{
return true;
}
return false;
});
}
catch (FabricTransientException)
{
}
catch (TimeoutException)
{
}
catch (OperationCanceledException)
{
}
catch (FabricObjectClosedException)
{
// retry on the different client
this.ReportFaulted(client);
}
// check if the rsp is valid
try
{
if (rsp != null)
{
rsp.GetEndpoint();
try
{
// Registering for Notification only for the first request for a service uri.
if (this.UseNotification && !this.registrationCache.ContainsKey(serviceUri))
{
var added = this.registrationCache.TryAdd(serviceUri, true);
if (added)
{
ServiceNotificationFilterDescription filter = new ServiceNotificationFilterDescription(
name: serviceUri,
matchNamePrefix: true,
matchPrimaryChangeOnly: false);
await client.ServiceManager.RegisterServiceNotificationFilterAsync(filter, totaltime.GetRemainingTime(), CancellationToken.None);
}
}
}
catch (Exception)
{
// Remove the Entry so that in next call we can again try registeration
bool res;
this.registrationCache.TryRemove(serviceUri, out res);
}
return rsp;
}
}
catch (FabricException)
{
// retry if no suitable endpoints found from the RSP
}
previousRsp = rsp;
// wait before retry
await Task.Delay(
new TimeSpan((long)(randomGenerator.NextDouble() * maxRetryInterval.Ticks)),
cancellationToken);
}
}