Есть ли способ автоматически генерировать ObjectId, когда модель mongoose new'ed?
Есть ли способ объявить схему модели в мангусте, так что, когда модель будет new'ed, поле _id будет автоматически генерироваться?
например:
var mongoose = require('mongoose');
var Schema = mongoose.Schema;
var ObjectIdSchema = Schema.ObjectId;
var ObjectId = mongoose.Types.ObjectId;
var PersonSchema = new Schema({
_id: ObjectIdSchema,
firstName: {type: String, default: 'N/A'},
lastName: {type: String, default: 'N/A'},
age: {type: Number, min: 1}
});
var Person = mongoose.model('Person', PersonSchema);
сначала, я думал, отлично!, я просто сделаю
_id: {type:ObjectIdSchema, default: new ObjectId()}
но, конечно, это не работает, потому что новый ObjectId() вызывается только при инициализации схемы. поэтому вызов new Persion() дважды создает два объекта с одинаковым значением _id.
так есть ли способ сделать это, чтобы каждый раз, когда я делал "новый Person()", создаваемый новый ObjectId()?
причина, по которой я пытаюсь это сделать, заключается в том, что мне нужно знать значение нового значения _id для дальнейшей обработки.
Я также пробовал:
var person = new Person({firstName: "Joe", lastName: "Baz"});
person.save(function(err, doc, num){
console.log(doc._id);
});
даже тогда, doc не содержит ObjectId. но если я смотрю в базе данных, он ее содержит.
p.s. я использую mongoose 2.7.1
p.p.s. я знаю, что могу вручную создать ObjectId при создании человека как такового:
var person = new Person({_id: new ObjectId(), firstName: "Joe", lastName: "Baz"});
но мне не нужно импортировать ObjectId, и мне нужно его обновлять каждый раз, когда я хочу создать новое Person. думаю, я привык использовать java-драйвер для mongodb, где я могу просто создать значение для поля _id в конструкторе Model.
Ответы
Ответ 1
момент, когда вы вызываете var person = new Person();
person._id должен предоставить вам идентификатор (даже если он еще не сохранен). Просто создать экземпляр достаточно, чтобы дать ему идентификатор. Вы можете сохранить его после, и это сохранит идентификатор, а также остальную часть объекта person
Ответ 2
Добавьте флаг auto
:
_id: {
type: mongoose.Schema.Types.ObjectId,
index: true,
required: true,
auto: true,
}
источник
Ответ 3
Вместо:
_id: {type:ObjectIdSchema, default: new ObjectId()}
Вам следует:
_id: {type:ObjectIdSchema, default: function () { return new ObjectId()} }
Ответ 4
Взято из официального руководства MongoDB и Документов:
_Я бы
Поле, обязательное для заполнения в каждом документе MongoDB. Поле _id
должно иметь уникальное значение. Вы можете рассматривать поле _id
как первичный ключ документов. Если вы создаете новый документ без поля _id
, MongoDB автоматически создает поле и назначает уникальный BSON ObjectId.
Источник
ObjectID
ObjectIds являются маленькими, вероятно уникальными, быстро генерируемыми и упорядоченными. Значения ObjectId состоят из 12 байтов, где первые четыре байта представляют собой временную метку, которая отражает создание ObjectIds. В частности:
4-байтовое значение, представляющее секунды с начала эпохи Unix, 5-байтовое случайное значение и 3-байтовый счетчик, начиная со случайного значения. В MongoDB каждый документ, хранящийся в коллекции, требует уникального поля _id
которое действует как первичный ключ. Если вставлен документ опускает _id
поля, драйвер MongoDB автоматически генерирует ObjectId для _id
поля.
Это также относится к документам, вставленным через операции обновления с upsert: true.
Клиенты MongoDB должны добавить _id
поле с уникальным ObjectId. Использование ObjectIds для _id
поля предоставляет следующие дополнительные преимущества: в Монго оболочке, вы можете получить доступ к времени создания ObjectId, используя ObjectId.getTimestamp()
метод. сортировка по полю _id, в котором хранятся значения ObjectId, примерно эквивалентна сортировке по времени создания.
ВАЖНЫЙ
Хотя значения ObjectId должны увеличиваться со временем, они не обязательно являются монотонными. Это потому что они:
Содержит только одну секунду временного разрешения, поэтому значения ObjectId, созданные в одну и ту же секунду, не имеют гарантированного порядка и генерируются клиентами, которые могут иметь разные системные часы.
Источник
Явно объявляя _id
:
При явном объявлении поля _id
укажите параметр auto
:
new Schema({ _id: { type: Schema.ObjectId, auto: true }})
Только ObjectId - добавляет автоматически сгенерированный ObjectId по умолчанию, если turnOn имеет значение true.
Источник
TL; DR
Если вы создаете новый документ без поля _id, MongoDB автоматически создает поле и назначает уникальный BSON ObjectId.