Heavily inspired from this AngularJS Style Guide
- Single Responsibility
- IIFE
- Modules
- Controllers
- Factories
- Data Services
- Directives
- Manual Annotating for Dependency Injection
- Naming
- Angular $ Wrapper Services
- Testing
- Comments
- Constants
[Style Y001]
Define 1 component per file.
[Style Y010]
Wrap AngularJS components in an Immediately Invoked Function Expression (IIFE).
[Style Y021]
Declare modules without a variable using the setter syntax.
[Style Y022]
When using a module, avoid using a variable and instead use chaining with the getter syntax.
[Style Y023]
Only set once and get for all other instances.
[Style Y033]
- Place bindable members at the top of the controller, alphabetized, and not spread through the controller code.
[Style Y034]
Use function declarations to hide implementation details. Keep your bindable members up top. When you need to bind a function in a controller, point it to a function declaration that appears later in the file. This is tied directly to the section Bindable Members Up Top. For more details see this post.
[Style Y035]
Defer logic in a controller by delegating to services and factories.
[Style Y037]
Define a controller for a view, and try not to reuse the controller for other views. Instead, move reusable logic to factories and keep the controller simple and focused on its view.
[Style Y052]
Expose the callable members of the service (its interface) at the top, using a technique derived from the Revealing Module Pattern.
[Style Y053]
Use function declarations to hide implementation details. Keep your accessible members of the factory up top. Point those to function declarations that appears later in the file. For more details see this post.
[Style Y060]
Refactor logic for making data operations and interacting with data to a factory. Make data services responsible for XHR calls, local storage, stashing in memory, or any other data operations.
[Style Y061]
When calling a data service that returns a promise such as $http, return a promise in your calling function too.
[Style Y070]
Create one directive per file. Name the file for the directive.
[Style Y072]
When manipulating the DOM directly, use a directive. If alternative ways can be used such as using CSS to set styles or the animation services, Angular templating, ngShow
or ngHide
, then use those instead. For example, if the directive simply hides and shows, use ngHide/ngShow.
[Style Y073]
All of the custom made directives must start with the hyp
prefix.
[Style Y074]
When creating a directive that makes sense as a stand-alone element, allow restrict E
(custom element) and optionally restrict A
(custom attribute). Generally, if it could be its own control, E
is appropriate. General guideline is allow EA
but lean towards implementing as an element when it's stand-alone and as an attribute when it enhances its existing DOM element.
Note: EA is the default for AngularJS 1.3 +
[Style Y081]
When a controller depends on a promise to be resolved before the controller is activated, resolve those dependencies in the $routeProvider
before the controller logic is executed. If you need to conditionally cancel a route before the controller is activated, use a route resolver.
Use a route resolve when you want to decide to cancel the route before ever transitioning to the View.
[Style Y090]
Avoid using the shortcut syntax of declaring dependencies without using a minification-safe approach.
[Style Y120]
Use the following pattern for all the components: feature.type.js
[Style Y122]
Name test specifications similar to the component they test with a suffix of spec
.
[Style Y123]
Use consistent names for all controllers named after their feature. Use UpperCamelCase for controllers, as they are constructors.
[Style Y124]
Append the controller name with the suffix Ctrl
.
[Style Y125]
Use consistent names for all factories named after their feature. Use camel-casing for services and factories.
[Style Y126]
Use consistent names for all directives using camel-case. Use the following short prefix hyp
.
[Style Y127]
When there are multiple modules, the main module file is named app.module.js
while other dependent modules are named after what they represent. For example, an admin module is named admin.module.js
. The respective registered module names would be app
and admin
.
[Style Y128]
Separate configuration for a module into its own file named after the module. A configuration file for the main app
module is named app.config.js
(or simply config.js
). A configuration for a module named admin.module.js
is named admin.config.js
.
[Style Y129]
Separate route configuration into its own file. Examples might be app.route.js
for the main module and admin.route.js
for the admin
module. Even in smaller apps I prefer this separation from the rest of the configuration.
[Style Y180]
Use $document
and $window
instead of document
and window
.
[Style Y181]
Use $timeout
and $interval
instead of setTimeout
and setInterval
.
[Style Y190]
Write a set of tests for every story. Start with an empty test and fill them in as you write the code for the story.
[Style Y191]
Use Jasmine.
[Style Y195]
Run JSHint on your tests.
[Style Y197]
Place unit test files (specs) side-by-side with your client code. Place specs that cover server integration or test multiple components in a separate tests
folder.
[Style Y220]
Use jsDoc
syntax to document function names, description, params and returns. Use @namespace
and @memberOf
to match your app structure.
[Style Y240]
Create an AngularJS Constant for vendor libraries' global variables.