【问题标题】:How do I correctly split angularjs module controllers/services/etc into their own files?如何正确地将 angularjs 模块控制器/服务/等拆分为自己的文件?
【发布时间】:2023-03-25 08:54:01
【问题描述】:

我见过一些项目将所有“片段”(控制器/服务/指令)保存在一个文件中的一个模块中。 angular-app 就是这样。

示例:

angular.module('myModule', ['depA', 'depB'])
  .controller('MyController', function() {})
  .service('myService', function() {});

但是,我过去曾与团队合作过大型 Angular 项目,其中各个控制器/服务/指令保存在自己的文件中。我喜欢将它们保存在自己的文件中以保持文件小以及其他原因的想法。现在的问题是我是负责将开始的部分和构建过程放在一起的人。之前我所要做的就是编写应用程序代码并遵循这些项目的标准。

为了正确地拥有单独的文件,我相信我必须拥有一个主模块文件。

示例:

// file 1
angular.module('myModule', ['depA', 'depB']);

// file 2
angular.module('myModule')
  .controller('MyController', function() {});

所以我的问题是,我需要确保发生什么文件加载顺序?我只需要确保在文件 2 之前加载主模块文件(文件 1)吗?

这对我来说似乎很奇怪。如果还有一个服务文件附加到前面提到的模块并且控制器文件 2 已经加载,但服务文件还没有,那么 Angular 是否有可能调用该控制器文件,然后最终导致事情得到不正常?

另外,如果您认为我的处理方式有误,我很乐意听取您的建议。

【问题讨论】:

  • 这件事众说纷纭,但你可以从角度种子项目文件结构入手
  • @DayanMorenoLeon 不。大多数人认为 angular-seed 项目并不是构建应用程序的最佳方式。首先是由某种“组件”构建。我什至没有问如何构建应用程序。我问我需要什么文件加载顺序才能确保发生。

标签: angularjs


【解决方案1】:

模块加载顺序

只需确保当您注册一个新模块时,当您的应用程序启动时,它的模块依赖项应该已经被浏览器加载。

所以任何时候你这样做:

    angular.module('myApp', ['dep1', 'dep2', 'dep3']);

dep1dep2dep3 的文件应该在您的应用程序引导时已经加载。

如果您使用<script> 标签和自动bootstrapping(默认角度),那么<script> 标签的顺序应该无关紧要。但是,如果使用 requirejs 之类的库,请确保在手动引导之前加载所有依赖项。

其他注意事项

只要您的模块以正确的顺序加载,那么..

  • 不用担心控制器指令服务工厂的顺序>、提供者常量

  • run 块的顺序可能很重要,因为它们与其他运行块相关,因为它们按照注册的顺序执行(在特定模块中)。

  • config 块的顺序可能很重要,因为它们与其他 config 块相关,因为它们按照注册的顺序执行(在一个特定的模块)。

关于前两点,依赖的顺序(例如['dep1', 'dep2', 'dep3'] vs ['dep2', 'dep3', 'dep1'])也会影响run块和config的执行顺序em> 块。 Angular 将遍历依赖树两次,并依次执行所有 config 块,然后是所有 run 块。

Angular 使用post-order traversal 来初始化模块及其关联的配置和运行块。因此,如果我们将模块依赖关系表示为树:

遍历顺序为ACEDBHIGF

【讨论】:

  • 在进行更多研究时,我认为“确保在实例化新模块时,[其] 模块依赖项应该已经被浏览器加载”并不完全正确。这很有意义,但我忘记了 angular bootstrap 等待 document.ready 事件。因此,浏览器的
  • @user45763,感谢您的更正。如果您使用像 requirejs 这样的脚本加载器,您仍然必须小心,因为在开发中,angular 可以在加载所有依赖项之前引导。我已经更新了答案。
【解决方案2】:

我在我的项目中所做的是将开发环境中的所有内容分开,然后通过 gulp.js 进行编译(grunt 应该也可以)。虽然这是一个单独的主题,但这里有一个如何将 Angular 代码保存在不同文件中的示例。

主文件(必须先加载)可以如下。我们将定义我们的模块、控制器、指令、存储库或其他任何东西。我们称之为 app.js

// AngularJS Application File

var example = angular.module(
    // ngApp name
    'example',

    // Default Dependencies
    [
        'exampleControllers',
        'exampleRepositories',
        'exampleDirectives'
    ]
);

var exampleControllers = angular.module('exampleControllers', []);
var exampleRepositories = angular.module('exampleRepositories', []);
var exampleDirectives = angular.module('exampleDirectives', []);

现在,我们可以从后面的任何 javascript 文件中访问这个 exampleControllers、exampleRepositories 和 exampleDirectives。

controllers.js 文件。

exampleControllers
  // Main Controller
  .controller('MainController',
    [
      '$scope',
      '$log',
      function ($scope, $log) {
        $scope.hello = 'Hello World';
      }
    ]
  )
  // Sub Page Controller
  .controller('SubPageController',
    [
      '$scope',
      'someService',
      '$log',
      function ($scope, sService, $log) {
        $log.info($scope.hello);
      }
    ]
  );

另一个控制器.js 文件:

exampleControllers
  // Another Controller
  .controller('AnotherController',
    [
      '$scope',
      '$log',
      function ($scope, $log) {
        $scope.helloagain = 'Hello World, from another controller';
      }
    ]
  )

等等.. 只需确保首先加载您的 app.js 文件,以便示例 变量可用。

我肯定会阅读 gulp.js (http://gulpjs.com/)。自动化工作流程非常棒。

【讨论】:

  • 感谢分享。实际上,我确实已经在这个项目中设置并广泛使用了 gulp :) 在处理 grunt 之后,与它一起工作是一种乐趣。
  • 是的,gulp 很棒。我从来没有享受过使用 grunt 的乐趣,但我参与了一个同时使用 gulp 和 grunt 的项目。你有什么要我详细说明的吗?如果满足请求,请不要忘记将答案标记为可接受。
猜你喜欢
  • 2014-11-15
  • 1970-01-01
  • 1970-01-01
  • 2016-02-26
  • 2014-03-06
  • 1970-01-01
  • 2020-01-30
  • 2019-06-04
  • 1970-01-01
相关资源
最近更新 更多