Rosan Paudel
Rosan Paudel

Reputation: 170

I am not able to change the markdown while updating in mongodb

I am trying create an update route but whenever I try to update the content I can only update title and description & markdown but not sanitized html. How Can I udpate the sanitized html while I edit. Here is my article.js model.

const mongoose = require('mongoose');
const marked = require('marked');
const slugify = require('slugify');
const createDomPurify = require('dompurify');
const { JSDOM } = require('jsdom');
const dompurify = createDomPurify(new JSDOM().window);

const articleSchema = new mongoose.Schema({
  title: {
    type: String,
    required: true,
  },
  description: {
    type: String,
  },
  markdown: {
    type: String,
    required: true,
  },
  createdAt: {
    type: Date,
    default: Date.now,
  },
  slug: {
    type: String,
    required: true,
    unique: true,
  },
  sanitizedHtml: {
    type: String,
    required: true,
  },
});

articleSchema.pre('validate', function (next) {
  if (this.title) {
    this.slug = slugify(this.title, { lower: true, strict: true });
  }

  if (this.markdown) {
    this.sanitizedHtml = dompurify.sanitize(marked.parse(this.markdown));
  }

  next();
});

module.exports = mongoose.model('Article', articleSchema);

Here is my put route :

router.put('/:id', async (req, res) => {
  const { id } = req.params;
  const article = Article.findById(id);
  const newArticle = {
    title: req.body.title,
    description: req.body.description,
    markdown: req.body.markdown,
  };
  const updatedArticle = await Article.findByIdAndUpdate(id, newArticle);
  await updatedArticle.save();
  res.redirect(`/articles/${article.slug}`);
});

Upvotes: 0

Views: 122

Answers (2)

Fabian Strathaus
Fabian Strathaus

Reputation: 3570

You can find the answer in the mongoose documentation (https://mongoosejs.com/docs/middleware.html#notes):

Pre and post save() hooks are not executed on update(), findOneAndUpdate(), etc. You can see a more detailed discussion why in this GitHub issue. Mongoose 4.0 introduced distinct hooks for these functions.

Since the pre validation hook is internally called by pre save hook, your hook will not be called in your findByIdAndUpdate call. In order to enrich the data during this call as well, you should also define your function as an updateOne hook.

Upvotes: 1

HighDevWizards
HighDevWizards

Reputation: 166

const { id } = req.params;
const { title, description, markdown } = req.body;
const updateArticle = await Article.findByIdAndUpdate(
 { _id: id },
 {$set: { title, description, markdown } },
 {upset: true, new: true }
)
res.redirect(`/articles/${article.slug}`);

To my experience, findByIdAndUpdate function update the DB value, but don't return updated result. In order to get updated result, you might use { new: true }

Upvotes: 1

Related Questions