【问题标题】:Private methods in Controllers [closed]控制器中的私有方法[关闭]
【发布时间】:2011-07-12 01:33:40
【问题描述】:
您好,
我现在已经开发了很多使用 MVC 模式的应用程序,无论是在 Rails 还是 .Net 中,我总是看到在控制器类中添加了一些私有方法。这些私有方法真正知道“如何”验证某事或“如何”为域模型创建视图模型。在我看来,这个逻辑正在泄漏,应该放在帮助器中或域模型本身中。我一直很喜欢“控制器应该知道该做什么,但现在该怎么做”这句话。似乎在类中添加了一堆私有方法会破坏这一点。
我希望有人对此事有一些有用的见解。
谢谢!
【问题讨论】:
标签:
ruby-on-rails
asp.net-mvc
model-view-controller
design-patterns
【解决方案1】:
我使用过 Spring MVC (3.0),我喜欢它构建 servlet/Web 服务的方式。
它有:
- 控制器
- 命令对象
- 验证器对象
每个 @RequestMappings(控制器中的公共方法)都充当 Web 服务。一个 HttpRequest 会进来,传递给正确的请求映射,映射到命令对象,然后验证。
类似这样的:
GetUserCommand {
int userId;
public Map execute() {
Map result = new HashMap();
result.put("user", new UserService().get(userId) );
return result;
}
}
Controller {
@RequestMapping(value="/user")
public ModelAndView handle(GetUserCommand cmd) {
new GetUserCommandValidator().validate(cmd); //checks userid is > 0 or something
return new ModelAndView("userView", cmd.execute());
}
}
请务必注意,HTTP 请求的参数使用反射映射到 GetUserCommand 对象。所以必须有一个 FrontController 来解决这个问题,以及找出将请求转发到哪个方法。
这里的关键是参数、验证、执行逻辑和视图的选择被分成不同的组件。
您还可以使用 IoC 来构造带有所需服务的命令对象。我最终决定将 Command 对象拆分为 Parameters 对象和 Command 对象。 Parameters 对象包含用户ID,而Command 对象使用Parameters(和UserService)实例化并包含execute() 方法。它更冗长,但对我来说似乎是更好的分离。
【解决方案2】:
我同意这个逻辑不应该是控制器的一部分。我避免在我的控制器中使用私有方法。如果我们以“如何”为领域模型创建视图模型为例,这个逻辑通常应该驻留在映射层中。