sql >> Database >  >> RDS >> Mysql

Hoe vergrendel ik een InnoDB-rij die nog niet bestaat?

Hoewel het bovenstaande antwoord waar is, omdat een SELECT ... VOOR UPDATE zal voorkomen dat gelijktijdige sessies / transacties hetzelfde record invoegen, is dat niet de volledige waarheid. Ik kamp momenteel met hetzelfde probleem en ben tot de conclusie gekomen dat de SELECT ... FOR UPDATE in die situatie bijna nutteloos is om de volgende reden:

Een gelijktijdige transactie / sessie kan ook een SELECT ... FOR UPDATE doen op dezelfde record / indexwaarde, en MySQL accepteert dat graag onmiddellijk (niet-blokkerend) en zonder fouten te veroorzaken. Zodra de andere sessie dat heeft gedaan, kan natuurlijk ook jouw sessie het record niet meer invoegen. Noch uw noch de andere sessie / transactie krijgen informatie over de situatie en denken dat ze het record veilig kunnen invoegen totdat ze dit daadwerkelijk proberen. Proberen in te voeren leidt tot een impasse of tot een dubbele sleutelfout, afhankelijk van de omstandigheden.

Met andere woorden, SELECT ... FOR UPDATE voorkomt dat andere sessies de respectieve record(s) invoegen, MAAR zelfs als u een SELECT ... FOR UPDATE doet en het respectieve record niet wordt gevonden, is de kans groot dat u dit niet kunt dat record invoegen. IMHO, dat maakt de "first query, then insert" methode onbruikbaar.

De oorzaak van het probleem is dat MySQL geen enkele methode biedt om echt niet-bestaande records vergrendelen. Twee gelijktijdige sessies / transacties kunnen tegelijkertijd niet-bestaande records "FOR UPDATE" vergrendelen, iets wat eigenlijk niet mogelijk zou moeten zijn en de ontwikkeling aanzienlijk moeilijker maakt.

De enige manier om dit te omzeilen lijkt het gebruik van semafoortabellen of het vergrendelen van de hele tabel bij het invoegen. Raadpleeg de MySQL-documentatie voor meer informatie over het vergrendelen van hele tabellen of het gebruik van semafoortabellen.

Gewoon mijn 2 cent ...



  1. Datetime opslaan als UTC in PHP/MySQL

  2. SQLite-gebruikersmachtigingen

  3. Entity Framework core - Bevat is hoofdlettergevoelig of niet hoofdlettergevoelig?

  4. Netherlands Access Developer Day 2019 – 14 september