In the previous exercises, we looked at different ways to update and insert data into a collection. Now, we’ll learn about combining both operations using upsert
.
The upsert
option is an optional parameter we can use with update methods such as .updateOne()
. It accepts a boolean value, and if assigned to true
, upsert
will give our .updateOne()
method the following behavior:
- Update data if there is a matching document.
- Insert a new document if there’s no match based on the query criteria.
Let’s take a look at its syntax below:
db.<collection>.updateOne( <filter>, <update>, { upsert: <boolean> } );
The upsert
parameter is false by default. If the property is omitted, the method will only update the documents that match the query. If no existing documents match the query, the operation will complete without making any changes to the data.
To see the upsert
option in action, consider a collection named pets
, holding a large number of documents with the following structure:
{ _id: ObjectId(...), name: "Luna", type: "Cat", age: 2 }
Imagine it’s Luna’s birthday, and we want to be sure that we capture her current age, but we aren’t sure whether or not we have an existing document for her. This would be an excellent opportunity to use upsert
since one of two things will happen:
- If Luna does not exist in the database, our command will create the document
- If Luna does exist, the document will be updated
To upsert
our document for Luna, we can call the .updateOne()
command as follows:
db.pets.updateOne( { name: "Luna", type: "Cat"}, { $set: { age: 3 }}, { upsert: true } )
As noted, this command would search our pets
collection for a document where the name
is "Luna"
and the type
is "Cat"
. If such a document exists, its age
field would be updated. Otherwise, the following document would be inserted into our collection:
{ _id: ObjectId(...), name: "Luna", type: "Cat", age: 3 }
Let’s spend some time practicing using the upsert
option with the .updateOne()
method.
Instructions
Connect to the restaurants
database. Then, in the listingsAndReviews
collection, find and update the restaurant with the name
"Vinnys"
to have the following properties. If the document does not exist, it should be added with these properties.
{ borough: "Queens", cuisine: "Italian" }
Use the .findOne()
method to query the collection for the newly updated document. Use the name
field as the query.