点击查看AngularJS系列目录
转载请注明出处:http://www.cnblogs.com/leosx/


什么是AngularJS的模块

我们所说的模块,是你的AngularJS应用程序的一个组成部分,它可以是一个Controller,也可以是一个Service服务,也可以是一个过滤器(Filter),也可以是一个directive(指令)等等…都是属于一个模块!

大多数的应用程序都是有一个自己的函数入口方法Main ,用它来进行初始化,以及加载装配各个模块,然后这些模块的组合,构成了你的应用程序,对吧?

但是,but, AngularJS应用程序却不是这样的哦,它没有main 方法,没有函数入口。代替之的是在模块中指定声明这个模块在AngularJS应用程序中该如何去加载,启动。这种方法有以下几个优点:

1) 使用声明的方式,让人更加容易理解。

2) 你可以更加容易的让你的代码进行重用。

3) 模块的加载顺序就更加容易控制了。因为这些模块是延迟执行的。

4) 对于进行单元测试就变得更加的方便了。更加可靠,你只需要载入这个模块就可以进行测试了。

5) 端对端的测试中,你可以使用模块去重写配置。

还是看看代码最重要,直接上代码:

<div ng-app="myApp">
<div>
{{ 'World' | greet }}
</div>
</div>
<script src="https://code.angularjs.org/1.3.0/angular.min.js"></script>
<script type="text/javascript">
(function(){
// declare a module
var myAppModule = angular.module('myApp', []); // configure the module.
// in this example we will create a greeting filter
myAppModule.filter('greet', function() {
return function(name) {
return 'Hello, ' + name + '!';
};
});
})();
</script>

单元测试的代码:

it('should add Hello to the name', function() {
expect(element(by.binding("'World' | greet")).getText()).toEqual('Hello, World!');
});

效果图:

有几个事情需要注意一下的:

1. 关于模块的API,点击这里

2. <div ng-app=”myApp”>引用了myApp 模块。 这既是告诉启动器,你使用了这个名为myApp的模块,当AngularJS启动的时候,它就会去加载力的这个模块。

3. 在 angular.module(‘myApp’, [] )中,有个空的数组,这个数组是myApp模块说依赖的模块的列表.

推存设置

上面的例子都是非常简单的。它不是大型应用。我们建议你将你的AngularJS应用程序碎片化,也就是让你的应用程序变成多个模块的组合,例如:

1.不同的业务,为一个模块。

2.一个模块中,包含很多可以重用的组件(特别是指令和过滤器,以后也可以使用的)

3.一个应用程序级别的模块,它依赖于上级的模块,并且它还包含有所有的初始化代码。。。

在Google上,有一个关于如何编写大型应用程序的文档,你可以点击这里查看。

当然咯!  上面的都是建议,你可以根据你的需求,进行量身定做。比如:

<div ng-app="xmpl">
<div ng-controller="XmplController">
{{ greeting }}
</div>
</div>
<script src="https://code.angularjs.org/1.3.0/angular.min.js"></script>
<script type="text/javascript">
(function(){
angular.module('xmpl.service', []) .value('greeter', {
salutation: 'Hello',
localize: function(localization) {
this.salutation = localization.salutation;
},
greet: function(name) {
return this.salutation + ' ' + name + '!';
}
}) .value('user', {
load: function(name) {
this.name = name;
}
}); angular.module('xmpl.directive', []); angular.module('xmpl.filter', []); angular.module('xmpl', ['xmpl.service', 'xmpl.directive', 'xmpl.filter']) .run(function(greeter, user) {
// This is effectively part of the main method initialization code
greeter.localize({
salutation: 'Bonjour'
});
user.load('World');
}) .controller('XmplController', function($scope, greeter, user){
$scope.greeting = greeter.greet(user.name);
});
})();
</script>

效果图:

模块的加载和依赖

一个模块,其实是一个在应用程序的引导程序中运行的,一个配置的集合和运行块的集合。

1. 配置模块,它可以在provider提供者中进行注册,还可以再配置应用阶段进行执行。只有provider和常量才能够被注入到配置块中去。这样做是为了防止在配置块没有配置完成之前,意外的实例化了服务,这是不被允许的。

2. 运行(run)块, 是在注入器被创建出来之后和被用于应用程序之后,进行执行的。只有实例对象和常量能够被注入到 运行(run )块当中。这样做的目的是为了防止在应用程序运行期间,增加,修改了系统配置。

来看看例子:

angular.module('myModule', []).
config(function(injectables) { // provider-injector
// This is an example of config block.
// You can have as many of these as you want.
// You can only inject Providers (not instances)
// into config blocks.
}).
run(function(injectables) { // instance-injector
// This is an example of a run block.
// You can have as many of these as you want.
// You can only inject instances (not Providers)
// into run blocks
});

