【问题标题】:Reasons for not having a compact structure of an MVC application?没有紧凑的 MVC 应用程序结构的原因是什么?
【发布时间】:2019-01-02 19:36:29
【问题描述】:

在一个 web MVC 项目中,我有以下结构:

mymvc/                      -> Project root.
    public/                 -> Document root. The only one folder accessible from web.
        assets              -> Client-side assets. NOT ONLY for global themes and libraries, BUT ALSO for each specific "view" controlled by the "src/Application" components.
            css/
            js/
            images/
            ...
        index.php           -> Application's entry point.
    src/                    -> UI layer rules.
        Application/
            Controller/
            View/
            ViewModel/
        Dispatcher/         -> Application dispatching - route matching, dispatching to the specified controller, etc.
        ...                 -> Other classes used by the components in the "src/Application" folder.
    templates/              -> Layout and template files.

注意:所有域模型组件(实体、存储库、数据映射器、服务等)都位于mymvc 目录之外的文件夹中,因此任何其他应用程序也可以访问它们。

我想过——实际上是很多——关于执行以下两个步骤:

  1. templates 目录移动到src/Application 文件夹。
  2. assets 目录移动到src/Application,在Web 服务器(Apache) 配置中创建别名/assets/ - 指向移动的文件夹,并允许外部世界对其进行完全访问。

全局使用的资产(如 css 主题、js 库代码或背景图像等)仍可能位于 public 目录中 - 显然不在名为或别名为 assets 的文件夹中。

我真的觉得这两个步骤是一个非常好的主意,因为在我看来,这两个文件夹都包含与来自src/Application 的结构相关的资源。 所以,不要有这样的东西:

  • src/Application/Controller/AboutUs.php
  • public/assets/js/AboutUs.js
  • templates/AboutUs/[multiple-layout-and-template-files],

类似以下的结构似乎要好得多:

  • src/Application/Controller/AboutUs.php
  • src/Application/assets/js/AboutUs.js
  • src/Application/templates/AboutUs/[multiple-layout-and-template-files],

但是,在我研究了很多 Web 框架之后,我意识到它们都将两个文件夹(templatesassets)与应用程序文件夹完全分开。

所以我想问一下:有什么具体原因,为什么我提议的两个目录的移动不能,或者不应该做?

谢谢。

【问题讨论】:

  • 您的网络资源(.js 等)肯定需要保留在公用文件夹中以允许用户访问它们。
  • 对于可能会决定否决我的问题的用户:公平地说,让我知道您投反对票的动机,以便我可以相应地更改我的问题。我对您的所有建议或批评持开放态度。谢谢。

标签: php model-view-controller web-applications architecture directory-structure


【解决方案1】:

这完全取决于您想要实现的目标以及您的工作流程。您似乎在使用 PHP - 值得关注非 PHP 框架,例如 Ruby on Rails。

通常,您希望输出文件夹为“只读” - 开发人员不应手动编辑文件,而是构建和部署管道运行 Gradle 等工具来转换 SASS/LESS 和 JS 文件(来自 /source文件夹)到 CSS 和缩小/连接的 Javascript 中,并将它们放置在 /public 中的正确位置。构建和部署管道对于开发和生产构建通常具有不同的配置(例如,仅针对生产进行缩小)。

在 Ruby on Rails 中,结构大多如您所描述的“好多了”——除了“模板”是“视图”下的一个文件夹,称为“布局”。有一个构建步骤(自动运行)转换各种资产文件(SASS/LESS、JS 等)。

您可以查看 Ruby on Rails 目录结构here 的详细说明。 Django的目录结构解释here.

回答您的 cmets 中的问题:

  • SASS/LESS/JS/Coffee 脚本文件应该放在哪里? - 由您决定。在 Rails 中,他们住在/app/assets/javascripts 和/app/assets/stylesheets;在这些文件夹中,每个视图都有一个文件,以及应用程序级文件。这使您的构建过程变得简单而简单 - 您只需担心 2 个文件夹,并且不必在每次创建新视图时都修改您的构建。
  • 我如何构建我的视图 - 我有应用程序级别的视图和特定的页面视图。再次 - 主要是方便的问题。在 Rails 中,所有模板都位于 /app/views 下。应用程序级视图位于一个名为 /app/views/layouts 的文件夹中 - 它们与页面级模板并没有太大区别,因此将它们移出该文件夹似乎并没有太大的作用,同时将所有内容保持在同一顶层文件夹使构建和配置更简单。

