Microsoft.OData.Core无法反序列化NavigationProperty的$ expand响应?

时间:2018-02-09 03:05:19

标签: c# asp.net asp.net-web-api odata

我正在使用Microsoft ASP.NET Web API 2.2 for OData v4。由于edmx中的循环引用,我不能使用ODataConventionModelBuilder,所以我使用ODataModelBuilder。

我的一个实体类型具有可选的NavigationProperty,可以像这样添加

var item = builder.EntityType<API.Item>();
...
item.HasOptional(a => a.Customer);

这会产生以下$元数据

<EntityType Name="Item">
...
<NavigationProperty Name="Customer" Type="XXX.API.Customer" />
...

浏览器当然在获取odata / Items的$ expand结果方面没有问题?$ expand = Customer 像这样

{"@odata.context":"http://localhost:5404/odata/$metadata#Items","value":
[
  {"ItemId":15, ... "Customer":{"CustomerId":5,...}}
  ...
]

然而,当涉及到使用

的客户端C#应用程序时
Microsoft.OData.Client.DataServiceQuery<Item> _items;
...
_items.Expand(i => i.Customer)

失败,出现以下异常:

编写JSON响应时,必须指定用户模型,并且必须将实体集和实体类型传递给ODataMessageWriter.CreateODataEntryWriter方法,或者必须在正在写入的ODataEntry或ODataFeed上设置ODataFeedAndEntrySerializationInfo。

但是,如果我将服务器型号更改为

var item = builder.EntityType<API.Item>();
...
item.ContainsOptional(a => a.Customer);

导致以下$元数据

<EntityType Name="Item">
...
<NavigationProperty Name="Customer" Type="XXX.API.Customer" ContainsTarget="true"/>
...

以下回复(注意第二个@ odata.context)

{"@odata.context":"http://localhost:5404/odata/$metadata#Items","value":
[
  {
    "ItemId":15, ... 
    "Customer@odata.context": "http://localhost:5404/odata/$metadata#Items(15)/Customer/$entity", 
    "Customer":{"CustomerId":5,...}}
  ...
]

客户端代码很好。展开就像魅力一样。

所以,正如我想的那样,这是因为第二个@ odata.context描述了嵌套对象。 当然,我可以使用ContainsOptional作为解决方法,但这似乎不适合做,因为“item”不包含“customer” - 它们在业务逻辑中是独立的。

这是OData核心库中的错误吗?或者,有没有办法强制Web API将@ odata.context包含在HasOptional属性中?

编辑:我已检查过最新版本7.4.0,现在它提供了稍微不同的错误:“无法计算ID,因为导航源”客户“无法解析为从模型中设置的已知实体。“但基本上,它是一样的。

1 个答案:

答案 0 :(得分:0)

最后,我已经从MS客户端库切换到Simple OData Client https://github.com/object/Simple.OData.Client - 这是一种更容易使用的方式。