ASP.NET Web API IQueryable <t> challenge </t>

时间:2012-04-11 20:51:58

标签: asp.net-web-api

我想在我的控制器中使用以下模式:

  

API / {控制器} / {ID} / {收集}

示例: api / customers / 123 / addresses

但我想从相应的Get操作返回IQueryable Of T。我想要这样的东西(简化):

public IQueryable<????> GetCollection(int id, string collection)  
{  
    switch(collection)  
    {  
        case "addresses":  
            return _addresses.AsQueryable();  
            break;  
        case "orders":  
            return _orders.AsQueryable();  
            break;  
        default:  
            throw new Exception(NotSupported);  
    }  
}   

这可以吗?
推荐的方法是什么?

3 个答案:

答案 0 :(得分:6)

@SLacks是正确的,如果可以,您应该返回IQueryable<object>IQueryable<someBaseType>

您获得的错误是DataContract Serializer的功能。所以你有几个选择。

  1. 切换到支持您想要的备用xml serlializer。
  2. 切换到绕过有问题的序列化程序的输出形式(比如说使用JSON.net的JSON)
  3. 使用
  4. 教授数据合同序列化程序如何序列化对象

    对于“教学”选项,您可以通过两种方式进行教学。

    (A)利用[KnownType(typeof(...))]属性。这是a post on the KnownType attribute。这是为WCF,但应该让你开始。

    (B)使用数据合约解析程序。这post should get you started

答案 1 :(得分:3)

扩展@Ebarr所说的,实现此目的的最简单方法是更新您希望能够以这种方式返回的各种类,并让它们从公共基类或接口继承。

示例:

[KnownType(typeof(Address))]
[KnownType(typeof(Order))]
public abstract class _BaseObject { }

public partial class Address : _BaseObject { }
public partial class Order : _BaseObject { }

现在您可以使用您的控制器方法:

public IQueryable<_BaseObject> GetCollection(int id, string collection) {  
    switch(collection) {  
        case "addresses":  
            return _addresses.AsQueryable();
        case "orders":  
            return _orders.AsQueryable();
        default:  
            throw new NotSupportedException();  
    }  
}

请注意,[KnownType]属性位于System.Runtime.Serialization。您还应该知道,此方法将完全符合您对JSON序列化的期望 - 但XML序列化通常会生成将对象显示为基类的标记(因为这就是你回来了)而不是子类。

答案 2 :(得分:0)

只需返回非通用IQueryableIQueryable<object>通过协方差。