web-dev-qa-db-fra.com

Service de chargement AngularJS puis appelez le contrôleur et effectuez le rendu

Mon problème est que j'ai besoin d'un service chargé avant que le contrôleur soit appelé et que le modèle soit rendu. http://jsfiddle.net/g75XQ/2/

Html:

<div ng-app="app" ng-controller="root">
    <h3>Do not render this before user has loaded</h3>            
    {{user}}
</div>
​

JavaScript:

angular.module('app', []).
factory('user',function($timeout,$q){
    var user = {};            
    $timeout(function(){//Simulate a request
        user.name = "Jossi";
    },1000);
    return user;
}).
controller('root',function($scope,user){

    alert("Do not alert before user has loaded");
    $scope.user = user;

});
​

La

21
Jossi

Vous pouvez différer l'initialisation de angular en utilisant initialisation manuelle , au lieu de l'initialisation automatique avec ng-app attribut.

// define some service that has `$window` injected and read your data from it
angular.service('myService', ['$window', ($window) =>({   
      getData() {
          return $window.myData;
      }
}))    

const callService = (cb) => {
   $.ajax(...).success((data)=>{
         window.myData = data;
         cb(data)
   })
}

// init angular app 
angular.element(document).ready(function() {
       callService(function (data) {
          doSomething(data);
          angular.bootstrap(document);
       });
});

callService est votre fonction exécutant AJAX appel et acceptant le rappel de succès, qui initiera angular app.

Vérifiez également la directive ngCloak, car elle contient peut-être tout ce dont vous avez besoin.

Alternativement, lorsque vous utilisez ngRoute vous pouvez utiliser la propriété resolve, pour cela vous pouvez voir la réponse @honkskillet

14
vittore

encore mieux que l'amorçage manuel (ce qui n'est pas toujours une mauvaise idée non plus).

angular.module('myApp', ['app.services'])
   .run(function(myservice) {
      //stuff here.
   });
9
davidjnelson

Comme je l'ai dit dans les commentaires, il serait beaucoup plus facile de gérer un état non chargé dans votre contrôleur, vous pouvez bénéficier de $ q pour le rendre très simple: http://jsfiddle.net/g/g75XQ/ 4 /

si vous voulez faire quelque chose dans le contrôleur lorsque l'utilisateur est chargé: http://jsfiddle.net/g/g75XQ/6/

EDIT: Pour retarder le changement d'itinéraire jusqu'à ce que certaines données soient chargées, regardez cette réponse: Retarder le changement d'itinéraire AngularJS jusqu'au chargement du modèle pour éviter le scintillement

4
Guillaume86

La bonne façon d'y parvenir est d'utiliser la propriété de résolution sur la définition des routes: voir http://docs.angularjs.org/api/ngRoute.$routeProvider

puis créez et retournez une promesse en utilisant le service $ q; utilisez également $ http pour faire la demande et sur réponse, résolvez la promesse.

De cette façon, lorsque l'itinéraire est résolu et que le contrôleur est chargé, le résultat de la promesse sera déjà disponible et aucun scintillement ne se produira.

4
Ciul

Vous pouvez utiliser la résolution dans le .config $ routeProvider. Si une promesse est retournée (comme c'est le cas ici), l'itinéraire ne se chargera pas tant qu'il ne sera pas résolu ou rejeté. De plus, la valeur de retour sera disponible pour être injectée dans le contrôleur (dans ce cas Somert).

angular.module('somertApp')
  .config(function($routeProvider) {
    $routeProvider
      .when('/home/:userName', {
        /**/
        resolve: {
          Somert: function($q, $location, Somert) {
            var deferred = $q.defer();
            Somert.get(function(somertVal) {
              if (somertVal) {
                deferred.resolve(somertVal);
              } else {
                deferred.resolve();
                $location.path('/error/'); //or somehow handle not getting
              }
            });
            return deferred.promise;
          },
        },
      });
  });
1
honkskillet

Il existe plusieurs méthodes, certaines plus avancées que d'autres, mais dans votre cas, ng-hide fait l'affaire. Voir http://jsfiddle.net/roytruelove/g75XQ/3/

0
Roy Truelove