Declaration of Controller AngularJS

3

Following the script below generated a doubt on which statement to use, in the AngularJS documentation I found the two forms in different examples, but I did not find an explanation of which statement is used or if there is any specific case to use.

application.js :

//Declaração da aplicacao
$myApp = angular.module('myApp',[]);

//Declaração dos controllers
var controller1 = function ($scope,$http){
 $scope.name = 'controller declaracao 1';
}

$myApp.controller('controller2',[ '$scope', '$http', function($scope, $http) {
 $scope.name = 'controller declaracao 2';
}]);

index.html :

<html ng-app="myApp">
<body>
  <div ng-controller="controller1">{{name}}</div>
  <div ng-controller="controller2" >{{name}}</div>
</body>
</html>

Doubt which way to use? Does it have performance differences?

Example on JSFiddle - https://jsfiddle.net/dyb8ne27/

    
asked by anonymous 07.04.2015 / 15:53

3 answers

1

claudsan your first controller works because it is being declared inside the global scope (window).

If you isolate the scope using Immediate-Invoked Function Expression (IIFE) your var controller1 will not be valid and your code will break as you will not find the variable.

example:

//Declaração da aplicacao
$myApp = angular.module('myApp',[]);

//Declaração dos controllers
var controller1 = function ($scope,$http){
 $scope.name = 'controller declaracao 1';
}

$myApp.controller('controller2',[ '$scope', '$http', function($scope, $http) {
 $scope.name = 'controller declaracao 2';
}]);

Error:

Error: [ng:areq] Argument 'controller1' is not a function, got undefined

Using IIFE you need to declare the controller1 as you declared the controller2, and Angular will make it possible to access controler1:

(function() {
  'use strict';

  //Declaração da aplicacao
  $myApp = angular.module('myApp',[]);

  //Declaração dos controllers
  var controller1 = function ($scope,$http){
   $scope.name = 'controller declaracao 1';
  };

  $myApp.controller('controller1', ['$scope', '$http', controller1]);

  $myApp.controller('controller2',[ '$scope', '$http', function($scope, $http) {
   $scope.name = 'controller declaracao 2';
  }]);

}());

I hope I have helped and remember that it is always good practice not to mess up the global scope (window).

If you want to learn more about IIFE, check out this link

    
24.02.2016 / 13:16
1

As far as performance is concerned, there is no difference whatsoever. But there are some differences that I will list below:

What happens when you use the ng-controller directive:

  • A new scope ($ scope) is created for each DOM element that uses the policy. In other words, you can have the same view (template) with several elements using the same controller.
  • The relationship between element and controller is quite explicit, since you know that this controller is being defined for a specific element of the DOM
  • When you use the inspect (console), it will be much easier to see where exactly the controller is being used since the ng-controller name will be visible in HTML.

What happens when you set the controller via a route:

  • A new scope ($ scope) is created for each route / url (route). That is, it will be available for the entire view (template) that is part of that route.
  • You can inject dependencies in the controller through the%% of route / url (route) property
  • There is no direct relationship between the controller and the view. The relationship exists between the controller and the route / url (route).

There is no right or wrong way to declare Controllers in AngularJS. The two acimas are correct and work. Everything will really depend on your project requirements - and sometimes even personal preference.

An example scenario for using the controller via a route / url (route), when you need to use the same template for two different url / routes, but the logic and data for each url / route should be different.

Since you need to use the same template (view), you can not use the ng-controller in the view, because it has to change depending on the route. So the solution is to define different controllers for each route and still use a single template.

I hope you have helped.

    
07.04.2015 / 19:10
0

I'm assuming your question is about the difference between the non-declaration version of dependency injections ...

var controller1 = function ($scope,$http){}

and the version with addition to the collection of injectables via method controller and declaration of dependencies:

$myApp.controller('controller2',[ '$scope', '$http', function($scope, $http) {}]);

If this is the case, let's break it down:

No declaration of dependency injections

Your code is doing the following:

var             // Declaração de variável no escopo atual
controller1 =   // Nome do controller
function (      // A interface da função definirá as dependências
$scope,         // Injeta a dependência para o módulo $scope 
                //     usando o handler default
$http           // Injeta a dependência para o módulo $http
                //     usando o handler default
){
...             // Corpo da função
}

This format keeps the code lean and smooth. Dependencies are resolved using your default handlers , which is convenient if you are using a default service repeatedly.

Since Angular has no idea what controller1 means, it will map the DOM to find an object with the same name, make sure that the object is a function, and that this function can be mapped as a controller . This takes time - not much, but it's an overhead .

With declaration of dependencies

$myApp          // Referência ao objeto que contém a aplicação
.controller(    // Declaração de controle 
'controller2',  // Nome do controller
[               // coleção de objetos; N referências a dependências,
                //     Último parâmetro será a função que as consome.
'$scope',       // Mapeando a dependência $scope para a posição 0
'$http',        // Mapeando a dependência $http para a posição 1
function(       // Interface da função
$scope,         // apelido (handler) da dependência na posição 0
$http           // apelido (handler) da dependência na posição 1
) {
...             // Corpo da função
}]);

This method is more complex, but offers more possibilities. Imagine that you want to write a generic controller that expects to receive a dependency that has the Get (id), GetAll (), Remove () methods.

Instead of rewriting your controller each time you need to implement a driver for each new implementation of this dependency, you will only need to change the mapped reference. Example:

Original

$myApp.controller('dep1Controller',[ '$scope', 'dep1svc', function($scope, dependencia) {}]);

New version

$myApp.controller('dep2Controller',[ '$scope', 'dep2svc', function($scope, dependencia) {}]);

The internal functions of the controllers will reference dependencia , completely ignorant if the called methods belong to dep1svc or dep2svc - thus allowing a greater abstraction of your code.

    
08.05.2015 / 19:53