Nous envisageons un système de réservation où il y a deux modèles impliqués: Store
et Reservation
. Store
a max_seats
et Reservation
a guests_count
colonne.Éviter les sur-réservations en raison des conditions de course
Pour éviter la surréservation, nous avons implémenté la validation. En cas de surréservation, la transaction est annulée. Mais je ne sais pas si cela est assez infaillible contre les conditions de course.
comme ceci:
class Store < ActiveRecord::Base
has_many :reservations
validates :max_seats, presence: true, numericality: true
end
class Reservation < ActiveRecord::Base
belongs_to :store
validates :guests_count, presence: true, numericality: true
after_create do
total_seats_taken = reservation_slot.reservations.sum(&:guests_count)
unless total_seats_taken <= store.max_seats
raise ActiveRecord::Rollback
end
end
end
Je soupçonnais ce scnenerio peut encore se produire, même si elle est rare:
On suppose que A et B client clients font une réservation de 6 sièges individuellement, max_seats
est défini sur 10. Si la transaction du client A est validée avant que le client B exécute le rappel after_create
, l'exception ActiveRecord::Rollback
est déclenchée et l'enregistrement du client B n'est pas créé, ce qui est prévu. Cependant, si le rappel after_create
est effectué avant la validation de la transaction du client A, je pense qu'il en résultera une situation de surréservation.
A commence transaction -> A effectue after_create
-> A commet transaction -> B effectue after_create
: B rencontre ActiveRecord::Rollback
exception
A commence transaction -> A effectue after_create
-> B effectue after_create
-> A commet transaction: Surréservation!!
Si vous pouviez partager des idées, je l'apprécierais grandement. Je vous remercie.