2

假设我有一个 RESTful API 用于管理使用HAL来促进 HATEOAS 的订单:

GET /orders/2
  {
    "_links": {
      "self": "/orders/2",
      "items": "/orders/2/items"
    },
    "subtotal": 30.0,
    "shipped": false
  }

我想使用一组接口来编写我的客户端(应用程序),这样,假设这些接口的实现是 DI-d/由 DI-d 工厂等构建的,我真的(想要)不必关心他们得到了我的 RESTful API 的支持。例如(伪 C#/Java):

public interface Order {
  public void addItem(Item item);
  public float getSubtotal();
  public boolean getShipped();
}

Order order = ...;
Item item = ...;
order.addItem(item);
...(order.getSubtotal())...;

我的问题是:我/从 API生成Order/接口的实现是否有意义?Item我的意思是与导出 WSDL 的 C#/web 服务提供的方式类似。

我一直在考虑实现OPTIONS诸如/orders和之类的资源,/orders/{id}这样我就可以有效地拥有一个 HATEOAS API 来遍历 API 的模式:

GET /orders/* (I'd need a suitable wildcard of course)
  {
    "_links": {
      "addItem": {
        "href": "/orders/{id}/items",
        "templated": true,
        "type": "method"
      }
    }
  }

当然,我可以_links使用任何给定的资源(/orders/2例如)返回对象的这一部分,但这会排除静态代码生成。

我想知道是否有一种明智的方法来封装这样一个事实,即如果提供了特定链接,则相关操作应该可用/执行,否则不可用。

注意:如果重要的话,我实际上是在使用 JavaScript(特别是使用 AngularJS)。但是,我仍然想使用一组概念接口/合同来编写我的应用程序。

4

1 回答 1

1

我的问题是:从 API 生成 Order/Item 接口的实现是否有意义?我的意思是与导出 WSDL 的 C#/web 服务提供的方式类似。

这部分是有道理的。通过一个简单的 CRUD API,您可以将资源映射到实体。对于复杂的应用程序,它不起作用,因为您将URIs 映射到resources 并将METHOD URI对映射到operations。所以每次如果你需要一个不是由 HTTP 定义的操作,你就必须为一个已经存在的资源创建一个新的资源或者至少一个新的 URI。

一些例子:

  • 将资金从一个帐户转移到另一个帐户:POST /transfer [acc1, acc2, amount, currency]-转移不必作为您的域逻辑中的实体存在(除非您想破产,否则不要在生产代码中尝试这种解决方案:D)
  • 向另一个用户发送电子邮件:POST /messages [recipient, message]
  • 您也可以将资源映射到值对象:GET /users/123/address
  • 您可以使用 URI 映射减少集合:GET /users?name="John"
  • 您可以使用PUT /users/123 [details]而不是POST /users [details]创建新用户
  • 您可以使用POST /player/123/xp/increment 10而不是PUT /player/123/xp [xp+10]更新玩家的经验值

关于类似 WSDL 的解决方案,您可以在此处阅读更多内容:第三代 Web API - Markus Lanthaler

我个人认为构建这样一个系统不值得努力,因为它弊大于利。

于 2013-10-06T11:46:20.103 回答