johnpapa/angular-styleguide权威解读:从入门到精通的编码规范
【免费下载链接】angular-styleguide johnpapa/angular-styleguide: 由John Papa创建的一份Angular编程风格指南,提供了遵循最佳实践的建议,帮助开发者编写高质量、可维护的Angular应用程序代码。 项目地址: https://gitcode.***/gh_mirrors/an/angular-styleguide
你是否在开发Angular应用时遇到过代码混乱、难以维护的问题?是否在团队协作中因编码风格不一致而效率低下?本文将为你详细解读由John Papa创建的这份Angular编程风格指南,帮助你从入门到精通Angular编码规范,编写高质量、可维护的Angular应用程序代码。读完本文,你将了解到Angular应用开发的最佳实践、命名规范、文件结构等关键内容,让你的代码更加规范、高效。
项目概述
本项目是由John Papa创建的一份Angular编程风格指南,提供了遵循最佳实践的建议,帮助开发者编写高质量、可维护的Angular应用程序代码。该指南得到了Angular团队的认可,Igor Minar(Angular团队负责人)对其进行了审查、提供了反馈,并委托John Papa负责这份指南。
官方文档:README.md
版本选择
Angular有多个版本,因此也有多个版本的指南。你需要根据自己使用的Angular版本选择相应的指南。
Angular 1 Style Guide
如果你使用的是Angular 1版本,可以参考The Angular 1 Style Guide。
Angular 2 Style Guide
对于Angular 2版本,The Angular 2 Style Guide已移至官方Angular 2文档,但本项目中仍保留了相关内容。
Angular 1编码规范详解
单一职责原则
每个文件一个组件
Style [Y001]建议每个文件只定义一个组件,代码行数最好少于400行。这样做有以下好处:
- 便于单元测试和模拟
- 更易于阅读、维护,避免团队在版本控制中发生冲突
- 避免隐藏的bug,如组件共享变量、创建不必要的闭包或与依赖项的不必要耦合
以下是不推荐和推荐的代码示例对比:
不推荐的写法:
/* avoid */
angular
.module('app', ['ngRoute'])
.controller('SomeController', SomeController)
.factory('someFactory', someFactory);
function SomeController() { }
function someFactory() { }
推荐的写法:
// app.module.js
/* re***mended */
angular
.module('app', ['ngRoute']);
// some.controller.js
/* re***mended */
angular
.module('app')
.controller('SomeController', SomeController);
function SomeController() { }
// some.factory.js
/* re***mended */
angular
.module('app')
.factory('someFactory', someFactory);
function someFactory() { }
小函数原则
Style [Y002]建议定义小函数,不超过75行代码(越少越好)。小函数具有以下优点:
- 更容易测试,特别是当它们只做一件事并服务于一个目的时
- 促进代码重用
- 更易于阅读和维护
- 避免因大型函数共享外部作用域变量、创建不必要的闭包或与依赖项的不必要耦合而产生的隐藏bug
立即执行函数表达式(IIFE)
JavaScript作用域
Style [Y010]建议将Angular组件包装在立即执行函数表达式(IIFE)中。这样可以将变量从全局作用域中移除,防止变量和函数声明在全局作用域中存在过长时间,避免变量冲突。当代码被压缩并捆绑到单个文件部署到生产服务器时,IIFE可以防止变量冲突和过多的全局变量。
不推荐的写法:
/* avoid */
// logger.js
angular
.module('app')
.factory('logger', logger);
// logger function is added as a global variable
function logger() { }
// storage.js
angular
.module('app')
.factory('storage', storage);
// storage function is added as a global variable
function storage() { }
推荐的写法:
/**
* re***mended
*
* no globals are left behind
*/
// logger.js
(function() {
'use strict';
angular
.module('app')
.factory('logger', logger);
function logger() { }
})();
// storage.js
(function() {
'use strict';
angular
.module('app')
.factory('storage', storage);
function storage() { }
})();
模块
避免命名冲突
Style [Y020]建议使用带有分隔符的唯一命名约定来命名子模块。唯一的名称有助于避免模块名称冲突,分隔符有助于定义模块及其子模块层次结构。例如,app可能是根模块,而app.dashboard和app.users可能是用作app依赖项的模块。
模块定义(设置器)
Style [Y021]建议使用设置器语法声明模块,不使用变量。因为每个文件一个组件,很少需要为模块引入变量。
不推荐的写法:
/* avoid */
var app = angular.module('app', [
'ngAnimate',
'ngRoute',
'app.shared',
'app.dashboard'
]);
推荐的写法:
/* re***mended */
angular
.module('app', [
'ngAnimate',
'ngRoute',
'app.shared',
'app.dashboard'
]);
模块获取(获取器)
Style [Y022]建议在使用模块时,避免使用变量,而是使用获取器语法进行链式调用。这样可以生成更具可读性的代码,避免变量冲突或泄漏。
不推荐的写法:
/* avoid */
var app = angular.module('app');
app.controller('SomeController', SomeController);
function SomeController() { }
推荐的写法:
/* re***mended */
angular
.module('app')
.controller('SomeController', SomeController);
function SomeController() { }
设置与获取
Style [Y023]强调模块只应创建一次,然后从那时起获取。
/* re***mended */
// to set a module
angular.module('app', []);
// to get a module
angular.module('app');
命名函数与匿名函数
Style [Y024]建议使用命名函数,而不是将匿名函数作为回调传递。这样可以生成更具可读性的代码,更容易调试,并减少嵌套回调代码的数量。
不推荐的写法:
/* avoid */
angular
.module('app')
.controller('DashboardController', function() { })
.factory('logger', function() { });
推荐的写法:
// dashboard.js
/* re***mended */
angular
.module('app')
.controller('DashboardController', DashboardController);
function DashboardController() { }
// logger.js
angular
.module('app')
.factory('logger', logger);
function logger() { }
控制器
controllerAs视图语法
Style [Y030]建议使用controllerAs语法,而不是经典的带有$scope的控制器语法。controllerAs语法更接近JavaScript构造函数的语法,促进在视图中绑定到"点分"对象(例如customer.name而不是name),更具上下文,更易于阅读,并避免没有"点分"可能出现的引用问题,还有助于避免在具有嵌套控制器的视图中使用$parent调用。
不推荐的写法:
<!-- avoid -->
<div ng-controller="CustomerController">
{{ name }}
</div>
推荐的写法:
<!-- re***mended -->
<div ng-controller="CustomerController as customer">
{{ customer.name }}
</div>
controllerAs控制器语法
Style [Y031]和Style [Y032]建议在控制器中使用controllerAs语法,并为this使用捕获变量,选择一致的变量名,例如vm(代表ViewModel)。this关键字是上下文相关的,当在控制器内的函数中使用时,其上下文可能会改变。捕获this的上下文可以避免遇到此问题。
不推荐的写法:
/* avoid */
function CustomerController($scope) {
$scope.name = {};
$scope.sendMessage = function() { };
}
/* avoid */
function CustomerController() {
this.name = {};
this.sendMessage = function() { };
}
推荐的写法:
/* re***mended */
function CustomerController() {
var vm = this;
vm.name = {};
vm.sendMessage = function() { };
}
可绑定成员置顶
Style [Y033]建议将可绑定成员放在控制器的顶部,按字母顺序排列,不要分散在控制器代码中。这样可以轻松阅读,并帮助你立即识别控制器中哪些成员可以绑定并在视图中使用。将内联匿名函数定义为一行代码时可以放在顶部,但如果函数超过一行代码,将其放在可绑定成员下方可以提高可读性。
不推荐的写法:
/* avoid */
function SessionsController() {
var vm = this;
vm.gotoSession = function() {
/* ... */
};
vm.refresh = function() {
/* ... */
};
vm.search = function() {
/* ... */
};
vm.sessions = [];
vm.title = 'Sessions';
}
推荐的写法:
/* re***mended */
function SessionsController() {
var vm = this;
vm.gotoSession = gotoSession;
vm.refresh = refresh;
vm.search = search;
vm.sessions = [];
vm.title = 'Sessions';
////////////
function gotoSession() {
/* */
}
function refresh() {
/* */
}
function search() {
/* */
}
}
将控制器逻辑委托给服务
Style [Y035]建议通过委托给服务和工厂来延迟控制器中的逻辑。将逻辑放在服务中并通过函数公开,可由多个控制器重用;服务中的逻辑更容易在单元测试中隔离,而控制器中的调用逻辑可以轻松模拟;还可以消除依赖关系,并对控制器隐藏实现细节,使控制器保持精简和专注。
服务和工厂
服务
Style [Y040]指出服务是使用new关键字实例化的,使用this表示公共方法和变量。由于服务和工厂非常相似,为了一致性,建议使用工厂。
服务示例:
// service
angular
.module('app')
.service('logger', logger);
function logger() {
this.logError = function(msg) {
/* */
};
}
工厂
Style [Y050]和Style [Y051]强调工厂应该有单一职责,并且是单例的,返回一个包含服务成员的对象。
工厂示例:
// factory
angular
.module('app')
.factory('logger', logger);
function logger() {
return {
logError: function(msg) {
/* */
}
};
}
项目资源
代码片段
本项目提供了多种编辑器的Angular代码片段,方便开发者快速编写符合规范的代码:
- Brackets代码片段
- Emacs代码片段
- Sublime Text代码片段
- Vim代码片段
- VSCode代码片段
- WebStorm实时模板
国际化
项目提供了多种语言的翻译版本,可在a1/i18n/目录下查看,方便不同地区的开发者学习和使用。
总结
John Papa的Angular风格指南为开发者提供了全面的编码规范和最佳实践,遵循这些规范可以帮助我们编写高质量、可维护的Angular应用程序代码。从单一职责原则到模块管理,从控制器设计到服务使用,每一个细节都旨在提高代码的可读性、可维护性和可扩展性。
希望本文对你理解和应用这份权威的Angular风格指南有所帮助。如果你有任何问题或建议,欢迎在项目仓库中提出。同时,也欢迎你点赞、收藏本文,关注后续更多关于Angular开发的优质内容!
社区教程:a1/i18n/zh-***.md
【免费下载链接】angular-styleguide johnpapa/angular-styleguide: 由John Papa创建的一份Angular编程风格指南,提供了遵循最佳实践的建议,帮助开发者编写高质量、可维护的Angular应用程序代码。 项目地址: https://gitcode.***/gh_mirrors/an/angular-styleguide