Fetching the latest data in listviews and detail screens in the lightswitch html client

Introduction

The behavior of the HTML client different quite a lot from the Silverlight client and that’s quite normal.

A difference you might not notice immediately is that in the context of a simple List screen with a connection to the details screen via a tap action, the html client will not automatically fetch the latest data. That’s simply by design and I think it’s ok. Nonetheless, you sometimes want it differently. Luckily the way how to implement it is so simple, that I amost feel ashamed to present it, but the reason why I present it because all LightSwitch html samples I downloaded or saw in articles, simply don’t handle concurrent user situations.

Tell me more

You can simply observe the standard behavior as follows:

So, make a trivial app with a browse screen on customers (with fields FirstName and LastName) and a corresponding add/edit screen. So, all out of the box.

Start now the application 2 times and wait until they both have the customer browse screen up and running.

In application 1, select the first customer and make a small change to the data (e.g. modify the last name).

Go now to application 2 and tap the same customer. You will notice that you still get the old data, because the html client will not by default fetch the latest data.

A very simple solution

We have 2 options:

1. Always fetch the latest data when the detail screen is opened

This can be simply accomplished with following code in the screen’s created method.

myapp.AddEditCustomer.created = function (screen) {

  screen.Customer.details.refresh();  
};

 

2. fetch the latest data inside the detail screen by means of a refresh button

image

 

Again, the code for the Refresh execute method is trivial:

myapp.AddEditCustomer.Refresh_execute = function (screen) {
     screen.Customer.details.refresh();
};

In case you really care about details, I would suggest to hide the Refresh button when the screen opens in create new mode. It doesn’t really make sense to refresh an item which is under construction:

myapp.AddEditCustomer.Refresh_canExecute = function (screen) {
    // Write code here.
    if (screen.Customer.RowVersion) {
        return true;
    }
};

A new entity typically has no rowversion field associated. No doubt, there are other techniques, but this simply works.

Don’t forget, as I did, the replace the star icon with the fancy “Refresh” icon :)

You can do something similar for the browse screen

I would recommend against an automatic fetch of the latest data, each time you open the browse screen. That causes in most cases too much data load.

Nonetheless, a refresh button sounds great. Here we might want some additional comfort. Sometimes, there is an item selected (like in my example, the second customer), so it would be great if this item stays selected after the refresh:

image

 

myapp.BrowseCustomers.Refresh_execute = function (screen) {
     var selectedEntity = screen.Customers.selectedItem;
     screen.Customers.refresh().done(function () {
         screen.Customers.selectedItem = selectedEntity;
     });
};

I start loving the promise library with which I  set back the selected item after the refresh completed.

Many thanks to Matt Evans for making me aware of the fact a refresh method exists, all over the place,  in the html client Glimlach