2014-05-21 15 views
10

Quando si crea nuovo documento e quindi provare a upsert una nuova sotto-documento ottengo questo errore:errore di chiave duplicata quando si crea una mangusta nuovo sub-documento

Object {error: "E11000 duplicate key error index: sales.users.$gro…p key: 
     { : ObjectId('537b7788da19c4601d061d04') }"} 
error: "E11000 duplicate key error index: sales.users.$groups.groupId_1 
     dup key: { : ObjectId('537b7788da19c4601d061d04') }" 
__proto__: Object 

Il sub-documento che sto cercando di inserire è definito come sotto-schema che ha un campo groupId con i requisiti {unique: true}, {sparse: true}. La chiamata al metodo mangusta che sto usando per fare l'upsert è:

User.findByIdAndUpdate(userId, 
         { $push: { 'groups': userUpdate} }, 
         function (err, obj) where userUpdate = { groupId: groupId }. 

Dopo aver lasciato gli indici il problema è stato risolto e questo errore non si verifica più.

var UserSchema = new Schema({ 
    email: { 
     type: String, 
     required: true, 
     unique: true 
    }, 
    active: { 
     type: Boolean, 
     default: true 
    }, 
    username: { 
     type: String, 
     required: true, 
     unique: true 
    }, 
    password: { 
     salt: { 
      type: String, 
      required: true 
     }, 
     hash: { 
      type: String, 
      required: true 
     } 
    }, 
    securityQuestion: { 
     question: String, 
     salt: String, 
     hash: String 
    }, 
    mobile: { 
     PIN: Number, 
     Number: Number 
    }, 
    createDate: { 
     type: Date, 
     default: Date.now 
    }, 
    updateDate: Date, 
    lastLoginDate: Date, 
    prevLoginDate: Date, 
    passChangeDate: Date, 
    locked: Boolean, 
    lockDate: Date, 
    failedCount: Number, 
    failedDate: Date, 
    profile: profile, 
    preference: preference, 
    courses: [UserCourseSchema], 
    groups: [UserGroupSchema], 
    rewards: [UserRewardSchema], 
    roles: UserRoleSchema, 
    scores: [UserScoreSchema] 
}); 

var UserGroupSchema = new Schema({ 
    groupId: { 
     type: Schema.Types.ObjectId, 
     unique: true, 
     sparse: true 
    }, 
    joinDate: { 
     type: Date, 
     default: Date.now 
    }, 
    receiveNotifications: { 
     type: Boolean, 
     default: true 
    }, 
    isAdmin: { 
     type: Boolean, 
     default: false 
    }, 
    isOwner: { 
     type: Boolean, 
     default: false 
    }, 
    isModerator: { 
     type: Boolean, 
     default: false 
    }, 
    updateDate: Date 
}); 
+0

Potrebbe estendere la domanda con lo schema dei documenti e con gli indici utilizzati? –

+1

Se stai cercando di assicurarti che un singolo utente non possa avere gruppi duplicati in 'groups', allora questo non funzionerà. Vedi http://stackoverflow.com/q/13907257/1259510 – JohnnyHK

+0

la cosa che non riesco a capire è che questo ** utenteUpdate ** ha l'_id? per precauzioni, elimina semplicemente la proprietà _id da questo oggetto prima di passare a $ push – Taha

risposta

0

La {unico nel suo genere: true} requisito sul campo groupId significa che non ci sono due documenti della collezione possono contenere lo stesso groupId, piuttosto che quello che intendeva, far rispettare l'unicità delle groupIds all'interno del documento. Puoi fare ciò che vuoi usando invece l'operatore MongoDB $addToSet.

1

Se si applica ups su array di oggetti, questo creerà sempre un nuovo documento in quanto non confronta i documenti secondari di un array e si dispone di un indice univoco su groupId, pertanto non consente di creare un nuovo record con lo stesso valore. Per questo dovresti trovare quel record e se esiste, quindi aggiornarlo altrimenti creare un nuovo record.

Un altro modo migliore è utilizzare $ addToSet. Spero che questo aiuti.

0

Se si sta tentando di aggiornare il gruppo esistente dall'array di gruppi, $ push non è la soluzione.

User.findAndUpdate({_id:userId,'groups.groupId': userUpdate.groupId}, 
         { $set: {'groups.$': userUpdate}}, 
         function (err, obj){}) 

altrimenti come altri $ addToSet suggeriti aggiungerà l'elemento nel set se esiste.

User.findByIdAndUpdate(userId, 
         { $addToSet : { 'groups': userUpdate} }, 
         function (err, obj){}) 
Problemi correlati