WCF and async await

NealCulinerNealCuliner USBeta ✭✭✭

Currently I'm generating my WCF service reference using slsvcutil from silverlight 5. I'd like to use the async await pattern and I don't believe you can generate task based contracts using silverlight 5 as I believe it's .NET 4.0? Not sure. Or I don't know the proper command line switch required to make this happen. So instead what I'd like to use is a WPF 4.5 application, add a service reference, then copy those files over to Xam Studio.

Any problems with this solution to using async await for WCF?

Thank you

P.S. If this is a good solution Xamarin may want to note this in the docs

Posts

  • JonathanPryorJonathanPryor USXamarin Team Xamurai

    Any problems with this solution to using async await for WCF?

    I have no idea, but if you want C#5 async support you need to use the beta releases.

  • ShawnCastrianniShawnCastrianni USBeta ✭✭✭

    The main difference between svcutil and slsvcutil is that slsvcutil is geared towards Silverlight and does NOT generate proxy code that relies on dynamic code generation at runtime. Since iOS does not allow dynamic code generation at runtime, ONLY the slsvcutil client generator can be used. I have not tested, but I suspect that Android WOULD allow the more powerful svcutil since Android DOES allow dynamic code generation at runtime. Now in order to use async and await, you would want to wrap the WCF web service call inside a Task so that your UI code can await it. However, because the slsvcutil only generates proxy methods that are ALREADY asynchronous, you cannot easily wrap it inside a Task. Therefore, I am stuck! If slsvcutil had the option to generate synchronous calls instead, then everything would work. Anybody have any ideas?

  • SteveS.3521SteveS.3521 USMember

    Im currently encountering the same problem. If I find a reasonable solution I'll be sure to post it here.

  • KimjKimj USMember

    You can hand edit the generated proxy code to wrap the Begin/End calls in a task. Something like this:

    Task<bool>.Factory.FromAsync(_client.BeginPing, _client.EndPing, null));
    
  • markcarewmarkcarew AUMember

    I use a Request Response pattern for all my web service interactions. So the form of FromAsync is identical for each Request Response pair.

    I can, thus, add a service reference to my PCL by using Microsoft.Net.Http version 2.2.28. This means that Silverlight slsvcutil is not required.

    I just run Update Service Reference after I have published a new version of my web service to IIS.

    private async Task<ServiceReference1.PingResponse> PingWcfService(ServiceReference1.PingRequest request) { ServiceReference1.PingResponse response = new ServiceReference1.PingResponse(); try { PetzoldOne.ServiceReference1.IPetzoldOneWcfService client = new PetzoldOneWcfServiceClient(); var task = Task<ServiceReference1.PingResponse>.Factory.FromAsync<ServiceReference1.PingRequest>( client.BeginPing, client.EndPing, request, null); response = await task; } catch (Exception ex) { response.Status = "Failed"; response.Message = ex.Message; } return response; }

  • bhldevbhldev CAMember

    Hi,

    In case anyone is still having this problem
    You can wrap with the above FromAsync with the task as above
    Then create a synchronous layer by using Task.Run and grabbing Result

    var x = Task.Run(() => Clazz.AsyncMethod(text)).Result;

    This is bad form and blocking in 99% of cases, but for the 1% of times... for example, if you can't allow async to spread across the whole application and you can't change the whole architecture of your application to support 1 async call from 1 legacy wcf webservice, this will do what you want... not sure about app store or other implications with blocking...

    ~ B

Sign In or Register to comment.