配置块

其实在模块上有一些非常方便的方法,它们就相当于是一个 config 配置块,看例子:

angular.module('myModule', []).
value('a', 123).
factory('a', function() { return 123; }).
directive('directiveName', ...).
filter('filterName', ...); // is same as angular.module('myModule', []).
config(function($provide, $compileProvider, $filterProvider) {
$provide.value('a', 123);
$provide.factory('a', function() { return 123; });
$compileProvider.directive('directiveName', ...);
$filterProvider.register('filterName', ...);
});

当AngularJS在进行引导启动你的应用程序的时候,它会首先定义所有的常量。然后再在配置块中使用同一个 常量列表 去注册它们。

运行块(Run)

Run,我们这里叫运行块,它是最接近Main入口函数的一个方法。运行块(run) 是建立在AngularJS应用程序之上的。它会在所有的服务配置完毕,注入器被创建完毕之后执行。。 一个运行块(run block) 通常会包含着单元测试,正因如此,应该把他声明在一个独立的模块(module)当中,这样,就可以把单元测试给独立开来了。

依赖关系

一个模块,它知道所有它所依赖的其它模块,也就是说在它加载起来前,需要将它所依赖的其它所有模块给加载起来。换句换说,对于需要配置块的模块来说,配置块一定是在需要它的模块初始化之前就被初始化完毕了。 同样的,运行块(run block)也是这样的,一个模块,会且仅会被加载一次,无论有多少个模块引用了它,它都只会被加载一次的。

异步加载(Asynchronous Loading)

Modules are a way of managing $injector configuration, and have nothing to do with loading of scripts into a VM. There are existing projects which deal with script loading, which may be used with Angular. Because modules do nothing at load time they can be loaded into the VM in any order and thus script loaders can take advantage of this property and parallelize the loading process.(这句话实在翻译不了,英文太烂,有看到并且英文好的哥们儿,望帮忙翻译下)

创建和检索

在使用 angular.module(‘myModule’, [] )的时候得注意,它会创建一个叫做 myModule的模块,并且会覆盖掉所有之前叫做 myModule 的模块。  我们使用 angular.module(‘myModule’) 就可以去查找,检索我们已经创建的模块。来个例子:

var myModule = angular.module('myModule', []);

// add some directives and services
myModule.service('myService', ...);
myModule.directive('myDirective', ...); // overwrites both myService and myDirective by creating a new module
var myModule = angular.module('myModule', []); // throws an error because myOtherModule has yet to be defined
var myModule = angular.module('myOtherModule');

单元测试

单元测试是一个很好的去初始化你的应用模块,并且调用它的一个小的应用。  有结构的模块对于单元测试时非常有用的,可以很好的找到关注重点。

一个模块只能在注入器(injector) 中被加载一次,且仅有一次。通常,一个Angular 应用程序只有一个 注入器(injector) 而且所有模块只会被加载一次。但是每个单元测试都会有自己的注入器(injector) ,而且模块可以被加载多次。 在我们的所有例子中,都遵循了模块定义的这个规则:

angular.module('greetMod', []).

factory('alert', function($window) {
return function(text) {
$window.alert(text);
}
}). value('salutation', 'Hello'). factory('greet', function(alert, salutation) {
return function(name) {
alert(salutation + ' ' + name + '!');
}
});

我们来写一些单元测试,来看看在单元测试当中如何重写配置

describe('myApp', function() {
// load application module (`greetMod`) then load a special
// test module which overrides `$window` with a mock version,
// so that calling `window.alert()` will not block the test
// runner with a real alert box.
beforeEach(module('greetMod', function($provide) {
$provide.value('$window', {
alert: jasmine.createSpy('alert')
});
})); // inject() will create the injector and inject the `greet` and
// `$window` into the tests.
it('should alert on $window', inject(function(greet, $window) {
greet('World');
expect($window.alert).toHaveBeenCalledWith('Hello World!');
})); // this is another way of overriding configuration in the
// tests using inline `module` and `inject` methods.
it('should alert using the alert service', function() {
var alertSpy = jasmine.createSpy('alert');
module(function($provide) {
$provide.value('alert', alertSpy);
});
inject(function(greet) {
greet('World');
expect(alertSpy).toHaveBeenCalledWith('Hello World!');
});
});
});

