0

I have a collection in MongoDB and I am able to use get in Express to retrieve the data. But when make a put request to update from the client it works but mongooseInstance.save().then((err, settings) ... the promise returns the payload as the error variable.

Here is the code:

const SettingsSchema = mongoose.Schema({
  _id: mongoose.Schema.Types.ObjectId,
  main_email: String,
  bio: String,
  gitHub_url: String,
  linkedin_url: String,
  bio_intro: String,
  bio_tagline: String,
  bio_pic: String
}),

SettingsModel = mongoose.model('profile_settings', SettingsSchema, 'profile_settings');

app.get('/profileSettings', (req, res) => {
  SettingsModel.find((err, settings) => {
    if (err) {
      res.status(500).send(err);
    } else {
      res.json(settings);
    }
  });
});

app.put('/profileSettings', (req, res) => {
  SettingsModel.findById("5ec40c318f3ebfe68a400e6f", (err, settings) => {
    if (err) {
      res.status(500).send(err);
    }
    if (settings) {
      settings.main_email = req.body.main_email;
      settings.bio_intro = req.body.bio_intro;
      settings.bio_tagline = req.body.bio_tagline;
      settings.bio_pic = req.body.bio_pic;
      settings.bio = req.body.bio;
      settings.linkedin_url = req.body.linkedin_url;
      settings.gitHub_url = req.body.gitHub_url;

      settings.save().then((err, settings) => {
        console.log('err: ', err);
        console.log('settings: ', settings);
        if (err) {
          res.status(500).send(err);
          //res.json(err);
        } else {
          res.json(settings);
        }
      }); 
    } else {
      res.status(404).send('Settings Failed to Update');
    }
  });
});

SO the get works as expected and the put actually updates all the values in the mongo db. But inside the save method the err and settings are both the same. When this code runs it sends a 500 error to the client even though everything worked on the backend.

      console.log('err: ', err);
      console.log('settings: ', settings);
      if (err) {
        res.status(500).send(err);
        //res.json(err);
      } else {
        res.json(settings);
      }
    });

if i put res.json(err) in the if(err){} then it returns the same as res.json(settings) and I get a 200 status but this doesn't let me properly handle errors.

Thanks in advance. Here are the versions I am using

node: 10.15.1

express: 4.16.1

mongoose: 5.9.14

mongoDB Atlas Service

1 Answers1

1

There is a mistake in the syntax of .then. You need to update it as shown below

settings.save().then(settings => {
 console.log('settings: ', settings);
 res.json(settings);
}, err => {
 console.log('err: ', err);
 res.status(500).send(err);
}); 
vishnu
  • 1,961
  • 2
  • 7
  • 11
  • Thank you that worked, So I guess the promise doesn't return the error as the first arg? I ended up using your method but with a catch instead. – Craig Bauer May 26 '20 at 18:01
  • settings.save() .then(settings => { console.log('settings: ', settings); res.json(settings); }) .catch( err => { console.log('err: ', err); res.status(500).send(err); }); – Craig Bauer May 26 '20 at 18:01
  • Also I tried breaking the model and it didn't save in mongo but also didn't throw an error. I wonder what it would take for the save method to throw an error. I got a 200 back to the client but my data didn't save. – Craig Bauer May 26 '20 at 18:10
  • Yes, you can you `catch` block also, you can check this out to choose the best approach for your use case https://stackoverflow.com/questions/33278280/promise-then-vs-then-catch – vishnu May 26 '20 at 18:10
  • I exactly didn't understand regarding breaking the model. But let's say you need to check promise rejection scenario one simple option would be add a temporary field in your model for testing purpose and mark it as `required:true` and save without that field. You will get validation error – vishnu May 26 '20 at 18:19
  • I just meant I re-named a couple keys in the model to try and get an error to test the handler. Thanks for the tip. Really appreciate it. – Craig Bauer May 26 '20 at 19:39