Silverlight has matured into a solid platform for developing and deploying line-of-business applications.
Just three short years have passed since Microsoft introduced Silverlight to the world. It was at Mix07 in Las Vegas where we all saw Silverlight, the new Microsoft Rich Internet Application (RIA) platform in its first version. Today, Silverlight has matured into a platform ready for building and maintaining business applications.
To “test” Silverlight’s capabilities and suitability for building LOB applications, we composed a short shopping list of typical business application requirements. We’ll see if Silverlight can fulfill these requirements.
What comes to mind when you consider business applications? Data is king. Silverlight applications run on the client side, inside the browser. Data lives in a database on the server side, however. Looking at the Silverlight namespaces and assemblies, it has no ADO.NET support, so it doesn’t support well-known features such as DataReaders or LINQ-To-SQL.
Also, Silverlight has no client-side database. In many cases, this wouldn’t be a solution either. You certainly wouldn’t want to inadvertently store a temporary copy of a database with sensitive information on a client’s machine.
The solution is simple: add a service layer on top of the database. You can use this service layer to connect to the database, preferably through a business layer. On the client side, Silverlight can then connect to these services and have access to the data (see Figure 1).
Figure 1 Silverlight can connect to services on the client side.
Silverlight supports ASMX, WCF and REST service types. You can also use Silverlight to consume more exotic types of services like sockets and net.tcp. This is good news if you’re adding Silverlight to an existing technology stack within your enterprise. The services from which Silverlight can get its data are the same ones you’d use for other application types.
Working with ASMX and WCF services is similar, from the Silverlight point of view. WCF should be your default choice if you’re implementing the service. Let’s look at a basic example of connecting to a WCF service. The first step is defining what the service does. This service returns a list of products:
[ServiceContract(Namespace = "")]
Once the service is ready, we can connect with Silverlight. To do so, add a service reference from Visual Studio (see Figure 2).
Figure 2 Use Visual Studio to add a service reference to Silverlight.
Visual Studio will now build a proxy class for us. You can consider a proxy class as a client-side copy of the service class, where the method implementations are replaced by a call to the service method. All service communication in Silverlight happens asynchronously. In the code example below, we’re using this proxy to get a list of products:
privatevoid button1_Click(object sender, RoutedEventArgs e)
OrderService.OrderServiceClient proxy = new OrderService.OrderServiceClient();
proxy.GetAllProductsCompleted += newEventHandler<OrderService.GetAllProductsCompletedEventArgs>(proxy_GetAllProductsCompleted);
void proxy_GetAllProductsCompleted(object sender, OrderService.GetAllProductsCompletedEventArgs e)
ProductGrid.ItemsSource = e.Result;
REST is currently a popular protocol because of its high adoption in Web 2.0 APIs like Facebook and Twitter. Silverlight fully supports it as well. Silverlight also has a specific service framework developed with n-tier Silverlight applications in mind: WCF RIA Services.
When creating a Silverlight application, you’ll typically get your data through a service layer. However, there’s no easy way out of the box to simply write your data transfer objects and classes—including validation, authentication/authorization—just once. Silverlight applications are built against a limited version of the Microsoft .NET Framework 4. Therefore, you can’t reference an assembly (for example, one containing your classes/validation logic) built against the full .NET Framework 4 in a Silverlight application.
This is where WCF RIA Services come in. These were created to simplify LOB RIA development. They address the complexity of building n-tier applications by providing a framework, controls and services on both the server side and the client side.
They let you write services linked to a data store on your server side. This can be a SQL Server Database, your own POCO classes or an Entity Model. It then regenerates these entities on your client. Next to that, it generates the necessary context, methods and operations on your client to easily talk to your services.
If you’re familiar with the Entity Framework, you’ll feel right at home. It actually lets you code in a similar way. For example, you may have a client-side DomainContext, which tracks change sets, contains lists of entities and lets you submit these changes. This “hides” the fact that you’re working through a service layer.
WCF RIA Services is essentially a server-side technology that projects code to a client. It also simplifies adding validation and authorization/authentication to your services and entities. It vastly reduces the development time you’ll have to spend building LOB Silverlight applications.
Silverlight has an extended control set containing simple controls such as Buttons, TextBoxes and ComboBoxes. It also has many more advanced controls like the DataGrid, the RichTextBox and the MediaElement in the default install package. With every new version, Microsoft adds more controls.
Microsoft has also created the Silverlight Control Toolkit. This is a set of extra controls, which are open source and available for free via CodePlex.com. This package is updated quite regularly and out-of-band with the regular Silverlight releases.
It includes many controls that can make your life as a Silverlight enterprise developer even easier. There are also charting controls, which can come in handy in our next requirement: reporting.
Printing is still an often-requested business requirement. Now with Silverlight 4, you can print directly from Silverlight. That API lets you indicate what you want to print, whether it’s the entire screen or dynamically generated content like a report. Therefore, it’s easy to create a reporting solution in Silverlight 4, in combination with the controls available from the toolkit, such as rich charts.
When working with Silverlight- or XAML-based applications, one important thing to consider is the way code should be written differently from how we’re used to coding in older technologies, like ASP.NET or Windows Forms. You can write code in the same manner, but you shouldn’t. You wouldn’t be using the full power of the technology that way.
Silverlight applications should rely heavily on DataContext, Data Binding and the Observer pattern. There should be no repetitive code to assign TextBox values to objects or vice versa. The more of that kind of code you have to write, the more likely you are to inject a bug in your code. You bind an object to UI elements, and the correct values are automatically made available through the object in code. Actually, you should never access UI elements directly.
This is where the Model-View-ViewModel (MVVM) design pattern comes in. This is often used to encourage separation of concerns (your code-behind contains little to no code). It lets you work on your application UI separately from the developer. It also makes for better code testability.
However, the most important advantage it offers is that it encourages developers to leverage the power of the DataContext and Data Binding technology. Your View has a ViewModel as DataContext, which contains all the data properties.
These properties are bound to the UI elements in the View through Data Binding. So the ViewModel essentially converts the data it gets from the Model (an object representation of your data) to data the View can use. You can think of a ViewModel as “a converter on steroids.”
Once this is in place, you’ll need a way to relay your events (such as a Button Click) to the ViewModel, instead of to the Views code-behind. You do this through commanding. Silverlight provides an ICommand interface, and you can bind UI Elements inheriting button base to Commands. These commands are defined on the ViewModel.
Next, you’ll need a way to communicate between different ViewModels, without them having reference to each other. You can do this through a broadcast/listen principle. ViewModel subscribers receive a certain type of message, while another ViewModel sends another message. You can take the necessary actions once you receive the message.
Last, you’ll need to make sure your View knows what its DataContext should be. There are different approaches—the View first approach (the View is instantiated by the application and is responsible for instantiating the ViewModel it needs) or the ViewModel first approach (the other way around). These often use an IoC container or the Managed Extensibility Framework (MEF) to replay responsibilities.
There are quite a few different implementations of MVVM. You could write your own, but in the open source community, there are great implementations already available, like the MVVM Light Toolkit, Caliburn or Prism.
As you can see, Silverlight is ready for building enterprise-grade applications. In fact, both of us do so on a daily basis.