MongoDB
 sql >> Base de données >  >> NoSQL >> MongoDB

Comment extraire une instance d'un élément d'un tableau dans MongoDB ?

Vous avez donc raison de dire que le $pull L'opérateur fait exactement ce que dit la documentation en ce sens que ses arguments sont en fait une "requête" utilisée pour faire correspondre les éléments à supprimer.

Si le contenu de votre tableau a toujours l'élément en "première" position comme vous le montrez, alors le $pop l'opérateur supprime en fait ce premier élément.

Avec le pilote de nœud de base :

collection.findOneAndUpdate(
    { "array.0": "bird" },       // "array.0" is matching the value of the "first" element 
    { "$pop": { "array": -1 } },
    { "returnOriginal": false },
    function(err,doc) {

    }
);

Avec mangouste l'argument pour renvoyer le document modifié est différent :

MyModel.findOneAndUpdate(
    { "array.0": "bird" },
    { "$pop": { "array": -1 } },
    { "new": true },
    function(err,doc) {

    }
);

Mais ni l'un ni l'autre ne sont d'une grande utilité si la position du tableau du "premier" élément à supprimer n'est pas connue.

Pour l'approche générale ici, vous avez besoin de "deux" mises à jour, l'une pour faire correspondre le premier élément et le remplacer par quelque chose d'unique à supprimer, et la seconde pour supprimer réellement cet élément modifié.

C'est beaucoup plus simple si vous appliquez des mises à jour simples et ne demandez pas le document renvoyé, et cela peut également être fait en masse sur plusieurs documents. Il est également utile d'utiliser quelque chose comme async.series afin d'éviter d'imbriquer vos appels :

async.series(
    [
        function(callback) {
            collection.update(
                { "array": "bird" },
                { "$unset": { "array.$": "" } },
                { "multi": true }
                callback
            );
        },
       function(callback) {
           collection.update(
                { "array": null },
                { "$pull": { "array": null } },
                { "multi": true }
                callback
           );
       }
    ],
    function(err) {
       // comes here when finished or on error   
    }
);

Donc, en utilisant le $unset ici avec le positionnel $ l'opérateur permet de changer le "premier" élément en null . Puis la requête suivante avec $pull supprime simplement tout null entrée du tableau.

C'est ainsi que vous supprimez la "première" occurrence d'une valeur en toute sécurité d'un tableau. Déterminer si ce tableau contient plus d'une valeur identique est une autre question.