Vad kan en försvagning av isoleringsnivån i databaser leda till?

Hej alla. Det är Vladislav Rodin här. Just nu är jag kursledare för kursen "Arkitekt för hög belastning" på OTUS, och jag undervisar också i kurser relaterade till mjukvaruarkitektur.

Förutom undervisning, som ni kanske har märkt, skriver jag originalmaterial för OTUS-bloggen på Habré och dagens artikel vill jag koppla till lanseringen av kursen "PostgreSQL", som just nu har öppnat för anmälningar.

Vad kan en försvagning av isoleringsnivån i databaser leda till?

Introduktion

I förra gången pratade vi om att transaktioner i databaser tjänar två syften: att säkerställa tillförlitlighet och åtkomst till data i en konkurrensutsatt miljö. För att dessa syften ska uppfyllas måste en transaktion uppfylla ACID-egenskaperna. Idag kommer vi att diskutera bokstaven I (isolation) i denna akronym.

Isolering

Isolering löser problemet med åtkomst till data i en konkurrensutsatt miljö, vilket i praktiken skyddar mot race conditions. Idealiskt betyder isolering serialisering, dvs. en egenskap som säkerställer att resultatet av att köra transaktioner parallellt är detsamma som om de utfördes sekventiellt. Det stora problemet med denna egenskap är att den är mycket svår att säkerställa tekniskt och därmed påverkar systemets prestanda kraftigt. Det är därför isolering ofta försvagas, vilket medför risker för uppkomst av vissa anomalier, som vi kommer att diskutera nedan. Möjligheten till uppkomsten av olika anomalier kännetecknar just isoleringsnivån för transaktioner.

De mest kända anomalierna är: dirty read, non-repeatable read, phantom read, men det finns faktiskt ytterligare 5: dirty write, cursor lost update, lost update, read skew, write skew.

Dirty write

Essensen av anomalien är att transaktioner kan skriva över ocommenderade data.

Vad kan en försvagning av isoleringsnivån i databaser leda till?

Denna anomali är farlig inte bara för att data kan krocka efter att båda transaktionerna har genomförts (som på bilden), utan också för att den bryter atomariteten: eftersom vi tillåter att skriva över ocommenderade data, är det oklart hur man kan rulla tillbaka en transaktion utan att påverka den andra.

Anomalien kan åtgärdas ganska enkelt: genom att sätta en lås på skrivningen innan skrivningen börjar, förhindrar vi andra transaktioner från att ändra posten tills låset har tagits bort.

Dirty read

Dirty read innebär att läsa obekräftade data.

Vad kan en försvagning av isoleringsnivån i databaser leda till?

Problem uppstår när man behöver fatta beslut eller vidta åtgärder baserat på urvalet.

För att åtgärda anomalien kan man låsa läsningen, men detta påverkar prestandan kraftigt. Det är mycket enklare att säga att för rollback av transaktionen måste det ursprungliga tillståndet av data (innan skrivning) sparas i systemet. Varför inte läsa därifrån? Det är ganska billigt, därför inaktiverar de flesta databaser dirty read som standard.

Lost update

Lost update innebär förlorade uppdateringar, och översättningen återspeglar problemet ganska bra:

Vad kan en försvagning av isoleringsnivån i databaser leda till?

Faktiskt har resultatet av transaktionen T2 annullerats. Denna situation kan åtgärdas med explicita eller implicita lås av posten. Det vill säga att vi antingen bara uppdaterar posten, vilket resulterar i ett implicerat lås, eller så utför vi select for update, vilket skapar en låsning både för läsning och skrivning. Observera att denna operation är ganska farlig: med vår "oskyldiga" läsning låser vi andra läsningar. Vissa databaser erbjuder en säkrare select for share, som gör det möjligt att läsa data men inte att ändra dem.

Cursor lost update

För mer i detaljkontroll kan databaser erbjuda andra verktyg, som t.ex. en kursör. En kursör är en struktur som innehåller en uppsättning för att iterera över rader. declare cursor_name for select_statement. Innehållet i kursören beskrivs av select.

Varför behövs en kursör? Det är så att vissa databaser erbjuder lås på alla poster som valts av select (read stability) eller endast på den post som för närvarande hanteras av kursören (cursor stability). Vid cursor stability görs en kort låsning, vilket minskar antalet låsningar om vi itererar över en stor uppsättning data. Därför särskiljs anomalien lost update för kursören.

