Requirements:
Similar to a message queue, multiple users simultaneously retrieve data from a table for processing, in order to ensure that each user obtains a different number and adds user_id immediately after the number is completed
db.foo.findOneAndUpdate({"user_id":{$exists:false}, {$set:{user_id:"123456"}},{sort:{_id:1}}})
Official documentsIt is not stated in whether the commandThread safety
If you have the following records
{"_id":1}
{"_id":2}
{"_id":3}
Is it possible that all 5 users come to request at the same time_id
A record of 1?
Using Python to develop a script to verify what seems to be thread safe but is not sure whether the application code is explicitly locked for safety reasons. Python code is as follows:
def query_and_set_user_id(user_id):
result = db.test.find_one_and_update({"user_id":{"$exists":False}},{'$set': {'user_id': user_id}}, sort=[("id", 1)])
print(threading.current_thread(), result)
return result
max_workers = 5
pool = ThreadPoolExecutor(max_workers)
futures = []
for i in range(max_workers):
f = pool.submit(query_and_set_user_id, "user_{}".format(i+1))
futures.append(f)
wait(futures)
It is thread safe.
In factfindAndModify
The behavior of the withupdate
It is the same, the two functions will not be interrupted between query and update. the difference isfindAndModify
You can also return documents before or after the update after the operation. More differences can be seen in the documentation:Comparisons with the update Method