Brian Liang
Brian Liang

Reputation: 7774

await / async issues

I'm working on Windows 8 CP and discovered that in my app, I'm unable to properly get the new async/await mechanism to work.

This method I am showing you will work when run as a UnitTest (called from a unit test) but when ran normally, it DOES NOT WORK!

StreamSocket _client;

private void Start() {
     SomeMethod();
     SomeOtherMethod();
}

private async void SomeMethod(string sample)
{
    var request = new GetSampleRequestObject(sample);
    byte[] payload = ConvertToByteArray(request, Encoding.UTF8);

    DataWriter writer = new DataWriter(_client.OutputStream);
    writer.WriteBytes(payload);
    await writer.StoreAsync(); // <--- after this executes, it exits the method and continues
    await writer.FlushAsync(); // <--- breakpoint never reaches here, instead
    writer.DetachStream();
}

private void SomeOtherMethod()
{
    string hello = "hello"; // <--- it skips everything and reaches here!
}

What gives?

Upvotes: 3

Views: 2932

Answers (4)

Amir Movahedi
Amir Movahedi

Reputation: 1792

I think you should edit:

StreamSocket _client;

private async Task Start() {
    await SomeMethod();
     SomeOtherMethod();
}

private async Task SomeMethod(string sample)
{
    var request = new GetSampleRequestObject(sample);
    byte[] payload = ConvertToByteArray(request, Encoding.UTF8);

    DataWriter writer = new DataWriter(_client.OutputStream);
    writer.WriteBytes(payload);
    await writer.StoreAsync(); // <--- after this executes, it exits the method and continues
    await writer.FlushAsync(); // <--- breakpoint never reaches here, instead
    writer.DetachStream();
}

private void SomeOtherMethod()
{
    string hello = "hello"; // <--- it skips everything and reaches here!
}

I hope help you

Upvotes: 0

Zhuang Pearl
Zhuang Pearl

Reputation: 46

I think Daniel Schlößer's answer may has some other problem. Here are my improved method:

private async void Start() {
    await SomeMethod();
    SomeOtherMethod();
}

An async function should be called with "await" at the beginning surely. But the function which use async function should be signed "async" as well.

That's my point. Thanks

Upvotes: 2

James Manning
James Manning

Reputation: 13579

Since it sounds like you want SomeMethod to complete before calling SomeOtherMethod, you need to have it return a Task and wait on that task to complete. All you need to do is change the 'async void' in the declaration to 'async Task' and then in the Start method, change the caller to SomeMethod().Wait();

As it stands, since you're not waiting for anything about the task to complete, once the method exits (hitting the first await), there's nothing to 'block' anything else on it having completed.

Using 'async void' means you don't care when it completes (or perhaps even if it completes). If you do care, you need to use 'async Task' and then use that appropriately.

Not sure if it'll help explain, but here's a blog post I did on the subject:

http://blog.sublogic.com/2012/03/06/async-lesson-2-of-n-async-void-probably-isnt-what-you-want/

Upvotes: 1

I think you have to put await in front of your initial SomeMethod call in the Start function:

await SomeMethod();

Upvotes: 6

Related Questions