ODATA中多级导航的正确Uri语法是什么?

时间:2014-02-18 05:42:33

标签: odata

我有一个ODATA服务MyService,其中包含客户,产品和类别,其中导航属性是从客户定义到产品,从产品定义到类别。

我对从客户到产品到类别的导航的正确形式感到困惑。

最初我给了MyService / Customers(1)/ Products(10)/ Categories,但它给了我一个错误。

然后我尝试了MyService / Customers(1)/ Products / Categories,它们正常工作。我在互联网上看到了许多我最初尝试过的uri形式的例子,但它对我不起作用。

任何人都可以解释一下吗?

2 个答案:

答案 0 :(得分:2)

URI的正确形式取决于导航属性Products的多样性。如果客户可以拥有多个产品,那么第一个表格是正确的。如果客户最多只能有一个产品,那么第二个表格是正确的。

也许在您的服务中,此导航属性的多重性设置不正确。

答案 1 :(得分:0)

<块引用>

使用括号指定资源键表示这是一个 OData v4 主题。

根据规范 OData v4: 4.3.3 URLs for Related Entities with Referential Constraints,只要 Porducts 是集合类型,您的语法就是合规的。

<块引用>

包括未来相关资源的相关 $metadata 以解决这种歧义。

如果您的第二种形式的 URL 有效,则通常表明 Products 导航属性的多重性是单一的,使其不再是一个集合,因此您无法按 .在这种情况下,如上所述,您可以使用 $filter 查询选项,但您也可以直接查询 Categories 控制器。


即使语法符合要求并且资源导航到 Products IS 是一个集合,但在许多实现中,这种类型的导航特性不受支持。也许是因为它是不必要的,但也可能是因为它在意图方面是一个灰色区域,因此代码框架默认情况下很难在该区域强制执行路由约定或规则。

例如,这个查询应该由 Customers 控制器评估,但返回 Category 资源的集合,还是应该由 Products 控制器评估以返回一个集合Category 资源?如果 Category 控制器是返回和查询 Category 资源的控制器,而不是潜在地向所有 Customer 添加相同的支持,那么设计底层控制器不是更容易吗? ,ProductCategory 控制器?

鉴于 10唯一键已提供给预期的 Product 资源返回,Customer 1 无关紧要。

如果您想故意返回一个 keyProduct10 资源,但仅当它属于 {{1 }} 的 keyCustomer 那么您还可以以下列形式指定该查询:

1

或者您可以直接查询类别控制器:

~/MyService/Products(10)/Categories?$filter=Product/CustomerFK eq 1
~/MyService/Products(10)/Categories?$filter=Product/Customer/PK eq 1

虽然服务作者可以选择支持多级导航,如规范建议和 OP 所尝试的那样,但它并不总是开箱即用,因此我们往往完全忘记实现它.这并不总是很难做到,通常我们只需要实现一些简单的路由,但由于解释和实现的可变性,我个人只支持导航 1 级深度但不允许 key 选择器在子级。

如果您查询的服务不支持它,那么只需直接通过 ~/MyService/Categories?$filter=Products/any(p:p/Customer/PK eq 1 and p/Category/PK eq 10) 或通过带有适当过滤器的 Category 控制器间接定位 Cateogry 资源。