views:

50

answers:

3

2 Questions really, and I'm not sure if I'm doing this right or not...

I want to send back an array of some sort for an Entity object I created. I'm not really sure how to mark it for sending (what attributes are needed or whatever), and I'm not really sure how to send it back (IList, List, Collection, ICollection).

Ideally I'd love to be able to send back an ObservableCollection, but would that work if a client that wants to consume the service isn't in .NET?

[ServiceContract(Namespace = "http://www.tempuri.com/MyService",
                 ConfigurationName = "IMyService")]
public interface IMyServie
{
    [OperationContract(Action = "http://www.tempuri.com/MyService/GetUsers",
                       ReplyAction = "*")]
    [XmlSerializerFormat(SupportFaults = true)]
    GetUsersResponse GetUsers(GetUsersRequest request);
}

[MessageContract(IsWrapped = false)]
public sealed class GetUsersRequest
{
    public GetUsersRequest() { }
    public GetUsersRequest(Int32 record = -1)
    {
        Record = record;
    }

    [MessageBodyMember(Namespace = "", Order = 0)]
    public Int32 Record { get; private set; }

}

[MessageContract(IsWrapped = false)]
//[ServiceKnownType(??)]
public sealed class GetUsersResponse
{
    public GetUsersResponse() { }
    public GetUsersResponse(PersonEntity[] entities)
    {
        Entities = entities;
    }

    [MessageBodyMember(Namespace = "", Order = 1)]
    //[XmlElement(DataType = "??")]
    public PersonEntity[] Entities { get; private set; }
    //Should this have been some other type of array-type (Collection, List, etc?)
}

//Does this need any attributes besides Serializable?
[Serializable()]
public PersonEntity : AbstractEntity
{
    public PersonEntity() { }
    public PersonEntity(Int32 id = 0, String fname = "", String lname = "")
    {
        ID        = id;
        FirstName = fname;
        LastName  = lname;
    }

    public String FirstName { get; set; }
    public String LastName { get; set; }

    //Functionality (Clone, Clear, Default, Equals, etc) Removed...
}

[Serializable()]
public abstract class AbstractEntity : IEntity
{
    public Int32 ID { get; set; }

    //Abstracts or Implements some functionality...
}

public interface IEntity
{
    //Defines functionality requirements
}
A: 

The most inter-operable means would be to return an array of the complex type, whatever you decide that to be. My personal preference is to use a dedicated DTO object for transfer across the wire, rather than expose internal entities directly via the service.

Regarding ObservableCollection, I suggest you wrap your array in an ObservableCollection client-side rather than try to return ObservableCollection.

Keep in mind that ObservableCollection will not transmit changes back to the service; you're going to h ave to do those manually.

Randolpho
I was just seeing if I could skip the step of Array-To-ObservableCollection since the client is going to be WPF.
myermian
@myermian: you probably could -- `OC` is serializable, after all -- but I wouldn't. First, you'd get no benefit; the `OC` returned by the service wouldn't update if the service had new data, for example, and updates to it wouldn't propagate back to the service. Second, it would needlessly destroy any interop you might obtain. This may or may not be an issue for you, but it would always be an issue for me -- I like to keep my options open.
Randolpho
+1  A: 

DataContract is what you are looking for. For more details check this link

On Observable collection front, not sure why sending an array would be any different for you. Can you elaborate a bit more to help us understand this.

Vinay B R
Do you have to mark this DataContract on the parent Abstract class and the interface as well?
myermian
have the attribute on the derived class Personentity should be enough. since that is the only type that is exchanged over the channel
Vinay B R
A: 

When it comes to passing objects over the wire, you must think of data rather than behaviour. So as far as this is concerned, a List or IEnumerable or T[] would not differ and my preference would be array which is supported in all languages. Server should not know or make any unncessary assumption about the client (WPF, Windows forms, ...) and all you are passing is a collection of data so least prescriptive is the best: T[] (Array of T).

As myermian said, your ObservableCollection sent over the wire would not be working as an ObservableCollection on the client.

Also you are using MessageContract while not using any of its benefits of Body/Header. So you must use DataContract.

Aliostad