Hola, todos,
Estoy usando la versión 5.0.3 de la mangosta y la versión 9.4.0 del nodo. De acuerdo con la documentación de mangosta model.create debería devolver una promesa que, supongo, se resuelve cuando el documento creado se guarda en la base de datos. Sin embargo, como se muestra en el código a continuación, parece que la promesa se resuelve antes de que el documento se guarde en la base de datos.
async function test(){
let schema = new mongoose.Schema({a: String});
let model = mongoose.model('test', schema);
await model.remove({}).exec();
await model.create({ a: 'test'},
(err,result)=> {console.log('created');});
await model.findOneAndUpdate(
{ a : 'test' } ,
{ a: 'newValue'}
)
.exec((err, result) => {
console.log('update : '+result);
});
await model.find({a: 'test'},(err,result) => {
console.log(result);
});
}
output in terminal :
update : null
found :
created
findOneAndUpdate no encuentra ningún documento. Además de que "creado" aparece al final en la terminal, por lo tanto, la devolución de llamada del método de creación se ejecuta como si la espera no estuviera esperando a que se realizara la tarea asíncrona "crear".
Sin embargo, al agregar una promesa que se resuelve una vez que se activa la devolución de llamada de create, como se muestra a continuación, obtenemos el resultado esperado:
async function test(){
let schema = new mongoose.Schema({a: String});
let model = mongoose.model('test', schema);
await model.remove({}).exec();
await new Promise((resolve,reject) => {
model.create({ a: 'test'},
(err,result)=> {
console.log('created');
resolve();
});
});
await model.findOneAndUpdate(
{ a : 'test' } ,
{ a: 'newValue'}
)
.exec((err, result) => {
console.log('update : '+result);
});
await model.find({a: 'newValue'},(err,result) => {
console.log('found : ' +result);
});
}
output in terminal:
created
update : { _id: 5a735fbc1fe826233014d62d, a: 'test', __v: 0 }
found : { _id: 5a735fbc1fe826233014d62d, a: 'newValue', __v: 0 }
Ahora tenemos el resultado esperado.
Todas las funciones que operan en la base de datos devuelven una promesa que, si se resuelve, indica que la operación se ha realizado, específicamente Consulta. Supongo que ese también fue el caso de model.create aunque no devuelve un objeto de consulta estrictamente hablando. También me pregunto qué significa la promesa devuelta cumplida, ya que no muestra que el documento se haya creado en la base de datos. Quizás me perdí todo el punto, pero lo encuentro un poco ambiguo.
Creo recordar haber leído en los documentos 4.x que si pasa una devolución de llamada a model.create, no devuelve una promesa.
let x = model.create({ a: 'test' }, () => {})
x.then(console.log(x)) //TypeError: Cannot read property 'then' of undefined
si saca la devolución de llamada:
let x = model.create({ a: 'test' })
x.then(console.log(x)) // Promise { <pending> }
la fuente 5.x para model.js lo confirma llamando a utils.promiseOrCallback
Sí, @lineus es correcto, ¿puedo cerrar este problema @CodeurSauvage ?
@CodeurSauvage @lineus es correcto, mongoose 5 no devuelve una promesa si se especifica una devolución de llamada. Su secuencia de comandos funciona si reemplaza:
await model.create({ a: 'test'},
(err,result)=> {console.log('created');});
Con:
await model.create({ a: 'test'}).then(result => console.log('created'));
Comentario más útil
Creo recordar haber leído en los documentos 4.x que si pasa una devolución de llamada a model.create, no devuelve una promesa.
si saca la devolución de llamada:
la fuente 5.x para model.js lo confirma llamando a utils.promiseOrCallback