Controladores e encapsulamento AngularJS definidos globalmente

De acordo com o tutorial do AngularJS, uma function de controlador fica dentro do escopo global.

http://docs.angularjs.org/tutorial/step_04

As próprias funções do controlador são automaticamente analisadas em um escopo encapsulado ou elas residem no escopo global? Eu sei que eles são passados ​​uma referência ao seu próprio escopo $, mas parece que a function em si está apenas sentado no escopo global. Obviamente, isso pode causar problemas no futuro, e eu aprendi através da experiência e da educação a encapsular. Além disso, se eles residem no escopo global, não seria considerado uma prática recomendada encapsulá-los dentro de um object a ser referenciado como este? :

Object.functionName(); 

Em vez disso:

  functionName(); 

De modo a evitar problemas que ocorrem com a poluição do escopo global (ou seja, substituindo funções, etc.)

O AngularJS suporta 2 methods de registro de funções do controlador – como funções acessíveis globalmente (você pode ver este formulário no tutorial mencionado) ou como parte de um módulo (que forma um tipo de namespace). Mais informações sobre os módulos podem ser encontradas aqui: http://docs.angularjs.org/guide/module, mas em suma, um registraria um controlador em um módulo como este:

 angular.module('[module name]', []).controller('PhoneListCtrl', function($scope) { $scope.phones = [..]; $scope.orderProp = 'age'; }); 

O AngularJS usa uma forma de function global curta de declarar controladores em muitos exemplos, mas enquanto esta forma é boa para amostras rápidas, ela não deve ser usada em aplicações da vida real .

Resumindo: o AngularJS possibilita encapsular adequadamente as funções do controlador, mas também expõe uma maneira mais simples, rápida e suja de declará-las como funções globais.

Você pode registrar um controlador como parte de um módulo, conforme respondido por pkozlowski-opensource .

Se você precisar de minificação, você pode simplesmente estender isso fornecendo os nomes das variables ​​antes da function real em uma lista:

 angular.module('[module name]', []). controller('PhoneListCtrl', ['$scope', function($scope) { $scope.phones = [..]; $scope.orderProp = 'age'; }]); 

Isso funcionará o mesmo depois de “minification”:

 angular.module('[module name]', []). controller('PhoneListCtrl', ['$scope', function(s) { s.phones = [..]; s.orderProp = 'age'; }]); 

Essa notação pode ser encontrada em “Anotação Inline” na Injeção de Dependência .

Para testar um controlador, que foi registrado como parte de um módulo, você precisa pedir ao angular para criar seu controlador. Por exemplo:

 describe('PhoneListCtrl test', function() { var scope; var ctrl; beforeEach(function() { module('[module name]'); inject(function($rootScope, $controller) { scope = $rootScope.$new(); ctrl = $controller('[module name]', {$scope: scope}); }); }); it('should be ordered by age', function() { expect(scope.orderProp).toBe('age'); }); }); 

Esse método de teste do controlador pode ser encontrado em “Controladores de teste” em Entendendo o componente do controlador .