Bonjour,

J'essaie de réaliser une petite application qui gère des marques-pages internet, que l'on peut ranger dans des boîtes. Le tout est une API REST codée avec Symfony et un client codé avec AngularJS.

J'en suis arrivé à la suppression d'une box, seulement, j'ai un souci: la suppression se fait bien en base de données, puisque lorsque j'actualise la page, la box est supprimée; mais la suppression n'apparaît pas tout de suite dans la liste des boxs, comme c'est le cas lorsque je crée une nouvelle box.

Mon code est disponible sur GitHub.

Je pense qu'il s'agit d'un problème d'héritage de la factory Bookmark dans la directive box.

Au passage, n'hésitez pas à dire ce que vous pensez de mon code, de la façon dont je l'organise (surtout pour le client). C'est mon premier projet avec AngularJS et je me demande si je m'y prends bien...

Merci par avance ! :)

5 réponses


Bonjour,

d'après ce que je vois, lorsque tu supprimes une box, tu recrées ton tableau de box dans ta factory mais tu ne refais jamais un appel pour obtenir ce nouveau tableau. Donc ton controller possède toujours l'ancien tableau contenant ta box. Il te faut donc récupérer ce nouveau tableau lorsque tu supprimes l'élément.

Qu'entends-tu par faire un appel pour obtenir ce nouveau tableau ? Je dois refaire une méthode GET ? Et comment passer le nouveau tableau au controller ? Ce que je ne comprends pas, c'est que c'est fait automatiquement lorsque j'ajoute une nouvelle box, mais pas lorsque je la supprime...

Alors voici un exemple fonctionnel : https://jsfiddle.net/prbaron/jnfkusue/.

Voici l'explication de ton code :

app.factory('BookmarksFactory', function($http, $q) {
    var factory = {
        boxes: [],
        getBoxes: function() {
            var deferred = $q.defer();
            $http.get(ROOT_URL + 'boxes')
                .success(function(data, status) {
                    // ici cette variable boxes n'existe pas donc JS va creer un var boxes = undefined avant var factory. (cf hoisting)
                    boxes = data;
                    deferred.resolve(boxes);
                }).error(function(data, status) {
                    deferred.reject(data.error);
                });
            return deferred.promise;
        },
        postBox: function(data) {
            var deferred = $q.defer();
            $http.post(ROOT_URL + 'boxes', {title: data})
                .success(function(data, status) {
                   // boxes ne fait pas reference a la valeur dans factory.boxes mais a la variable cree plus haut 
                   // ici tu ne crees pas un nouveau tableau mais tu ajoutes un element dedans
                    boxes.push(data);
                    deferred.resolve(data);
                }).error(function(data, status) {
                    deferred.reject(data.children);
                });
            return deferred.promise;
        },
        deleteBox: function(id) {
            var deferred = $q.defer();
            $http.delete(ROOT_URL + 'boxes/' + id)
                .success(function(data, status) {
                    // creation d'un nouveau tableau
                    newBoxes = [];
                    console.log(id);

                    // on ajoute les elements dans un tableau
                    for (var i = 0; i < boxes.length; i++) {
                        if (boxes[i].id!=id) {
                            newBoxes.push(boxes[i]);
                        }
                    }
                    // ici tu crees un nouveau tableau pour boxes
                    // tu perds donc le lien avec ton controller
                    boxes = newBoxes;
                    console.log(boxes);
                    deferred.resolve(boxes);
                }).error(function(data, status) {
                    deferred.reject(data.error);
                });
            return deferred.promise;
        }
    };
    return factory;
});

Une fois que tu as validé, je pourrais te donner des conseils sur comment améliorer ton code.

Voilà, j'ai corrigé mon code (et commité vers GitHub), la suppression d'une box fonctionne maintenant et je pense avoir compris où était mon erreur.

// attention a la minification pour ton injection de dependences. cf : http://thegreenpizza.github.io/2013/05/25/building-minification-safe-angular.js-applications/
app.factory('BookmarksFactory', function($http, $q) {
    var factory = {
        boxes: [],
        getBoxes: function() {
           //$http retourne une promesse donc pas besoin du defer
            var deferred = $q.defer();         
            $http.get(ROOT_URL + 'boxes')
                //.success()/.error() est depreciee dans la version 1.5, il vaut mieux utiliser .then()/.catch()
                .success(function(data, status) {
                    factory.boxes = data;
                    deferred.resolve(factory.boxes);
                }).error(function(data, status) {
                    deferred.reject(data.error);
                });
            return deferred.promise;
        },
        postBox: function(data) {
            var deferred = $q.defer();
            $http.post(ROOT_URL + 'boxes', {title: data})
                .success(function(data, status) {
                    factory.boxes.push(data);
                    deferred.resolve(data);
                }).error(function(data, status) {
                    deferred.reject(data.children);
                });
            return deferred.promise;
        },
        deleteBox: function(id) {
            var deferred = $q.defer();
            $http.delete(ROOT_URL + 'boxes/' + id)
                .success(function(data, status) {
                    var index = factory.boxes.findIndex(function(box) {
                        return box.id == id;
                    });
                    factory.boxes.splice(index, 1);
                    deferred.resolve(factory.boxes);
                }).error(function(data, status) {
                    deferred.reject(data.error);
                });
            return deferred.promise;
        }
    };
    return factory;
});

et le code corrigé

app.factory('BookmarksFactory', ['$http', '$q', function($http, $q) {
  return {
    boxes: [],
    getBoxes: function() {
      return $http.get(ROOT_URL + 'boxes')
        .then(function(data) {
          factory.boxes = data;
          return factory.boxes;
        })
        .catch(function(data) {
          return data.error;
        });
    },
    postBox: function(data) {
      return $http.post(ROOT_URL + 'boxes', {title: data})
        .then(function(data) {
          factory.boxes.push(data);
          return data;
        })
        .catch(function(data,) {
          return data.children;
        });
    },
    deleteBox: function(id) {
      return $http.delete(ROOT_URL + 'boxes/' + id)
        .then(function() {
          var index = factory.boxes.findIndex(function(box) {
            return box.id == id;
          });
          factory.boxes.splice(index, 1);
          return factory.boxes;
        })
        .catch(function(data) {
          return data.error;
        });
    }
  };
}]);