AngularJS -- Module (模块)的更多相关文章

  1. AngularJS多模块开发

    angularJS中的多模块开发是指多个module模块开发,步骤为: 1. 确定主模块    var app=angular.module('myApp',[]); 2. 其他的子模块添加到主模块后 ...

  2. 03、AngularJs的模块与控制器

    大部分的应用程序都有一个主方法(main)来组织,实例化,启动应用程序.而AngularJs应用是没有主方法的,它是通过模块来声明应用应该如何启动的.同时,模块允许声明来描述应用中依赖关系,以及如何进 ...

  3. Angularjs 异步模块加载项目模板

    ng-lazy-module-seed(Angularjs 异步模块加载项目模板) 相信做过SPA项目的朋友都遇到过这个问题:页面初始化时需要加载文件太大或太多了,许多文件加载后很可能不会运行到,这是 ...

  4. AngularJS-01.AngularJS,Module,Controller,scope

    1.AngularJS 一个构建动态Web应用程序的结构化框架. 基于JavaScript的MVC框架.(  MVC ---- Model(模型).View(视图).Controller(控制器) ) ...

  5. 利用Module模块把构建的神经网络跑起来

    训练一个神经网络往往只需要简单的几步: 准备训练数据 初始化模型的参数 模型向往计算与向后计算 更新模型参数 设置相关的checkpoint 如果上述的每个步骤都需要我们写Python的代码去一步步实 ...

  6. AngularJs angular.Module模块接口配置

    angular.Module Angular模块配置接口. 方法: provider(name,providerType); name:服务名称. providerType:创建一个服务的实例的构造函 ...

  7. AngularJs(七) 模块的创建

    module 目前我选编写的都是在AngularJs-1.5版本,如有疑问可以联系我. 理解模块的生命周期. config 和 run 方法是模块调用时加载的方法.那么module的执行顺序是怎么样呢 ...

  8. Angularjs Module类的介绍及模块化依赖

    后面的学习我们会遵循一个控制器管理一个视图,一个路由对应一个视图的单一原则,所以再不会将controller控制器代码直接写到 index.html 中. 我们会应用到angular.js中强大的模块 ...

  9. AngularJS 常用模块书写建议

    本文是依据 Angular Style Guide 对 Angular 常用模块书写建议的翻译和总结,仅供参考. IIFE 使用 立即执行函数表达式(Immediately Invoked Funct ...

随机推荐

  1. (转载)公开的海量数据集 Public Research-Quality Datasets

    转载自:http://rensanning.iteye.com/blog/1601663 海量数据数据集 海量数据(又称大数据)已经成为各大互联网企业面临的最大问题,如何处理海量数据,提供更好的解决方 ...

  2. Linux巩固记录(1) J2EE开发环境搭建及网络配置

    由于要近期使用hadoop等进行相关任务执行,操作linux时候就多了 以前只在linux上配置J2EE项目执行环境,无非配置下jdk,部署tomcat,再通过docker或者jenkins自动部署上 ...

  3. redi安装

    借鉴文章:https://segmentfault.com/a/1190000010709337 在linux中使用wget时,若报-bash: wget: command not found,则表明 ...

  4. Linux程序设计综合训练之简易Web服务器

    1.功能需求: (1)学习网络套接字编程.HTPP协议.Web服务器等知识: (2)设计一简单Web服务器,提供静态网页浏览服务功能. 2.实现的功能: (1)C语言实现基于socket的Web服务器 ...

  5. Spring Security学习笔记

    Spring Web Security是Java web开发领域的一个认证(Authentication)/授权(Authorisation)框架,基于Servlet技术,更确切的说是基于Servle ...

  6. python专题-函数式编程

    函数式编程是使用一系列函数去解决问题,按照一般编程思维,面对问题时我们的思考方式是"怎么干",而函数函数式编程的思考方式是我要"干什么". 至于函数式编程的特点 ...

  7. 【JSP】JSP Action动作标签

    Action动作标签简述 JSP action是JSP技术体系内置的一组标签,使用无需导入,或者添加另外的库.JSP action标签都是对Java代码的逻辑的封装.主要使用的是下面这些. 标签 作用 ...

  8. Selenium八种基本定位方式---基于python

    from selenium import  webdriver driver=webdriver.Firefox() driver.get("https://www.baidu.com&qu ...

  9. 构建具有用户身份认证的 React + Flux 应用程序

    原文:Build a React + Flux App with User Authentication 译者:nzbin 译者的话:这是一篇内容详实的 React + Flux 教程,文章主要介绍了 ...

  10. DES加密:8051实现(C语言) & FPGA实现(VHDL+NIOS II)

    本文将利用C语言和VHDL语言分别实现DES加密,并在8051和FPGA上测试. 终于有机会阅读<深入浅出密码学一书>,趁此机会深入研究了DES加密的思想与实现.本文将分为两部分,第一部分 ...