所以,不,没有理由按照您的建议去做。

【讨论】:

  • 谢谢你,内维尔。我很感激!我又延长了一周的赏金,因为我有一种感觉,有更多的方面需要揭示。
【解决方案2】:

在我看来,每个人都可以使用最适合他/她的结构。

过去几年我一直在使用 CodeIgniter,并且我自己也一直在处理文件和文件夹。最后我认为我有我喜欢的结构:)

对于应用程序文件夹,我主要还是坚持使用手册和教程中推荐的(基本)结构。

看起来像这样:

- versionX
    - application
        - config
        - controllers
            - assets // Folder to keep asset specific controllers
                css.php
                js.php  // These controllers are bundling all resources and returning it as css, js or image file. Images can be cropped etc by params in url. Framework routes urls as domain.com/css/stylesheet.css to the css.php controller etc
                img.php
            documents.php // normal controller files
            users.php
            ...
        - core // core (controller) files from which controllers can extend
            APP_Controller.php
            APP_AssetController.php
            ...
        - helpers // Holds files with functions that you can use everywhere in the app.
        - libraries // Holds library files and folders
            PasswordHash.php
            Permissions.php
            Template.php
            Twitter.php
            ...
        - models // holds files with all DB logic (one file per DB table in my case, join tables not included)
    - public
        - css
        - js
            - components // javascript files for specific (large) page element(s)
                modal.js
                timeline.js
            - controllers // one js file per controller for controller specific js code
                documents.js
                users.js
            - resources // all libraries from 3rd party (Bootstrap, jQuery, ...)
        - uploads // user generated content (folder divided per file use/ origin)
    - themes
        - blueSky
            - views
                - layouts // app level views
                    - partials // app level partials (main navs, footers, ...)
                - documents // a folder per controller
                    - modals // modals used at document controller
                        _merge_document.php
                        _split_document.php
                    - partials
                        _form.php // for adding and editing documents
                        _drawer.php // submenu for document controller
                    index_view.php
                    create_view.php
                    edit_view.php
                    ...
                - users

我希望这能让您对我如何做到这一点有所了解。但你真的应该做你最喜欢做的事。没有什么比浏览你不喜欢的东西更糟糕的了。

【讨论】:

  • 好的!我忘了提一下,index.php 文件(用于启动应用程序)直接位于 versionX 文件夹下,就像 .htaccess 和 robots.txt 之类的其他文件一样(实时服务器上的 versionX 可以是 public_html 文件夹,或者您可以添加指向的别名versionX 文件夹...
  • 非常感谢您,Brainfeeder!我研究了你的答案,我希望能够分享赏金。不幸的是,这是不可能的。但请知道,我非常感谢您的努力。我找到了 “这些控制器捆绑所有资源并将其作为 css、js 或图像文件返回。图像可以通过 url 中的参数裁剪等。” 一个有趣的部分。无论如何,我将赏金延长了一周,因为我有一种感觉,还有更多方面需要揭示。
【解决方案3】:

对代码进行分类

我唯一推荐的是保持命名空间与目录结构相同,以保持自动加载简单。从那里开始,语言并不关心代码是如何组织的。 两个限制是命名空间和目录:它们是分层的。所以这就决定了你只能在层次结构中对代码进行分类。

实际的问题是层次分类本身就是一个问题。对象可以通过多种方式进行分类。幸运的是 PHP 对分类是不可知的,那么为什么人类不能一样呢?因为我们实际上考虑的是代码和对象。我们寻找它们,使用它们,培育它们。这只是个人经验和品味的问题,您与某些对象行为最强烈的关联是什么?

还有一件额外的事情需要考虑:“别人就是地狱。”

一旦您的代码开始依赖该特定框架,保持您的分类与其他分类(例如 Symphony 框架的分类)将派上用场。或者别人的分类方案可能是你不愿意服从的。

不管怎样,没有理由做你想做的事。如果以后你改变主意,至少你会自己知道为什么改变它,并且你会从中吸取教训。

【讨论】:

  • 谢谢你,Code4R7。我接受了 Neville 的回答,虽然我发现你的回答也很有趣。
猜你喜欢
  • 2020-08-18
  • 1970-01-01
  • 1970-01-01
  • 2011-01-16
  • 2011-02-23
  • 2021-06-24
  • 2019-08-25
  • 2016-09-29
  • 2011-07-29
相关资源
最近更新 更多