0

I'm trying to implement .NET 4.5 async/await and am running into a few issues.

I have this code:

private async void GetPages()
{
    PageList = await _dataService.GetPageList(JobTypeId);
}

IDataService looks like this

public interface IDataService
{
    Task<List<PageDto>> GetPageList(int jobTypeId);
}

and DataService.GetPageList like this:

public Task<List<PageDto>> GetPageList(int jobTypeId)
{
    var retval = new List<PageDto>();

    try
    {
        retval =
            (from p in _connection.Table<PageDto>()
                where p.JobTypeId == jobTypeId
                select p).ToList();
    }

    catch (Exception ex)
    {
        Logger.Exception(ex);
    }

    return retval;
}

I somehow need to wrap the result in a task but I can't figure out how.

Any ideas?

UPDATE

I can't use ToListAsync due to limitations in the SQLLite library I'm using but how about something like this?

public async Task<List<PageDto>> GetPageListAsync(int jobTypeId)
{
    var retval = new List<PageDto>();

    try
    {
        await Task.Run(() =>
        {
            retval =
                (from jtp in _connection.Table<JobTypePage>()
                 join p in _connection.Table<PageDto>() on jtp.PageId equals p.PageId
                 where jtp.JobTypeId == jobTypeId
                 orderby jtp.JobTypePageId
                 select p).ToList();
        });

    }

    catch (Exception ex)
    {
        Logger.Exception(ex);
    }

    return retval;
}

1 Answer 1

5

First, you should be using asynchronous methods from the inside-out (not "imposing" async from the outside-in). In this case, I assume you're using EF6, so you could do:

retval = await
    (from p in _connection.Table<PageDto>()
        where p.JobTypeId == jobTypeId
        select p).ToListAsync();

And then you can just mark your method async:

public async Task<List<PageDto>> GetPageListAsync(int jobTypeId)

As I side note, I added the Async suffix to follow the Task-based Asynchronous Pattern.

For more information, check out my async intro.

Sign up to request clarification or add additional context in comments.

8 Comments

Stephen, Any reason for not returning task returned from ToListAsync and awaiting it?
It changes the error handling in this example. The error handling strategy the op is using is not one I would choose myself, but if the rest of the code assumes errors are logged and then ignored by the data service, then it's important for consistency.
It's SQLLite which does not have a ToListAsync method. I'm attempting to upgrade an old app that used backgroundworker.
If I can't use async from the inside out - due to the SQlLite library I'm using not supporting async - how would I then impose async from the outside in? Or is there another way?
Newer versions of SQLite (at least SQLite.NET) do support async. So check for a new version first, but if it still doesn't support it, then the proper solution is to return a plain List<T> from IDataService.GetPageList and not use async at all there. Then use Task.Run when you call it from your UI layer: PageList = await Task.Run(() => _dataService.GetPageList(JobTypeId));
|

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.