在哪里放置控制器hepler方法,以在建筑时与设计模式保持和谐.NET核心Api



我刚开始构建API,现在我正在尝试构建我的第一个应用程序。我希望使我的应用程序的体系结构尽可能符合设计模式。我有一个服务层,服务被注入控制器,并负责与存储库的通信。我想拆分控制器中的一些逻辑,使代码更加干净。举个例子,我有一个控制器:

[ApiController]
[Route("api/[controller]")]
public class UsersController : ControllerBase
{
private readonly IUserService _userService;
public UsersController(IUserService userService) : base()
{
this._userService = userService;
}
[HttpPost("authenticate")]
public async Task<IActionResult> AuthenticateUserAsync(AuthenticationDTO authentication)
{
var user = await _userService.AuthenticateUserAsync(authentication.Username, authentication.Password);
var tokenString = .....
}
...
} 

我想创建一个负责生成身份验证令牌的方法。我必须在哪里找到这样的逻辑?我应该把它放在UserService中,还是写在UsersController类中?我可以在控制器类中编写私有方法吗?或者控制器应该只包含通过api接口公开的方法?

Rest Api-在资源中思考

这个问题是关于你对rest api的思考方式(如果你正在构建一个(。rest api、web api和SOAP之间存在差异,但我假设您正在构建一个rest api。

在使用通用web api的情况下,您必须决定如何将应用程序分解为多个控制器。

查看Microsoft Rest Api指南。其中最重要的部分是:

围绕资源组织API

因此,在您的示例中,让我们假设您的资源是用户会话。然后,您可以有一个带有适当谓词的UserController,在其中您可以创建(POST(更新(PUT/PATCH(删除(Delete(或检索(GET(User资源。

现在你需要一个会议,不是吗?或者代币。简单:

TokenController,操作当然是(POST(-使用用户名和密码创建令牌

SessionController-创建令牌。

这样,您将尽量减少操作。另外,如果UserAccounts,那么创建一个名为UserAccountsController的新控制器,该控制器将由类似users/1/accounts GET的rest url作为服务器

服务层

拥有一个拥有所有业务逻辑的服务层是最好的选择。记住SRP(单一责任原则(是控制器的唯一责任,它是控制Http响应创建的代码流,并协调这样做的操作

实际的业务逻辑应该在服务层中实现。这样,即使有多个操作,控制器也会非常小(每个操作4/5行(。

用户继承

控制器之间的通用逻辑可以通过使用包含可重用代码的MyApiController: ControllerBase来实现。

不要使用Helper类。这是一个反模式。实用程序类是邪恶的是一篇关于这个问题的优秀文章。

例如,只需将这种辅助类或方法放在名为Infrastructure的文件夹中即可。对于这个例子,只需使用Generate((方法创建接口ITokenGenerator,创建它的实现类TokenGenerator,然后简单地将其注入控制器中。

从技术上讲,编译器允许您在控制器中编写私有方法。这就像一堂普通的课。然而,您应该把所有的东西都放在服务上,这样您就可以从控制器中解耦逻辑。(例如,稍后,您可以轻松地将逻辑迁移到不同的UI,如MVC,而不是web API(

在您的示例中,令牌生成不应该在controller或userService中。我认为最好的是拥有TokenGenerator服务。

最新更新