Follow

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use
Contact

Why I am getting Query was already executed error?

I have the following Schema and Model:

const userSchema = new mongoose.Schema({
  name: String,
})

const UserModel = mongoose.model('User', userSchema, 'users')

and I have written the following express middleware, which simply takes one argument, awaits that argument, set the returned value from that awaiting job to the req object on a property called gottenDocs, (i.e.: req.gottenDocs)

function getDocumentsMw(query) {
  return async (req, res, next) => {
    const dbRes = await query
    req.gottenDocs = dbRes
    
    next()
  }
}

and I have the following route:

MEDevel.com: Open-source for Healthcare and Education

Collecting and validating open-source software for healthcare, education, enterprise, development, medical imaging, medical records, and digital pathology.

Visit Medevel

app.get(
  '/users',
  getDocumentsMw(UserModel.find({})), 
  (req, res, next) => {
    const gottenDoc = req.gottenDocs
    res.status(200).json({
      status: 'success',
      data: gottenDoc,
    })
})

That’s all I have, now, when I request [ GET " /users " ] I recieve the following response which is great, and nothing is wrong:

{
  "status": "success",
  "data": []
}

but, the weird thing is when I request this route again, it throws this error:

MongooseError: Query was already executed: User.find({})

enter image description here

What could be the problem? is it a bug in Nodejs? which could be hmmm, something like, that it is not removing the function call from the call stack after the response has been sent?

any help appreciated.

>Solution :

The problem is on this line

getDocumentsMw(UserModel.find({})),

Here you create a query once the application start, because of that the query is created once but executed multiple times.

You may need to refactor your code to something like that

getDocumentsMw(() => UserModel.find({})),

Now you are passing a function and not a query. The function creates a query, aka factory. Next step is to refactor getDocumetnsMw to call the function to create a query when it needs to do something with it.

function getDocumentsMw(queryFactory) {
  return async (req, res, next) => {
    const dbRes = await queryFactory()
    req.gottenDocs = dbRes
    
    next()
  }
}

Add a comment

Leave a Reply

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use

Discover more from Dev solutions

Subscribe now to keep reading and get access to the full archive.

Continue reading