1

I try to find information about way to implement optimistic locks in Tarantool DB. This case doesn't covered in documentation so I can't get possible way for such action.

My goal is to find a way to resolve potential data collisions for concurent update of same tuples from multipal clients ( application servers ). For such load there is always lag between reading tuple and updating it - so there is room for race conditions. I try to avoid pessimistic locks in distributed system - for such locking we need additional component - and any addition of new component mast be done with many considerations in mind.

Mohsen Alyafei
  • 4,765
  • 3
  • 30
  • 42
cgi
  • 190
  • 1
  • 8

2 Answers2

1

That would be a stored procedure similar to the following (code is simplified):

function update_cas(key, tuple, version)
   local old = space:get(key)
   if old.version ~= version then error('Oops!') end
   tuple[VERSION_FIELD_NUMBER] = version + 1
   space:replace(tuple)
end

I hope it gives you the idea.

Dmitry Sharonov
  • 471
  • 2
  • 12
  • Thanks! As I can see from docs - such aproach is fine for in memory engine - there is no async operations - so whole procedure run without interrupts. Is there any holes if same goes to disk engine? – cgi Jul 22 '20 at 09:14
  • 1
    Yes, you should wrap it in box.begin/box.commit to be sure that such change is transactional then – Dmitry Sharonov Jul 22 '20 at 09:22
0

If I correctly understand your question I can suggest you following schema.

Add new field "version" or "timestamp" to your tuple. And check it before performing an update operation.

Example: I have a schema {id, value, version} and initial tuple {1, 0, 0}.

The first query request obtains tuple {1, 1, 0} and tries to perform update operation {{'+', 'value', 1}} and "only if version == 0". Then you go to the storage to save result. Before save you fetch original tuple and check that version is equal to "0" and then save tuple. Now you have updated tuple {1, 1, 1}.

Imagine you have the second request that tied to update the same tuple with operation {{'+', 'value', 2}} and again with "only if version == 0". You tries to save it but when you get tuple with id=1 you obtain {1, 1, 1}. That doesn't satisfy only_if_version == 0 condition (because current tuple version is 1). In this case you return error to your user.

Oleg Babin
  • 409
  • 3
  • 9
  • You essensialy correct in detail description of optimistic lock algorithm - my question is how implemet in tarantool part "only if version == 0" from your description. – cgi Jul 22 '20 at 09:09