Mongoose: atomic FindOne-Or-Insert(), do not update existing instance if found

Jeff Tanner

In Mongoose, I am seeking to perform atomically a way to Model.FindOne-Or-Insert(), similar functionality and signature as currently available Model.FindOneAndUpdate() except if an instance exists (i.e. matches filter) then do not update using provided object but return instance found as is, and if not exists (i.e. no match with filter) then insert object and return new instance.

I could not find a way using Model.FindOneAndUpdate() not to perform an update to an existing instance by trying out variances to its options and not providing fields to object that preferred not to update if instance exists.

So, my current non-atomic workaround is Model.FindOne() and if not found then perform Document.save().

const Foo = DB.model('foo', FooSchema)

async function findOneAndUpdateFoo(jsonFoo, next) {

  const filter = {
    deletedAt: null
  }
  if (jsonFoo.dsAccountId) {
    filter.dsAccountId = jsonFoo.dsAccountId
  }
  if (jsonIntegration.dsUserId) {
    filter.dsUserId = jsonIntegration.dsUserId
  }
  if (jsonFoo.providerId) {
    filter.providerId = jsonFoo.providerId
  }

  const fooDoc = {
    name: jsonFoo.name,
    dsAccountId: jsonFoo.dsAccountId,
    dsUserId: jsonFoo.dsUserId,
    providerId: jsonFoo.providerId,
    providerName: jsonFoo.providerName,

    // Most of these fields could be empty
    accessToken: jsonFoo.accessToken,
    refreshToken: jsonFoo.refreshToken,
    scope: jsonFoo.scope,
    tokenType: jsonFoo.tokenType,
    expiresAt: jsonFoo.expiresAt
  }

  return await Foo.findOneAndUpdate(
    filter, // find a document with that filter
    fooDoc, // document to insert when nothing was found
    { upsert: true, new: true, runValidators: true } // options
  )
    .catch(next)
}

Suggestions? Thank you

JohnnyHK

You can use $setOnInsert in your update parameter so that it will only apply in the insert case; with the update becoming a no-op in the case where the document already exists:

return await Foo.findOneAndUpdate(
  filter,                 // find a document with that filter
  {$setOnInsert: fooDoc}, // document to insert when nothing was found
  { upsert: true, new: true, runValidators: true }
)

Note that you should also create a unique index over the fields included in your filter and then handle the possibility of a duplicate error. See this post for the details why.

この記事はインターネットから収集されたものであり、転載の際にはソースを示してください。

侵害の場合は、連絡してください[email protected]

編集
0

コメントを追加

0

関連記事

分類Dev

mongoose findOne() is not a function

分類Dev

How to do a atomic find and save using mongoose in Node.js

分類Dev

Mongoose - Multer 内の FindOne()

分類Dev

Eloquent / Laravel: How to get last insert/update ID/instance of updateOrCreate()?

分類Dev

Mongoose.js findOne returning query metadata

分類Dev

How to mock mongoose query like findOne()?

分類Dev

How do I do atomic update using Bookshelf.js model?

分類Dev

Postgres INSERT ON CONFLICT DO UPDATE vsINSERTまたはUPDATE

分類Dev

mongoose.findOne()はnullを返します

分類Dev

In Core Data, how to do `if exists update else insert` in swift 4?

分類Dev

Mongoose bulk update operation

分類Dev

hashing password on update with mongoose

分類Dev

Mongoose update after save

分類Dev

Update existing JSON

分類Dev

Find existing instance of Office Application

分類Dev

Cascade insert of new and existing entities

分類Dev

update a document in mongodb using mongoose

分類Dev

Update specific value in array mongoose

分類Dev

how it works with mongoose multiple update?

分類Dev

Update a document with mongoose (update property of document property)

分類Dev

Realm order of insert or update

分類Dev

Update the data of an existing table in PHP

分類Dev

How to query findOne() in mongoose such that we get subset of array of documents which satisfy particular condition?

分類Dev

Mongoose.findOneは何も返しません、なぜですか?

分類Dev

Mongoose removeu alguns dados da resposta model.find e model.FindOne

分類Dev

how to insert an item to an array that is inside an object in mongoose?

分類Dev

Open file in existing instance of Visual Studio 2017

分類Dev

Deserialize to existing instance of classes in C#

分類Dev

Adding `__getattr__` method to an existing object instance

Related 関連記事

  1. 1

    mongoose findOne() is not a function

  2. 2

    How to do a atomic find and save using mongoose in Node.js

  3. 3

    Mongoose - Multer 内の FindOne()

  4. 4

    Eloquent / Laravel: How to get last insert/update ID/instance of updateOrCreate()?

  5. 5

    Mongoose.js findOne returning query metadata

  6. 6

    How to mock mongoose query like findOne()?

  7. 7

    How do I do atomic update using Bookshelf.js model?

  8. 8

    Postgres INSERT ON CONFLICT DO UPDATE vsINSERTまたはUPDATE

  9. 9

    mongoose.findOne()はnullを返します

  10. 10

    In Core Data, how to do `if exists update else insert` in swift 4?

  11. 11

    Mongoose bulk update operation

  12. 12

    hashing password on update with mongoose

  13. 13

    Mongoose update after save

  14. 14

    Update existing JSON

  15. 15

    Find existing instance of Office Application

  16. 16

    Cascade insert of new and existing entities

  17. 17

    update a document in mongodb using mongoose

  18. 18

    Update specific value in array mongoose

  19. 19

    how it works with mongoose multiple update?

  20. 20

    Update a document with mongoose (update property of document property)

  21. 21

    Realm order of insert or update

  22. 22

    Update the data of an existing table in PHP

  23. 23

    How to query findOne() in mongoose such that we get subset of array of documents which satisfy particular condition?

  24. 24

    Mongoose.findOneは何も返しません、なぜですか?

  25. 25

    Mongoose removeu alguns dados da resposta model.find e model.FindOne

  26. 26

    how to insert an item to an array that is inside an object in mongoose?

  27. 27

    Open file in existing instance of Visual Studio 2017

  28. 28

    Deserialize to existing instance of classes in C#

  29. 29

    Adding `__getattr__` method to an existing object instance

ホットタグ

アーカイブ