2013-11-08 5 views
0

Я очень новичок в mongodb и задаю основной вопрос, с которым у меня возникают проблемы. Как получить поле идентификатора документа, который уже был создан? Мне нужен идентификатор, поэтому я могу обновить/добавить новое поле в документ.Добавить новое поле в документ mongodb

//newProfile is an object, one string it holds is called school 
if(Schools.find({name: newProfile.school}).fetch().length != 1){ 
    var school = { 
     name: newProfile.school 
    } 
    Meteor.call('newSchool', school); 

    //Method 1 (doesn't work) 
    var schoolDoc = Schools.findOne({name: newProfile.school}); 
    Schools.update({_id: schoolDoc._id}, {$set: {enrolledStudents: Meteor.user()}}); 

    //Method 2? 
    //Schools.update(_id: <what goes here?>, {$push: {enrolledStudents: Meteor.user()}}); 
} 
else { 
    //Schools.update... <add users to an existing school> 
} 

Я создаю новый школьный документ, если указанная школа еще не существует. Школы должны содержать массив/список учеников (именно там у меня проблемы). Как добавить учащихся в новое поле (например, enrolledStudents)?

Спасибо!

ответ

0

Для чего вы пытаетесь сделать, нет необходимости получать _id. Когда вы используете update, просто выключите {_id: schoolDoc._id} с вашим запросом. Похоже, что использование {name: newProfile.school} будет работать, предполагая, что остальная часть вашего кода делает то, что вы хотите.

Хотя это будет работать с нормальным водителем Монго, я вижу, что метеор не позволяет ваш запрос на обновление, чтобы быть чем-нибудь, но _id: Meteor throws throwIfSelectorIsNotId exception

Во-первых, убедитесь, что вы тянете нужный документ, и вы может попробовать что-то вроде этого:

var school_id = Schools.findOne({name: newProfile.school})._id; 
Schools.update({_id: school_id}, { $push: { enrolledStudents: Meteor.user()}}); 

Если это не работает, вам придется сделать небольшую отладку, чтобы увидеть, что, в частности, об этом не работает.

+0

Когда я делаю это, я получаю сообщение об ошибке в веб-консоли «throwIfSelectorIsNotId» – Taylor

+0

Используете ли вы обычный драйвер Node Mongo, Mongoose или что-то еще? – EmptyArsenal

+0

драйвер узла mongo – Taylor

0

У меня возникли проблемы с пониманием того, что вы пытаетесь сделать. Вот мой анализ и понимание до сих пор с парой указателей придачу:

if(Schools.find({name: newProfile.school}).fetch().length != 1){ 

это было бы более эффективным

if(Schools.find({name: new Profile.school}).count() != 1) {

Meteor.call('newSchool', school);

Не уверен, что вы делаете здесь, если вы это будете запускать асинхронно, то есть к тому времени, когда остальная часть этого блока кода выполнила, скорее всего, эта функция Meteor.call() не была завершена на стороне сервера.

//Method 1 (doesn't work) 
var schoolDoc = Schools.findOne({name: newProfile.school}); 
Schools.update({_id: schoolDoc._id}, {$set: {enrolledStudents: Meteor.user()}}); 

Судя по заявлению, если в верхней части вашего кода, существует более чем одна школа с этим именем в базе данных. Поэтому я не уверен, что переменная schoolDoc - это запись, которую вы следите.

+0

Привет, Дейв, спасибо за вашу помощь. Чтобы уточнить ... Meteor.call («newSchool», школа) вызывает метод Meteor, называемый newSchool, который создает новый документ в коллекции Schools. первый оператор «если» проверяет, существует ли эта школа в коллекции «Школы», если она не создается с использованием текущей школы пользователей. Вторая часть (где у меня возникают проблемы) - это когда-то созданная школа, как я могу добавить первого пользователя и других пользователей, которые хотят присоединиться позже? Я пытаюсь использовать Schools.update ({...}), чтобы добавить начального ученика и будущих учеников в правильный школьный документ. – Taylor

0

Я считаю, что у вас возникают проблемы из-за асинхронного характера Meteor.call на клиенте.

Попробуйте сделать что-то вроде этого:

// include on both server and client 
Meteor.methods({ 
    newSchool: function (school) { 
    var newSchoolId, 
     currentUser = Meteor.user(); 
    if (!currentUser) throw new Meteor.Error(403, 'Access denied'); 

    // add some check here using the Meteor check/match function to ensure 'school' 
    // contains proper data 

    try { 
     school.enrolledStudents = [currentUser._id]; 
     newSchoolId = Schools.insert(school); 
     return newSchoolId; 
    } catch (ex) { 
     // handle appropriately 
    } 
    } 
}); 


// on client 
var schoolExists = false; 

if (Schools.findOne({name: newProfile.school})) { 
    schoolExists = true; 
} 

if (schoolExists) { 
    var school = { 
     name: newProfile.school 
     }; 
    Meteor.call('newSchool', school, function (err, result) { 
    if (err) { 
     alert('An error occurred...'); 
    } else { 
     // result is now the _id of the newly inserted record 
    } 
    }) 
} else { 

} 

В том числе метод на клиенте и на сервере позволяет Метеор сделать задержку компенсации и «» синтезированным вставку сразу на клиенте, не дожидаясь сервера округло поездка. Но вы также можете просто сохранить метод на стороне сервера.

Вы должны сделать часть зарегистрированных участников на сервере, чтобы предотвратить проникновение вредоносных пользователей вашими данными. Кроме того, вы, вероятно, не хотите фактически хранить весь пользовательский объект в массиве enrolledStudents, просто пользователь _id.

Смежные вопросы