Zwykle rozwiązanie takich problemów ze współbieżnością obejmuje transakcje i optymistyczne blokowanie :kiedy aktualizujesz licznik, dodaj where
klauzula, aby sprawdzić starą wartość i policzyć liczbę zaktualizowanych wierszy.
v = select value from counter where id=x.
update counter set value = v+1 where value = v and id=x
Jeśli licznik został w międzyczasie zaktualizowany, aktualizacja nie zmieni żadnego wiersza — więc wiesz, że musisz wycofać i spróbować jeszcze raz transakcję.
Jednym z problemów jest to, że może to prowadzić do dużej konkurencji , z tylko kilkoma transakcjami, które się powiodły i wieloma niepowodzeniem.
Wtedy może być lepiej trzymać się pesymistycznego blokowania , gdzie najpierw blokujesz wiersz, a następnie go aktualizujesz. Ale tylko benchmark Ci powie.
EDYTUJ
Jeśli używasz transakcji bez optymistycznego blokowania, może się zdarzyć następujący scenariusz.
Max authorized = 50. Current value = 49.
T1: start tx, read value --> 49
T2: start tx, read value --> 49
T1: update value --> 50, acquire a row lock
T1: commits --> release the lock
T2: update value --> 50, acquire a row lock
T2: commits --> release the lock
Obie transakcje powiodły się, wartość wynosi 50, ale występuje niespójność.