RIA Services in .NET – A Closer Look

Posted: March 7, 2010 in .NET, WCF
Tags: , ,

The RIA Services provides a mechanism of exposing data and business logic for consumption by the Rich Internet Applications like Silverlight.These are basically WCF services with some additional plumbing which makes it very easy to develop and consume service from Silverlight applications.Since these are basically WCF services they can be  consumed from other types of applications like ASP.NET/WinForms/WPF as well.

Normally we follow the following steps to create a RIA Service quickly:

  1. Create a Silverlight Application in VS 2008 with a linked Web Application.Make sure that “Enable RIA Services” option is checked.
  2. Create the data model using ADO.NET Entity Data Model template
  3. Add a DomainService class in the Web Application using the DomainService template.
  4. Compile the Web Application and generate the client access code
  5. Use the service in your Silverlight application.

This works fine and explained in more details at http://msdn.microsoft.com/en-us/library/ee707376%28VS.91%29.aspx

But by following these steps it was not very clear to me how WCF is coming into the picture and how internally the message flow was working.So I took a bit different route and tried to avoid using the DomainService item template coming in VS 2008.

  • I created a Silverlight application with linked Web Application and “Enable RIA Services” option checked as shown below:

ria1

  • Then I added a class as shown below:
namespace RIADemoApp.Web
{
  public class Employee
  {
     public string ID { get; set; }
     public string FirstName { get; set; }
     public string LastName { get; set; }
     public string PhoneNumber { get; set; }
  }
}

This is my Entity class ( a bit oversimplified sample :-))

  • I added another class as shown below:
namespace RIADemoApp.Web
{
     using System;
     using System.Collections.Generic;
     using System.Linq;
     using System.Web.DomainServices;
     using System.Web.Ria;
     public class EmployeeDomainServices : DomainService
     {
        public List<Employee> GetEmployees()
        {
            return new List<Employee>
                       {
                        new Employee(){ID="1",FirstName="John",
                        LastName="Doe",PhoneNumber="8888888888"},
                        new Employee(){ID="2",FirstName="Sherlock",
                        LastName="Holmes",PhoneNumber="3888888888"},
                        new Employee(){ID="3",FirstName="James",
                        LastName="Bond",PhoneNumber="4888888888"},
                        new Employee(){ID="4",FirstName="Robert",
                        LastName="Blake",PhoneNumber="5888888888"},
                    };
         }
    }
}

This is my DomainService class and it inherits from System.Web.DomainServices.DomainService class which is the base class for all DomainService implementations.

  • Now I compiled the code and found a file has been generated in the /Generated_Code folder of the Silverlight application.But this file contains only one class WebContext which inherits from System.Windows.Ria.WebContextBase.But this is the base class which provides a context within which all the application services are made available to the Silverlight app code.But I cannot see any code here which makes some calls to any remote service.So what needs to be done?
  • Here comes the attribute System.Web.Ria.EnableClientAccessAttribute.This attribute indicates that the domain service will be accessible by clients.So I applied this attribute.
namespace RIADemoApp.Web
{
    .................
    using System.Web.Ria;
    [EnableClientAccess()]
    public class EmployeeDomainServices : DomainService
    {
        public List<Employee> GetEmployees()
        {
            return new List<Employee>
            {
             ..........................................

            };
        }
    }
}

  • One compiling the code I got the following error:

The entity ‘RIADemoApp.Web.Employee’ does not have a key defined. Entities exposed by DomainService operations must have at least one property marked with the KeyAttribute

  • So I had to add the System.ComponentModel.DataAnnotations.KeyAttribute attribute to the ID field of Employee class.After compiling the code the following classes got generated in Generated_Code folder.
    • Employee class which inherits from System.Windows.Ria.Entity , a base entity class for all RIA service clients.This class also contains the Employee class properties as DataMembers marked with System.Runtime.Serialization.DataMemberAttribute as shown below
    [DataMember()]
    public string FirstName
    {
        get
        {
            return this._firstName;
        }
        set
        {
            if ((this._firstName != value))
            {
              ......
    
                      }
                  }
              }
    
    

    We need DataMembers to serialize data to be sent to WCF service.It seems we are in the right direction.

      • EmployeeDomainServices class which inherits from System.Windows.Ria.DomainContext class.DomainContext provides a stateful representation of the domain service in the client side.Within this class there is a ServiceContract definition as shown below:
    [ServiceContract()]
    public interface IEmployeeDomainServicesContract
    {
        [FaultContract(typeof(DomainServiceFault), .....]
        [OperationContract(AsyncPattern=true, ......]
        IAsyncResult BeginGetEmployees(AsyncCallback callback, object asyncState);
        QueryResult<Employee> EndGetEmployees(IAsyncResult result);
        [FaultContract(typeof(DomainServiceFault), ....]
        [OperationContract(AsyncPattern=true,...]
        IAsyncResult BeginSubmitChanges(IEnumerable<ChangeSetEntry> changeSet, AsyncCallback callback, object asyncState);
        IEnumerable<ChangeSetEntry> EndSubmitChanges(IAsyncResult result);
    } 
    

    Interesting thing to note here is, all the definitions of the methods are for the asynch call only.

      • So ServiceContract is found and DataMembers.But where is the service URL and where from service call made??This is found in the constructor as shown below. The service url follows the pattern namespace-classname.svc.The class System.Windows.Ria.Services class is the WCF client implementation for domain services.
        public EmployeeDomainServices() : 
                       this(new WebDomainClient<IEmployeeDomainServicesContract>(new Uri("RIADemoApp-Web-EmployeeDomainServices.svc", UriKind.Relative)))
               {
               } 
        
    • We had to put some code in the Silverlight app to show the data as well:
    public partial class MainPage : UserControl
       {
           private EmployeeDomainServices  _context
               = new EmployeeDomainServices();
           public MainPage()
           {
               InitializeComponent(); 
    
               LoadOperation<Employee> loadOp = this._context.Load(this._context.GetEmployeesQuery());
               EmployeeGrid.ItemsSource = loadOp.Entities;
           }
       } 
    
    
    
    • But still there is one thing missing.There is no physical file with .svc extension.We need some intercepting HttpModule which will make use of a virtual path provider and activate the service.This is done by the System.Web.Ria.Services.DomainServiceHttpModule class and we need to add this HttpModule in web.config.

    Now this sample is usable, up & running.

    ria2

    About these ads
Comments
  1. RIA Services in .NET – A Closer Look « Sankarsan’s Journal…

    Thank you for submitting this cool story – Trackback from DotNetShoutout…

  2. RIA Services in .NET – A Closer Look « Sankarsan’s Journal…

    Thank you for submitting this cool story – Trackback from Servefault.com…

  3. RIA Services in .NET – A Closer Look « Sankarsan’s Journal…

    Thank you for submitting this cool story – Trackback from PimpThisBlog.com…

  4. RIA Services in .NET ? A Closer Look…

    Thank you for submitting this cool story – Trackback from iAwaaz-News-for-the-People-by-the-People…

  5. My coder is trying to persuade me to move
    to .net from PHP. I have always disliked the idea because of the costs.
    But he’s tryiong none the less. I’ve been using WordPress on a number of
    websites for about a year and am concerned about switching to another platform.
    I have heard great things about blogengine.
    net. Is there a way I can transfer all my wordpress content into it?
    Any help would be greatly appreciated!

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s