我对Asp.NET MVC控制器在设计服务时的工作方式非常满意。 但是新的WebAPI控制器。我该怎么设计我的服务?
让我们说我们有3种不同的方式列出,例如用户。
获取最新信息,获取所有信息,获取无效状态或其他信息。
这些都不需要参数。那你将如何在WebAPI中解决这个问题
IEnumerable<User> Get10Latest()
IEnumerable<User> GetAll()
IEnumerable<User> GetInactive()
由于它们具有相同的param签名,因此无效。 那么在这里设计这个的正确方法是什么?
答案 0 :(得分:1)
通过使用action参数,您可以在一个控制器中为单个HTTP方法支持多种方法 E.g。
public class UsersController : ApiController
{
[ActionName("All")]
public HttpResponseMessage GetAll()
{
return new HttpResponseMessage();
}
[ActionName("MostIQ")]
public HttpResponseMessage GetMostIQ()
{
return new HttpResponseMessage();
}
[ActionName("TenLatest")]
public HttpResponseMessage GetTenLatest()
{
return new HttpResponseMessage();
}
}
不幸的是,我还没有办法让一个控制器同时处理和不处理动作。
e.g。
public class UsersController : ApiController
{
[ActionName("")] // Removing this attribute doesn't help
public HttpResponseMessage Get()
{
return new HttpResponseMessage();
}
[ActionName("All")]
public HttpResponseMessage GetAll()
{
return new HttpResponseMessage();
}
[ActionName("MostIQ")]
public HttpResponseMessage GetMostIQ()
{
return new HttpResponseMessage();
}
[ActionName("TenLatest")]
public HttpResponseMessage GetTenLatest()
{
return new HttpResponseMessage();
}
}
能够将单个控制器用于集合资源及其所有子集都很不错。
答案 1 :(得分:0)
有人可能会继续为此包裹我,但你需要配置你的路由以处理获取。这就是我使用上述操作的方法:
config.Routes.MapHttpRoute(
name: "CustomApi",
routeTemplate: "api/{controller}/{action}",
defaults: new { id = RouteParameter.Optional }
);
所以现在你的请求被映射到正确的控制器 - &gt;通过路线模板行动。请注意,需要首先在WebApiConfig.cs中注册新路由。如果你保留旧的,默认的。
修改
重新阅读这个问题,我意识到我并没有完全回答设计问题。我认为从REST的角度来看,一种方法是使用一个单独的资源来公开正确的集合(例如Get10Latest),因为我认为有一个商业原因可以通过公开数据的确切子集服务。在这种情况下,您将通过其自己的Controller中的单个Get公开该资源(如果这是所需的行为)。
答案 2 :(得分:0)
为什么没有这样的网址:
GET /users
GET /users/latest
GET /users/inactive
使用路由可以将它们路由到
public classs UserController : ApiController
{
public IEnumerable<User> Get(string mode)
{
// mode is in routing restricted to be either empty, latest, or inactive
}
}
否则使用多个控制器。在Web API中使用动作名称是一种错误的方式。