WCF 数据契约和多态性

发布于 2024-10-31 17:52:56 字数 1478 浏览 0 评论 0原文

这就是我想做的。这(理论上)应该非常简单。

假设我有一个包含以下代码(基本功能)的 WCF 服务:

<DataContract()>
Public Class BaseObj
    <DataMember()>
    Public ID As Integer
End Class


<DataContract()>
Public Class TestObj1
    Inherits BaseObj

    Public Sub New(ByVal idval As Integer)
        ID = idval
    End Sub

End Class


<DataContract()>
Public Class TestObj2
    Inherits BaseObj

    Public Sub New(ByVal idval As Integer)
        ID = idval
    End Sub

    <DataMember()>
    Public DoNotShow As String = "fail"

End Class

这是我要编写的代码:

<WebInvoke(Method:="GET", ResponseFormat:=WebMessageFormat.Json, UriTemplate:="Test?reqReportID={reqReportID}")>
Public Function GetCollection(ByVal reqReportID As Integer) As List(Of BaseObj)

    Dim myObjs as New List(Of BaseObj)
    myObjs.add(new TestObj1(1))
    myObjs.add(new TestObj2(2))
    return myObjs

End Function

我希望 JSON 响应看起来完全像这样: [{"ID":1},{" ID":2}]

现在,我当前的代码返回一个空响应(没有抛出错误,没有传递任何信息)。我可以通过这样做来让它返回一些东西:

<DataContract(), KnownType(GetType(TestObj1)), KnownType(GetType(TestObj2))>
Public Class BaseObj
    <DataMember()>
    Public ID As Integer
End Class

但是,响应向 JSON 对象添加了“__type”,并且还向 JSON 对象添加了“DoNotShow”(这不是一件好事)。

这里的问题是我不想传递每个对象唯一的信息。我只想要通过基类为每个对象所共有的信息。我无能为力改变它,除非我遗漏了一些东西,否则 WCF 的作者在创建它时似乎对 OO 编程有一种非常粗鄙的看法。

如果您对 SO 有任何见解,我们将不胜感激。

Here's what I want to do. This should (theoretically) be very simple.

Say I have a WCF service with the following code (bare bones functionality):

<DataContract()>
Public Class BaseObj
    <DataMember()>
    Public ID As Integer
End Class


<DataContract()>
Public Class TestObj1
    Inherits BaseObj

    Public Sub New(ByVal idval As Integer)
        ID = idval
    End Sub

End Class


<DataContract()>
Public Class TestObj2
    Inherits BaseObj

    Public Sub New(ByVal idval As Integer)
        ID = idval
    End Sub

    <DataMember()>
    Public DoNotShow As String = "fail"

End Class

Here is the code I want to write:

<WebInvoke(Method:="GET", ResponseFormat:=WebMessageFormat.Json, UriTemplate:="Test?reqReportID={reqReportID}")>
Public Function GetCollection(ByVal reqReportID As Integer) As List(Of BaseObj)

    Dim myObjs as New List(Of BaseObj)
    myObjs.add(new TestObj1(1))
    myObjs.add(new TestObj2(2))
    return myObjs

End Function

I want the JSON response to look exactly like this: [{"ID":1},{"ID":2}]

Now the code that I have currently returns an empty response (no error thrown, no information passed). I can get it to return something by doing this:

<DataContract(), KnownType(GetType(TestObj1)), KnownType(GetType(TestObj2))>
Public Class BaseObj
    <DataMember()>
    Public ID As Integer
End Class

However the response adds a "__type" to the JSON object, and also adds "DoNotShow" to the JSON object (not a good thing).

The problem here is that I do not want to pass information that is unique to each object. I only want information that is common to each object through the base class. Nothing I can do will change it, and unless I am missing something, it seems as though the authors of WCF had a very bassackwards view of OO programming when they created this.

Any insight you here at SO might have would be greatly appreciated.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

鹿港巷口少年归 2024-11-07 17:52:56

出于好奇,为什么这很重要?通过您给出的示例,我不确定我是否理解了它的重要性。

我立即想到的一个选择是从 TestObj1 继承 TestObj2。然后我会去掉knowntype(gettype(testobj2))。

如果您想动态添加已知类型,那么您应该自己调用 datacontractjsonserializer。

http://msdn.microsoft.com/en -us/library/system.runtime.serialization.json.datacontractjsonserializer.aspx

编辑:这将在客户端产生两个 TestObj1 对象。不确定您是否想要这种行为。

Out of curiosity, why does it matter? With the example you gave I'm not sure I'm following the why it's important.

One option I have off of the top of my head is to inherit TestObj2 from TestObj1. Then I would take off the knowntype(gettype(testobj2)).

If you want to dynamically add known types then you should call the datacontractjsonserializer yourself.

http://msdn.microsoft.com/en-us/library/system.runtime.serialization.json.datacontractjsonserializer.aspx

Edit: this will result in two TestObj1 objects on the client side. Not sure if you want that behavior.

裸钻 2024-11-07 17:52:56

如果您的集合仅输入到 BaseObj,我认为序列化程序不可能生成您正在寻找的 JSON。

如果它只是生成 [{"ID":1},{"ID":2}],则接收者无法区分类型。另一端如何确定第一个对象的类型为 TestObj1 而第二个对象的类型为 TestObj2?

If your collection is only typed to BaseObj I don't think it's possible for the serializer to produce the JSON you are looking for.

If it were to simply produce [{"ID":1},{"ID":2}], there is no way for the recipient to distinguish between the types. How would the other end determine that the first object is of type TestObj1 but the second object is of type TestObj2?

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文