Update Documents in MongoDB: updateOne, updateMany & upsert
Learn how to update MongoDB documents with updateOne() and updateMany(), update nested/embedded fields, and use upsert to insert-or-update in one call.
Update Documents in MongoDB
To modify existing documents, use updateOne() or updateMany(). Both take the same two arguments: a query that selects which document(s) to update, and an update document (almost always built with operators like $set) describing the change.
updateOne()
Updates only the first document that matches the query.
db.employees.updateOne({ empid: 201 }, { $set: { city: 'Mumbai' } })
// {
// acknowledged: true,
// matchedCount: 1,
// modifiedCount: 1,
// upsertedCount: 0
// }
Updating a Nested (Embedded) Field
db.employees.updateOne(
{ 'reportinmgr.mgrid': 110 },
{ $set: { 'reportinmgr.mgrprofile': 'Project Manager' } }
)
Adding a Brand-New Field
$set also works when the field doesn't exist yet — it simply creates it.
db.employees.updateOne({ city: "Palghar" }, { $set: { doj: new Date() } })
updateMany()
Same idea, but updates every document that matches the query.
db.employees.updateMany({ city: "Palghar" }, { $set: { doj: new Date() } })
// matchedCount: 3, modifiedCount: 3
db.employees.updateMany({}, { $set: { doj: new Date() } })
// an empty query object {} matches every document in the collection
upsert — Update or Insert
upsert (update + insert) is an option you pass as the third argument. If a matching document is found, it's updated as normal. If no document matches, MongoDB inserts a brand-new one using the update data.
db.employees.updateOne(
{ empid: 202 },
{ $set: { name: "Rajan11" } },
{ upsert: true }
)
// empid 202 exists -> this just updates it (upsertedCount: 0)
db.employees.updateOne(
{ empid: 212 },
{ $set: { name: "Rajan11", email: "rajan11@gmail.com", phone: 7894586523 } },
{ upsert: true }
)
// empid 212 doesn't exist -> a new document is inserted (upsertedCount: 1)
If you have a unique index on a field (like email) and omit it from the upsert data, MongoDB may throw a duplicate-key error trying to insert null for that field — always include your unique fields in the upsert document.
Common Errors & Troubleshooting
- Passing a plain object instead of an update operator —
updateOne({empid:201}, {city:'Mumbai'})(without$set) actually tries to replace the entire document with{city:'Mumbai'}, deleting every other field. Always wrap changes in$set(or another update operator) unless you genuinely intend a full replace. matchedCount: 0— the query didn't find any document at all; double-check the filter's field name and value type (a common cause: comparing a number field against a string value).modifiedCount: 0butmatchedCount: 1— the document was found, but the new value was identical to the existing one, so MongoDB considered nothing changed — this isn't an error.
Key Takeaways
updateOne()touches at most one document;updateMany()touches every match.- Both require an update operator like
$set— you can't just pass a plain replacement object without one (that would replace the whole document). { upsert: true }inserts a new document only when nothing matched the query.