Any sample on how to use WCF RIA Services in XAML

2020-03-31 04:18发布

I wonder if someone have tried using WCF RIA Services in XAML based metro application. If you have any blog or sample please share.

1条回答
Viruses.
2楼-- · 2020-03-31 05:02

As a matter of fact I did and here's the trick :)

I added a "Service Reference" to my WCF service exposing an ADO.NET Entity Framework model. The problem is that in a XAML/C# Metro app, executing the following code fails:

SampleEntities ctx = ((App)Application.Current).Context;
var query = from p in ctx.Products
              where p.Name == name
              select p;

foreach (Product p in query) /** this line fails **/
{
    // do stuff
}

Here's the exception you'll get at runtime:

"Silverlight does not enable you to directly enumerate over a data service query. This is because enumeration automatically sends a synchronous request to the data service. Because Silverlight only supports asynchronous operations, you must instead call the BeginExecute and EndExecute methods to obtain a query result that supports enumeration."} [System.NotSupportedException]: {"Silverlight does not enable you to directly enumerate over a data service query. This is because enumeration automatically sends a synchronous request to the data service. Because Silverlight only supports asynchronous operations, you must instead call the BeginExecute and EndExecute methods to obtain a query result that supports enumeration."

Ahhh, this would have been too good to be true!

As stated in the exception, you need your server calls to be asynchronous, just as in Silverlight.

Here's a sample of how you can consume a WCF RIA Service in a C# Metro App doing it the old school way:

(...)
var query = from p in ctx.Products
            where p.Name == Name
            select p;

((DataServiceQuery<Product>)query).BeginExecute(OnLoadItemsCompleted, query);
(...)

private void OnLoadItemsCompleted(IAsyncResult result)
{
    var query = result.AsyncState as DataServiceQuery<Product>;
    IEnumerable<Product> response = query.EndExecute(result);

    foreach (Product o in response)
    {
         // Do stuff
    }
}

Now using .NET 4.5 and its new await & async keywords, you can get the same result whilst avoiding your code to be chunked with all those little callback methods.

Example:

async void GetProducts()
{
    SampleEntities ctx = ((App)Application.Current).Context;
    var query = from p in ctx.Products
                  where p.Name == name
                  select p;
    DataServiceQuery<Product> dqs = (DataServiceQuery<Product>)(query);
    TaskFactory<IEnumerable<Product>> tf = new TaskFactory<IEnumerable<Product>>();
    myListView.ItemsSource = await tf.FromAsync(dqs.BeginExecute(null, null), 
                               iar => dqs.EndExecute(iar));
}

Using either of the last two methods worked fine for me :)

查看更多
登录 后发表回答