4

我们正在使用 ASP.NET MVC 开发一个相当大的应用程序,一开始我们看到拥有一个具有通用 CRUD 操作(新建、保存、删除...)以及默认列表操作的抽象基本控制器可能很有用。在我们的例子中,我们有 20 多个通过这种控制器管理的实体。

这样可以避免重复一些代码并使应用程序更加同质化,但是当您看到 Controller 时,很难确切地看到它实现了哪些操作,并且它可能实现了一些不应该存在的操作。例如,假设您想要编辑传递名称而不是 id,您必须创建一个新的 EditByName(name),即使这样做,您仍然可以使用 Edit(id) 操作,因为它位于基础中。

对我来说,整个事情对我来说有点味道,但我没有找到任何显示替代方案的示例,因为我看到的 MVC 应用程序的域非常狭窄。有什么建议吗?有什么例子吗?(我不一定在 ASP.NET MVC 中,我认为这个问题对于任何 MVC 框架都很通用)。

4

5 回答 5

3

在某些方面我认为这是一个好主意,但在其他方面我认为这是对继承的滥用。我确实有一个通用的基本控制器,但它存在是因为我将控制器中的通用代码重构到其中,而不是先验地设计。如果您的实体足够相似,以至于您在基本控制器中共享的代码超过了您被迫拖拉的杂物,那么也许这是值得的。另一方面,如果共享的代码相当少,并且只是调用一个私有抽象方法来完成工作(这样你无论如何都要在真实控制器中实现它),我不知道它会给你带来什么. 不像你'

我的投票是将那些真正常见或横切关注点的东西重构到基类中,而不是试图强制可能不存在的“is-a”关系。

于 2009-07-14T12:00:34.693 回答
2

我创建了您所建议的版本(尽管公认相对非 OOP),它对我来说效果很好。

我创建了一个 MasterController 来设置一个数据库实例和一些其他变量。一旦我开始查看我的 CRUD 操作中的相似之处,我意识到这可以被抽象并移动到 master 中的一个方法中。两种方法,其实。

protected ActionResult DisplayValidateAndEditModel<TModel>(TModel model, string modelPrefix,
                                        string editViewName, string successActionName, object routeValues, string successMessage,
                                        string[] includeProperties, bool acceptFiles
                                ) where TModel : class

protected ActionResult DisplayValidateAndEditModel<TModel>(TModel model, string modelPrefix,
                                        string editViewName, string successActionName, string successMessage,
                                        string[] includeProperties
                                ) where TModel : class

编辑涵盖创建/读取/更新和删除是删除。清单是控制器中的一行——我只是得到一组模型并添加到 viewdata。

这两种方法都检查它是否是一个帖子。如果不是,他们返回视图。如果是这样的话:

  • 编辑调用 TryUpdateModel 并进行一些 xVal 验证。如果一切正常,它会使用任何 routeValues 重定向到 successAction。如果没有,它会再次显示视图。可以传递 includeProperties 以便我的控制器可以准确指定可以获取更新的内容。并且 acceptFiles 添加了额外的功能,它会查找文件发布,如果存在,则将其放入数据库并在文件记录和模型之间创建链接。

  • delete 更新模型的 Cancel_Date 和 Cancel_User 属性(我有一个 ICancelable 接口)并重定向到成功操作

于 2009-07-14T12:29:46.903 回答
1

这是 Rails 打包的东西之一(以及为您生成相关的 CRUD 视图),它非常适合启动一个非常快速的应用程序,但是一旦您认真对待开发,保留原版 CRUD 的东西是非常不寻常的,因为每张桌子所需的东西开始发生变化,需要进一步定制。

这并不是说它没有形成有用的基础和在您开发和原型设计时设置事物的便捷方式 - 比在数据库领域进行修补要容易得多 - 但肯定是它与 Rails 一起工作的方式你没有'不希望在您的最终管理系统中有任何这些页面。

于 2009-07-14T11:57:15.680 回答
1

对我来说,整个东西闻起来有点..

这里有同样的气味:-)

控制器中的代码很少是常见的做法。它的主要目的是决定接下来用哪个模型渲染什么视图。

如果您希望它显示的所有控制器代码都有一个共同的地方,那么您可能需要在控制器中使用很多逻辑。

尝试将逻辑移动到模型中。使用过滤器和 CustomModelBinder。

于 2009-07-14T13:48:23.503 回答
0

只是:如您所知,ASP.NET MVC 支持像 Ruby on Rails 这样的基本脚手架。您可能会考虑自定义用于创建创建、更新、详细信息视图的 T4 文件以满足您的特定需求。

http://blogs.msdn.com/webdevtools/archive/2009/01/29/t4-templates-a-quick-start-guide-for-asp-net-mvc-developers.aspx

于 2009-07-14T17:15:12.253 回答