.NET RIA Services Exception handling

Note: This post is based on the July preview of the .NET RIA Services, so changes may happen in a future release of the framework

At the moment I’m updating a code example for my Silverlight 3.0 course and have added some exception handling to the code. I also got a question about how to handle exception while calling the Load operation of the DomainService class. So I decided to write a blog post about it, maybe someone more have the same question.

By default if you make a call to a DomainService query method, you will not get an exception on the client-side, if you don’t adding some extra code. Lets pretend that the following code is your DomainService and Query method:

public class MyDomainService : DomainService
      public IEnumerable<Customer> GetCustomers()
           //Code that can throw an exception;

The method above will throw an exception. If you on the client-side want to “call/use” the GetCustomers method, you will use the generated DomainContext class’s Load method:

var d = new MyDomainContext(); var loadOperation = d.Load<Customer>(d.GetCustomersQuery(), MyCallBack, null); LayoutRoot.DataContext = d.Customers;

When this code is executed, you will not get any exception, so the user or you may think that no exception have occurred. But that isn’t the case. So what I’m going to write about now, is different way you can check if an exception occurred (Wouldn’t it be nice if we only could get an exception instead of adding extra code to check if an exception is thrown ;)).

The LoadOperation class has two properties we can use, HasError and Error. To check if we got an exception we can use the HasError property, if we want to get information about an exception, we can use the Error property. The first example I’m going to use, will only display an exception for the client.

On the client-side I have a StackPanel called myErrorPanel, it also have a TextBlock where the Text property is bound to a property path “Error.Message”.

StackPanel x:Name="myErrorPanel"> <TextBlock Text="{Binding Path=Error.Message}"></TextBlock> </StackPanel>

In the code-behind we can now write the following code which will bound the LoadOperation to the myErrorPanel:

var d = new MyDomainContext(); var loadOperation = d.Load<Customer>(d.GetCustomersQuery()); LayoutRoot.DataContext = d.Customers; myErrorPanel.DataContext = loadOperation;

If the Load method of our DominContext has an error, the Error Message will be displayed for the User. By using this solution, we will not have any idea if an error has occurred during the Load operation, if it does it will only be shown for the User. The StackPanel will also take up some space on the user interface, so to solve it we can for example add a Converter, and bound the HasError to the StackPanel’s Visibility property. The following two other solution will instead show us, how we can use a callback method and the LoadOperation’s Complteted event to have a better control if an exception is thrown during the Load operation.

The DomainContext’s Load method can take a callback as an parameter, by using a callback, we will get a notification when the Load operation is completed, and we can also see if there was any error during the Load operation. The following code will use a callback and check if an error has occurred:

var d = new MyDomainContext(); var loadOperation = d.Load<Customer>(d.GetCustomersQuery(), MyCallBack, null); ... void MyCallBack(LoadOperation<Customer> loadOperation) { if (loadOperation.HasError) //Handle the error }

The following solution will use the LoadOptions’s Completed event to check if an error has occurred:

var d = new MyDomainContext(); var loadOperation = d.Load<Customer>(d.GetCustomersQuery()); loadOption.Completed += new EventHandler(loadOption_Completed); ... void loadOption_Completed(object sender, EventArgs e) { if (((LoadOperation)sender).HasError) //handle the error }

If you wonder what solution I prefer, it would be the one that uses a callback. I do want to see some changes to the .NET RIA Services Load operations, like specifying a callback just for handling exceptions, and a default generated callback added to the DominaContext, which will be called if no callback is used, by doing so, we could get an exception when the Load fails without adding some extra code.


Comments have been disabled for this content.