Asynchronous Loading of Data – a Better Way

When last we left off, we were loading the data for the ViewModel inside its constructor – a bad idea, because the data loading is done asynchronously, and constructors can’t be made async. So we need to find a better way to do that.

First off I want to factor the process of loading the data out to its own method inside my OverviewVM class:

With this public method I’ve got more options on handling the data. So the question is: do I really need to load the data right when my View Model is constructed? Actually, no. I don’t need the data until my View appears – and the OnAppearing() method can be made async to accommodate the asynchronous nature of data loading.

Because I need a reference to my View Model in OnAppearing(), I’m storing it in a field for now. Later on, when we get to decoupling our classes, that’s going to be done a better way, but for now this will do the job.

Except that there’s a little problem now. Because the data we’re binding to is not already in place when the page appears, our list of ToDo’s is empty. We need to explicitly tell our View that our collection of ToDoItems has changed.

I could do this by making my ViewModel implement the INotifyPropertyChanged interface – but fortunately MVVMLight already has a base class in place that will handle all of that for me. All I need to do is to make my View Model inherit from ViewModelBase and use ViewModelBase’s Set method, which handles both the assignment and notification for me.

The resulting View Model now looks like this:

So, another hurdle jumped. The code is slowly starting to look better, but still suffers from tight coupling. More on this next!

Repositories – Getting the Data to the ViewModel

Right now the ViewModel is pretty hideous. It shouldn’t be responsible for fetching the data, much less creating it – that’s a clear violation of the Single Responsibility Principle and all round Bad Idea (TM). So let’s make that the responsibility of a repository.

I have a go-to repository interface that I use as a starting point:

IEntity is there purely to make sure that the class in the repository has an Id field. Feel free to leave it out if you don’t need it, but it’s useful if you want to have a unique identifier for retrieving/updating entities in your repository.

For use with SQLite, I use IEntity to create a primary key on the Id:

…and then I make my ToDoItem class inherit from it.

Now my ToDoItem class fulfils all the requirements for use in a repository that implements IRepository<T>. Eventually I want that to be a repository that uses SQLite, but for now I’m going to use a bare-bones mock-up with some hard-coded data.

I’ll use this later in unit testing, so creating it is not actually a waste of time.

and now, finally, I can change my ViewModel to use this repository:

Now, looking at this, the ViewModel is still in a world of wrong. In fact, it’s so wrong that almost every line in it needs to be changed. We have tight coupling, we are blocking the UI thread because you can’t use ‘await’ in a constructor, we’re using a mock repository and an unsuitable collection, but fear not – all this will be addressed over the course of the next few posts…