Non-repeatable read

Non-repeatable read innebär att under utförandet av vår transaktion kommer 2 på varandra följande läsningar av samma post att ge olika resultat, eftersom en annan transaktion har blandat sig mellan dessa två läsningar, ändrat våra data och blivit bekräftad.

Vad kan en försvagning av isoleringsnivån i databaser leda till?

Varför är detta överhuvudtaget ett problem? Tänk dig att målet med transaktionen T2 på bilden är att välja alla varor vars pris är lägre än 150 enheter. Någon annan har uppdaterat priset till 200 enheter. Därmed fungerar inte den inställda filtreringen.

Dessa anomalier slutar uppstå vid användning av tvåfaslåsning eller en MVCC-mekanism, vilket jag skulle vilja diskutera separat.

Fantomläsning

En fantomläsning kallas de data som har lagts till av en annan transaktion.

Vad kan en försvagning av isoleringsnivån i databaser leda till?

Som ett exempel kan vi observera en felaktig urval av den billigaste produkten vid uppkomsten av denna anomali.

Att bli av med fantomläsningar är redan tillräckligt svårt. En vanlig låsning är inte tillräcklig, eftersom vi inte kan låsa något som ännu inte existerar. 2PL-system använder predikativ låsning, medan MVCC-systemet avbryter transaktioner som kan störas av insättning. Både den första och den andra mekanismen är ganska resurskrävande.

Läs-skevhet

Läs-skevhet uppstår när vi arbetar med flera tabeller vars innehåll ska förändras på ett koordinerat sätt.

Anta att vi har tabeller som representerar inlägg och deras meta-information:

Vad kan en försvagning av isoleringsnivån i databaser leda till?

En transaktion läser från tabellerna, en annan ändrar dem:

Vad kan en försvagning av isoleringsnivån i databaser leda till?

Som resultat av transaktionen T1 har inlägget titel = Good, och updated_by = T2, vilket skapar en viss inkonsekvens.

Detta är i själva verket en icke-repetitiv läsning, men med flera tabeller.

För att åtgärda detta kan T1 sätta lås på alla rader som den kommer att läsa, vilket hindrar transaktionen T2 från att ändra informationen. I fallet med MVCC kommer transaktionen T2 att avbrytas. Skyddet mot denna anomali kan bli viktigt om vi använder markörer.

Skriv-skevhet

Denna anomali är också lättare att förklara med ett exempel: anta att det i vårt system åtminstone en läkare måste vara i tjänst, men båda läkarna har beslutat att avbryta sina arbetspass:

Vad kan en försvagning av isoleringsnivån i databaser leda till?

Vad kan en försvagning av isoleringsnivån i databaser leda till?

Anomalien ledde till att ingen av läkarna kommer att gå i tjänst. Varför hände det? För att transaktionen kontrollerade ett villkor som kan brytas av en annan transaktion, och på grund av isoleringen såg vi inte denna förändring.

Detta är samma som en icke-repetitiv läsning. Som ett alternativ kan select-förfrågningar sätta lås på dessa poster.

Write skew och read skew är kombinationer av tidigare anomalier. Vi kan överväga write skew, som i grunden är en phantom read. Låt oss titta på en tabell som innehåller anställdas namn, deras löner och vilket projekt de arbetar med:

Vad kan en försvagning av isoleringsnivån i databaser leda till?

Vad kan en försvagning av isoleringsnivån i databaser leda till?

Som ett resultat får vi följande bild: varje chef trodde att deras ändringar inte skulle leda till budgetöverskridningar, vilket gjorde att de genomförde personaländringar som totalt ledde till överskridande av budgeten.

Orsaken till problemet är exakt densamma som vid phantom reading.

Slutsatser

Att sänka nivån av transaktionsisolering i databasen är en kompromiss mellan säkerhet och prestanda; valet av denna nivå bör baseras på potentiella risker för verksamheten vid uppkomsten av sådana eller andra anomalier.

Läs mer om kursen.

Källa: habr.com

Köp pålitlig webbhotell med DDoS-skydd, VPS VDS-servrar 🔥 Köp pålitlig webbhotell med DDoS-skydd, VPS VDS-servrar | ProHoster