我计划构建多个服务端点,例如这些端点,以便更新多个实体项目。
/api/order(orderInfo) [httppost]
/api/orderChangeCurrency(orderCurrency) [httppost]
/api/orderChangeClientName(orderClientName) [httppost]
public class orderInfo()
{
public int orderID {get;set;}
public int orderType {get;set;}
}
public class orderCurrency()
{
public int orderID {get;set;}
public int currencyID {get;set;}
}
public class orderClientName()
{
public int orderID {get;set;}
public string firstName{get;set;}
public stringlastName{get;set;}
}
但是我想到了一个单一的终点而不是全部
/api/order(orderExtendedInfo) [httppost]
public class orderExtendedInfo()
{
public int orderID {get;set;}
public orderInfo? OrderInfo{get;set;}
public orderCurrency? OrderCurrency{get;set;}
public orderClientName? OrderClientName{get;set;}
}
在这种情况下,我会有一个业务逻辑,可以根据提供的信息更新实体(无论是否为空值)。
在这种特定情况下,是否存在针对API端点的推荐做法或规则?
答案 0 :(得分:3)
嗯,这是一个相当广泛的问题,可能更适合http://programmers.stackexchange.com,但无论如何我都会放弃一些考虑。
首先,您的API设计应针对您的API用户。如果您的API是面向公众的API,您可以考虑使用REST。它是一种广泛使用(和辩论)的建筑风格,很多程序员都习惯这种风格。有关设计RESTful API的非常有用的建议列表可以是found here
其次,您应该考虑API的可消费性。以您的设计为例:消费者逐个更新实体是否合乎逻辑,或者一次更新一个或多个甚至所有实体更合乎逻辑?
第三,您必须考虑数据库事务。当所有实体都应该在一个原子操作中更新时,你就不能提供三个端点。
就个人而言,我非常喜欢REST,所以我很乐意为你的用例提供一个例子。
示例强>
首先让我介绍一个新实体:
public class OrderLine
{
public int Id {get;set;}
public int OrderId {get;set;}
public int ProductId {get;set;}
public int Quantity {get;set;}
public decimal Price {get;set;}
}
端点
POST /api/orders # creates a new order
GET /api/orders # gets all orders
GET /api/orders/1 # gets order 1
POST /api/orders/1/orderlines # creates a new order line for order 1.
GET /api/orders/1/orderlines/1 # gets order line 1 of order 1
GET /api/orderlines/{id} # gets order line 1
如果您需要在一次操作中更新多个实体,您可以这样做:
为更新创建模型:
public class EditOrder
{
public int orderID {get;set;}
public int orderType {get;set;}
public int currencyID {get;set;}
public string firstName{get;set;}
public string lastName{get;set;}
}
然后使用此端点
PUT /api/orders/1
这个方法
public IHttpActionResult Put(int id, EditOrder editOrder)
{
// retrieve current Order, OrderCurrency and OrderClient
// update the entities
// save entities
}
答案 1 :(得分:1)
我认为你应该在Business Layer中实现一个Controller动作方法和三个方法,就像这样
[HttpPost]
[Route("api/order")]
public async Task<IHttpActionResult> SubmitOrder(OrderExtendedInfo info)
{
var bl = new BusinessLayer();
if(info.orderInfo.HasValue)
{
bl.UpdateOrderInfo(orderInfo);
}
if(info.orderCurrency.HasValue)
{
bl.UpdateOrderCurrency(orderCurrency);
}
if(info.orderClientName.HasValue)
{
bl.UpdateOrderClientName(orderClientName);
}
}