Asynchronous WCF Query Final step
-
12-11-2019 - |
Question
I am trying to learn how to implement an asynchronous pattern to query multiple wcf services concurrently, but do not know how to check that all concurrent calls are complete. I have a class that executes the asynchronous operations and then adds to a List as operations complete:
public static class ODataAsync
{
static DataServiceContext ServiceContext;
static List<DynamicEntity> Results = new List<DynamicEntity>();
private static void GetAsync(string serviceUri, NameValueCollection queryOptions, IAuthenticationScheme authenticationScheme)
{
string baseUri;
string entitySet;
string entityKey;
string queryString;
ValidateServiceUri(serviceUri, out baseUri, out entitySet, out entityKey, out queryString);
string resource = !string.IsNullOrEmpty(entityKey) ? entitySet + "(" + entityKey + ")" : entitySet;
DataServiceContext context = new DataServiceContext(new Uri(baseUri));
context.IgnoreMissingProperties = true;
ServiceContext = context;
DataServiceContextHandler handler = new DataServiceContextHandler(authenticationScheme);
handler.HandleGet(context);
DataServiceQuery<EntryProxyObject> query = context.CreateQuery<EntryProxyObject>(resource);
NameValueCollection options = HttpUtility.ParseQueryString(queryString);
options.Add(queryOptions);
foreach (string key in options.AllKeys)
{
query = query.AddQueryOption(key, options[key]);
}
try
{
query.BeginExecute(GetAsyncComplete, query);
}
catch (DataServiceQueryException ex)
{
throw new ApplicationException("An error occurred during query execution.", ex);
}
}
private static void GetAsyncComplete(IAsyncResult result)
{
QueryOperationResponse<EntryProxyObject> response =
((DataServiceQuery<EntryProxyObject>)result).EndExecute(result) as QueryOperationResponse<EntryProxyObject>;
IList<dynamic> list = new List<dynamic>();
foreach (EntryProxyObject proxy in response)
{
DynamicEntity entity = new DynamicEntity(proxy.Properties);
Results.Add(entity);
}
while (response.GetContinuation() != null)
{
Uri uri = response.GetContinuation().NextLinkUri;
response = ServiceContext.Execute<EntryProxyObject>(uri) as QueryOperationResponse<EntryProxyObject>;
foreach (EntryProxyObject proxy in response)
{
DynamicEntity entity = new DynamicEntity(proxy.Properties);
Results.Add(entity);
}
}
}
}
My 2 questions are:
1) How do I ensure that I only get the List Result(s) when all concurrent calls are finished? For instance if call GetAsync() within a loop, starting several concurrent processes, I need to ensure that they are all finished before taking the data out of the List Result.
2) Can I use BeginExecute() inside the GetContinuation() call and recursively use the same method GetAsyncComplete() as the callback function ? Or would that create a ton of threads and actually slow things down.
Thank you.
No correct solution