locked
Consuming Service Operations Recommendation RRS feed

  • Question

  • I have been following this thread, and would like some guidance on how best to handle Service Operations in the client.

    http://social.msdn.microsoft.com/Forums/en-US/adodotnetdataservices/thread/86576348-f29c-418a-81b3-adb59a84fa3e

    I have a client application that would like to filter Entities exposed via WCF Data Services on none key fields. To do this I will populate drop down boxes, then compose a query based on the values selected.

    I will populate one box from a distinct list of ItemNames. I can do this a couple of different ways. Keep in mind Distinct is not supported by OData.

    1. Create a view in the database that will select distinct ItemNames from Items. Then create an Entity from this view.

    2. Create a Service Operaton that would return an IQueryable<string> of (from i in Items select i.ItemName).Distinct();. I cannot find a simple way to call this operation on the client, so I use WebClient and get an IQueryable<string>.

    3. The suggestion in the link above is to hand craft a URL, then execute that.

    Are any of these prefered? Is there a better way?

    Thanks,

    Beezler

    Monday, March 22, 2010 3:31 PM

Answers

  • Hi,

    I'm sorry, I was wrong. Unfortunately (as I learned right now) our client can't handle materialization of collections of simple types (like strings). So even though the service operation on the server works just fine, the client doesn't provide a nice way to read it.

    The sample in the forum thread you meantion above is probably the simplest way of doing this for now.

    I'm sorry for the confusion...


    Vitek Karas [MSFT]
    • Marked as answer by Beezler Thursday, March 25, 2010 5:21 PM
    Monday, March 22, 2010 9:22 PM
    Moderator

All replies

  • Hi,

    The suggestion would be to create a service operation which returns IEnumerable<string>  (IQueryable<string> since string is not an entity will be treated as IEnumerable anyway).

    On the client, construct the URL by hand (this is rather simple if you service operation has no parameters, something like new Uri(ctx.BaseUri, "ServiceOperationName") ). Use ctx.Execute<string> to get IEnumerable<string> on the client (or the async version of this). Eve if we would support service operations directly on the client it would do pretty much exactly this.

    Thanks,


    Vitek Karas [MSFT]
    Monday, March 22, 2010 5:09 PM
    Moderator
  • Pretty straight forward. When I instantiate my

    Uri uri = new Uri(ctx.BaseUri, "ServOpName");

    When I look at the uri, I see that there is now Service1.svc in the Uri. The URL I would have expected is http://localhost:####/MyFolder/MyService.svc/ServOpName, but I get http://localhost:####/MyFolder/ServOpName.

    Is there an explanation for this?

    Thanks,

    Monday, March 22, 2010 7:39 PM
  • The easiest way to fix this is in your context constructor where you specify the service URI just append '/' at the end.

    Thanks,


    Vitek Karas [MSFT]
    Monday, March 22, 2010 7:49 PM
    Moderator
  • Constructing the URI myself, I am getting an error "Error processing response stream. The XML element contains mixed content." which I find this link when I googled it

     http://social.msdn.microsoft.com/Forums/en/adodotnetdataservices/thread/7c71eff7-4951-480f-bbc1-b00046ee788b 

    This indicates that this method may not work since I am expecting an IEnumerable<string> as a result set.

     

    I'll try the backslash as well.

    Monday, March 22, 2010 7:56 PM
  • Hi,

    I'm sorry, I was wrong. Unfortunately (as I learned right now) our client can't handle materialization of collections of simple types (like strings). So even though the service operation on the server works just fine, the client doesn't provide a nice way to read it.

    The sample in the forum thread you meantion above is probably the simplest way of doing this for now.

    I'm sorry for the confusion...


    Vitek Karas [MSFT]
    • Marked as answer by Beezler Thursday, March 25, 2010 5:21 PM
    Monday, March 22, 2010 9:22 PM
    Moderator
  • If the DS client cannot materialize calls to service operations that expose collections of primitive types, why is there sample code for it in the documentation here ???


    Dick Page


    • Edited by dickP Friday, July 13, 2012 11:17 AM
    Friday, July 13, 2012 11:13 AM
  • The sample shows how to consume a service operation which returns a singleton primitive or complex result. The client can't consume service operations which return collection of primitive or complex types just yet.

    The sample is a bit confusing because the Execute returns IEnumerable even for singleton service operations, but that enumeration will have just one item in it. So the foreach over it will only ever return one item.

    Thanks,


    Vitek Karas [MSFT]

    Monday, July 16, 2012 2:33 PM
    Moderator