2014-09-07 3 views
0

Bonjour les gars je le code suivant ici:AngularJS pas en attente de requête HTTP à faire

angular.module('todomvc') 
.factory('todoStorage', function ($http) { 
    'use strict'; 

    var STORAGE_ID = 'todos-angularjs'; 

    return { 
     get: function() { 
      $http({method: 'GET', url: '/api/todo.php'}). 
      success(function(data, status, headers, config) { 
       // this callback will be called asynchronously 
       // when the response is available 
       return JSON.stringify(data); 
      }). 
      error(function(data, status, headers, config) { 
       // called asynchronously if an error occurs 
       // or server returns response with an error status. 
      }); 
     }, 

     put: function (todos) { 
      debugger; 
      localStorage.setItem(STORAGE_ID, JSON.stringify(todos)); 
     } 
    }; 
}); 

ainsi que

angular.module('todomvc') 
.controller('TodoCtrl', function TodoCtrl($scope, $routeParams, $filter, todoStorage, $http) { 
    'use strict'; 

    var todos = $scope.todos = todoStorage.get(); 

    $scope.newTodo = ''; 
    $scope.editedTodo = null; 

    $scope.$watch('todos', function (newValue, oldValue) { 
     $scope.remainingCount = $filter('filter')(todos, { completed: false }).length; 
     $scope.completedCount = todos.length - $scope.remainingCount; 
     $scope.allChecked = !$scope.remainingCount; 
     if (newValue !== oldValue) { // This prevents unneeded calls to the local storage 
      todoStorage.put(todos); 
     } 
    }, true); 

La question que j'ai est que la requête HTTP ne termine pas avant le code à $ scope. $ watch est en cours d'exécution, donc il appelle .length sur undefined. Je suis un total n00b à Angular et je voulais utiliser ce TodoMVC pour le faire fonctionner mais je ne suis pas sûr de ce que je peux faire pour arrêter tout le processus au lieu d'encapsuler le reste du code dans le rappel de succès de la requête http.

Merci à l'avance

+0

L'ensemble du code est terminé @ http://pastebin.com/5vkpHyUU – user3621357

+0

Utilisez-vous 'ngRoute'? Ensuite, vous pouvez utiliser la fonction de résolution. – zeroflagL

+0

@ user3621357 Avez-vous de la chance avec l'une des réponses? – PSL

Répondre

2

Problème

  • # 1 vous devez retourner la promesse de votre méthode get de votre usine, et utiliser $http.then au lieu de la promesse personnalisée de http méthode success.
  • # 2 vous devez l'enchaîner pour affecter une valeur à la propriété scope.
  • # 3 Lorsque vous regardez des propriétés affectées de manière asynchrone, vous devez effectuer une vérification NULL car la montre va s'exécuter lorsque le contrôleur est configuré.
  • # 4 Je ne suis pas sûr si vous devriez faire JSON.stringify la réponse parce que vous semblez avoir besoin d'un tableau de données?

Dans votre usine

return { 
    get: function() { 
     return $http({method: 'GET', url: '/api/todo.php'}). //Return here 
     then(function(response) { // 
      return response.data; 
     }, function(response) { 
      // called asynchronously if an error occurs 
      // or server returns response with an error status. 
     }); 
    }, 

Dans votre contrôleur: -

var todos; 
    todoStorage.get().then(function(data) { 
     todos = $scope.todos = data 
    }); 

et

$scope.$watch('todos', function (newValue, oldValue) { 
     if(!newValue) return; 
     $scope.remainingCount = $filter('filter')(todos, { completed: false }).length; 
     $scope.completedCount = todos.length - $scope.remainingCount; 
     $scope.allChecked = !$scope.remainingCount; 
     if (newValue !== oldValue) { // This prevents unneeded calls to the local storage 
      todoStorage.put(todos); 
     } 
    }, true); 
+0

Donc, je voudrais retourner une promesse de l'usine et une fois cela fait, le reste du code serait exécuté dans le contrôleur principal? – user3621357

+0

@ user3621357 Voir ma réponse, j'ai mentionné l'extrait de code, btw pourquoi faites-vous un JSON.stringify de la réponse. – PSL

+0

Je ne savais pas quelle meilleure façon de faire était? Sur l'API? – user3621357

0

$http est enveloppé dans une promesse. Vous pouvez retourner la promesse du service:

return $http({method: 'GET', url: '/api/todo.php'}) 

Dans le contrôleur, vous pouvez utiliser then méthode pour spécifier le comportement lorsque la demande est terminée:

$scope.newTodo = ''; 
$scope.editedTodo = null; 

todoStorage.get().then(function(result) { 

    $scope.todos = result.data; 

    $scope.$watch('todos', function (newValue, oldValue) { 
     $scope.remainingCount = $filter('filter')($scope.todos, { completed: false }).length; 
     $scope.completedCount = todos.length - $scope.remainingCount; 
     $scope.allChecked = !$scope.remainingCount; 
     if (newValue !== oldValue) { // This prevents unneeded calls to the local storage 
      todoStorage.put($scope.todos); 
     } 
    }, true); 
}); 

Un bon exemple sur la façon de promesses de la chaîne:

http://codepen.io/willh/pen/fCtuw

0

utilisent ce code:

angular.module('todomvc') 
    .factory('todoStorage', function ($http) { 
     'use strict'; 

    var STORAGE_ID = 'todos-angularjs'; 

    return { 
     get: function() { 
      return $http({method: 'GET', url: '/api/todo.php'}) 
     }, 

     put: function (todos) { 
      debugger; 
      localStorage.setItem(STORAGE_ID, JSON.stringify(todos)); 
     } 
    }; 
}); 


angular.module('todomvc') 
.controller('TodoCtrl', function TodoCtrl($scope, $routeParams, $filter, todoStorage, $http) { 
    'use strict'; 

    $scope.newTodo = ''; 
    $scope.editedTodo = null; 
    todoStorage.get() 
     .then(function(d){ 
      $scope.todos=d; 
    }) 
     .catch(function(e){ 
      console.error(e); 
     }) 

    $scope.$watch('todos', function (newValue, oldValue) { 
     $scope.remainingCount = $filter('filter')(todos, { completed: false }).length; 
     $scope.completedCount = todos.length - $scope.remainingCount; 
     $scope.allChecked = !$scope.remainingCount; 
     if (newValue !== oldValue) { // This prevents unneeded calls to the local storage 
      todoStorage.put(todos); 
     } 
    }, true); 
Questions connexes