Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Jag föreslår att du läser utskriften av rapporten från början av 2016 av Andrey Salnikov "Typiska fel i applikationer som leder till uppblåsthet i postgresql"

I denna rapport kommer jag att analysera de huvudsakliga felen i applikationer som uppstår vid design och skrivning av applikationskod. Och jag tar bara de fel som leder till uppblåsthet i Postgresql. Som regel är detta början på slutet av prestandan för ditt system som helhet, även om initialt inga förutsättningar för detta var synliga.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Glad att välkomna alla! Den här rapporten är inte lika teknisk som den tidigare från min kollega. Den här rapporten riktar sig främst till utvecklare av backend-system eftersom vi har ett ganska stort antal kunder. Och de gör alla samma misstag. Jag ska berätta om dem. Jag kommer att förklara vilka ödesdigra och dåliga saker dessa misstag leder till.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Varför görs misstag? De görs av två skäl: slumpmässigt, kanske det löser sig och på grund av okunnighet om vissa mekanismer som uppstår på nivån mellan databasen och applikationen, såväl som i själva databasen.

Jag ska ge dig tre exempel med hemska bilder på hur illa det gick. Jag ska kort berätta om mekanismen som händer där. Och hur man hanterar dem, när de hände och vilka förebyggande metoder man ska använda för att förhindra misstag. Jag ska berätta om hjälpverktygen och tillhandahålla användbara länkar.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Jag använde en testdatabas där jag hade två tabeller. En skylt med kundkonton, den andra med transaktioner på dessa konton. Och med viss frekvens uppdaterar vi saldonen på dessa konton.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Initial data för plattan: den är ganska liten, 2 MB. Svarstiden för databasen och specifikt för skylten är också mycket bra. Och en ganska bra belastning - 2 000 operationer per sekund enligt plattan.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Och genom denna rapport kommer jag att visa dig grafer så att du tydligt kan förstå vad som händer. Det kommer alltid att finnas 2 diabilder med grafer. Den första bilden är vad som händer i allmänhet på servern.

Och i det här läget ser vi att vi verkligen har ett litet tecken. Indexet är litet på 2 MB. Detta är den första grafen till vänster.

Den genomsnittliga svarstiden på servern är också stabil och kort. Detta är den övre högra grafen.

Den nedre vänstra grafen visar de längsta transaktionerna. Vi ser att transaktioner genomförs snabbt. Och autovacuum fungerar inte här än, eftersom det var ett starttest. Det kommer att fortsätta att fungera och kommer att vara användbart för oss.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Det andra objektglaset kommer alltid att vara dedikerat till plåten som testas. I denna situation uppdaterar vi ständigt kundens kontosaldon. Och vi ser att den genomsnittliga svarstiden för en uppdatering är ganska bra, mindre än en millisekund. Vi ser att processorresurserna (detta är den övre högra grafen) också förbrukas jämnt och ganska litet.

Den nedre högra grafen visar hur mycket drift- och diskminne vi går igenom på jakt efter vår önskade linje innan vi uppdaterar den. Och antalet operationer enligt skylten är 2 000 per sekund, som jag sa i början.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Och nu har vi en tragedi. Av någon anledning finns det en sedan länge glömd transaktion. Orsakerna är vanligtvis alla banala:

  • En av de vanligaste är att vi började komma åt en extern tjänst i applikationskoden. Och den här tjänsten svarar oss inte. Det vill säga vi öppnade en transaktion, gjorde en förändring i databasen och gick från applikationen till att läsa mail eller till en annan tjänst inom vår infrastruktur, och av någon anledning svarar den inte på oss. Och vår session har fastnat i ett tillstånd där det är okänt när det kommer att lösas.
  • Den andra situationen är när ett undantag inträffade i vår kod av någon anledning. Och i undantagsfall behandlade vi inte avslutandet av transaktionen. Och vi slutade med en hängsession med en öppen transaktion.
  • Och det sista är också ett ganska vanligt fall. Detta är kod av låg kvalitet. Vissa ramverk öppnar en transaktion. Den hänger, och du kanske inte vet i applikationen att du har den hängande.

Vart leder sådana saker?

Till den grad att våra tabeller och index börjar svälla dramatiskt. Detta är exakt samma svullnadseffekt. För databasen kommer detta att innebära att databasens svarstid kommer att öka mycket kraftigt och belastningen på databasservern ökar. Och som ett resultat kommer vår ansökan att lida. För om du spenderade 10 millisekunder i din kod på en begäran till databasen, 10 millisekunder på din logik, så tog din funktion 20 millisekunder att slutföra. Och nu kommer din situation att vara helt sorglig.

Och låt oss se vad som händer. Den nedre vänstra grafen visar att vi har en lång lång transaktion. Och om vi tittar på den övre vänstra grafen ser vi att storleken på vår tabell plötsligt har hoppat från två megabyte till 300 megabyte. Samtidigt har mängden data i tabellen inte förändrats, det vill säga att det finns en ganska stor mängd skräp där.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Den allmänna situationen när det gäller den genomsnittliga serverns svarstid har också förändrats i flera storleksordningar. Det vill säga att alla förfrågningar på servern började sjunka helt. Och samtidigt lanserades interna Postgres-processer i form av autovacuum, som försöker göra något och tär på resurser.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Vad händer med vår skylt? Det samma. Vår genomsnittliga svarstid enligt skylten har hoppat upp flera storleksordningar. Specifikt när det gäller förbrukade resurser ser vi att belastningen på processorn har ökat kraftigt. Detta är den övre högra grafen. Och det har ökat eftersom processorn måste sortera igenom ett gäng värdelösa rader på jakt efter den som behövs. Detta är den nedre högra grafen. Och som ett resultat började vårt antal samtal per sekund att sjunka väldigt markant, eftersom databasen inte hann behandla samma antal förfrågningar.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Vi måste komma tillbaka till livet. Vi går online och får reda på att långa transaktioner leder till problem. Vi hittar och dödar den här transaktionen. Och allt börjar bli normalt för oss. Allt fungerar som det ska.

Vi lugnade ner oss, men efter ett tag börjar vi märka att applikationen inte fungerar på samma sätt som innan akuten. Förfrågningar behandlas fortfarande långsammare och betydligt långsammare. En och en halv till två gånger långsammare specifikt i mitt exempel. Belastningen på servern är också högre än den var före olyckan.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Och frågan: "Vad händer med basen just nu?" Och följande situation uppstår med basen. På transaktionsdiagrammet kan du se att det har stannat och det finns verkligen inga långsiktiga transaktioner. Men storleken på skylten ökade dödligt under olyckan. Och sedan dess har de inte minskat. Medeltiden på basen har stabiliserats. Och svaren verkar komma tillräckligt med en hastighet som är acceptabel för oss. Autovakuumet blev mer aktivt och började göra något med skylten, eftersom den behöver sålla igenom mer data.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Närmare bestämt enligt testskylten med konton, där vi ändrar saldon: svarstiden för en förfrågan verkar ha återgått till det normala. Men i verkligheten är den en och en halv gånger högre.

Och från belastningen på processorn ser vi att belastningen på processorn inte har återgått till det önskade värdet innan kraschen. Och orsakerna där ligger just i den nedre högra grafen. Det kan ses att en viss mängd minne genomsöks där. Det vill säga, för att hitta den nödvändiga raden slösar vi med resurserna på databasservern samtidigt som vi sorterar genom värdelös data. Antalet transaktioner per sekund har stabiliserats.

Överlag bra, men situationen är värre än den var. Rensa databasförsämring som en konsekvens av vår applikation som fungerar med denna databas.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Och för att förstå vad som händer där, om du inte var på den förra rapporten, låt oss nu ta en liten teori. Teori om den interna processen. Varför en bildammsugare och vad gör den?

Bokstavligen kort för förståelse. Någon gång i tiden har vi ett bord. Vi har rader i tabellen. Dessa linjer kan vara aktiva, levande och vad vi behöver nu. De är markerade med grönt på bilden. Och det finns deadlines som redan har utarbetats, har uppdaterats och nya poster har dykt upp på dem. Och de markeras att de inte längre är intressanta för databasen. Men de finns i tabellen på grund av en Postgres-funktion.

Varför behöver du en bildammsugare? Autovacuum kommer vid något tillfälle, kommer åt databasen och frågar den: "Vänligen ge mig ID:t för den äldsta transaktionen som för närvarande är öppen i databasen." Databasen returnerar detta id. Och autovakuumet, beroende på det, sorterar igenom raderna i tabellen. Och om han ser att vissa rader har ändrats av mycket äldre transaktioner, så har han rätt att markera dem som rader som vi kan återanvända i framtiden genom att skriva ny data där. Detta är en bakgrundsprocess.

För närvarande fortsätter vi att arbeta med databasen och fortsätter att göra några ändringar i tabellen. Och på dessa rader, som vi kan återanvända, skriver vi ny data. Och därmed får vi en cykel, d.v.s. hela tiden dyker det upp några döda gamla rader där, istället för dem skriver vi ner nya rader som vi behöver. Och detta är ett normalt tillstånd för PostgreSQL att fungera.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Vad hände under olyckan? Hur gick den här processen till där?

Vi hade en skylt i något skick, en del live, några deadlines. Bildammsugaren har anlänt. Han frågade databasen vad vår äldsta transaktion är och vad dess id är. Jag fick detta ID, som kan vara många timmar sedan, kanske tio minuter sedan. Det beror på hur stor belastning du har på din databas. Och han letade efter linjer som han kunde markera som återanvända. Och jag hittade inte sådana rader i vår tabell.

Men vid det här laget fortsätter vi att arbeta med tabellen. Vi gör något i det, uppdaterar det, ändrar data. Vad ska databasen göra vid det här laget? Hon har inget annat val än att lägga till nya rader i slutet av den befintliga tabellen. Och därmed börjar vår bordsstorlek att svälla.

I verkligheten behöver vi gröna linjer för att fungera. Men under ett sådant problem visar det sig att andelen gröna linjer är extremt låg genom hela tabellen.

Och när vi kör en fråga måste databasen gå igenom alla rader: både röda och gröna, för att hitta den önskade raden. Och effekten av att svälla en tabell med värdelös data kallas "bloat", vilket också äter upp vårt diskutrymme. Kom ihåg att det var 2 MB, det blev 300 MB? Ändra nu megabyte till gigabyte och du kommer snabbt att förlora alla dina diskresurser.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Vilka konsekvenser kan det få för oss?

  • I mitt exempel växte tabellen och indexet 150 gånger. Några av våra kunder har haft fler dödsfall när de helt enkelt börjat få slut på diskutrymme.
  • Storleken på själva borden kommer aldrig att minska. Autovacuum kan i vissa fall skära av bordets svans om det bara finns deadlines. Men eftersom det är konstant rotation kan en grön linje frysa i slutet och inte uppdateras, medan alla andra kommer att skrivas ner någonstans i början av plattan. Men det här är en så osannolik händelse att ditt bord i sig kommer att krympa i storlek, så du bör inte hoppas på det.
  • Databasen måste sortera igenom en hel massa värdelösa rader. Och vi slösar diskresurser, vi slösar processorresurser och elektricitet.
  • Och detta påverkar direkt vår applikation, för om vi i början spenderade 10 millisekunder på förfrågan, 10 millisekunder på vår kod, så började vi under kraschen att spendera en sekund på begäran och 10 millisekunder på koden, det vill säga en order på storleken i applikationsprestanda minskade. Och när olyckan var löst började vi lägga 20 millisekunder på en förfrågan, 10 millisekunder på en kod. Det betyder att vi fortfarande sjönk en och en halv gånger i produktivitet. Och allt detta beror på en transaktion som frös, kanske på grund av vårt fel.
  • Och frågan: ”Hur kan vi få tillbaka allt?” så att allt är bra hos oss och förfrågningar kommer in lika snabbt som innan olyckan.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

För detta ändamål finns det en viss cykel av arbete som utförs.

Först måste vi hitta de problematiska tabellerna som är uppsvällda. Vi förstår att i vissa tabeller är inspelningen mer aktiv, i andra mindre aktiv. Och för detta använder vi tillägget pgstattuple. Genom att installera detta tillägg kan du skriva frågor som hjälper dig att hitta tabeller som är ganska uppsvällda.

När du har hittat dessa tabeller måste du komprimera dem. Det finns redan verktyg för detta. I vårt företag använder vi tre verktyg. Den första är den inbyggda VACUUM FULL. Han är grym, hård och skoningslös, men ibland är han väldigt användbar. Pg_repack и pgcompacttable - Det här är tredjepartsverktyg för att komprimera tabeller. Och de behandlar databasen mer noggrant.

De används beroende på vad som är bekvämare för dig. Men jag ska berätta om det här i slutet. Huvudsaken är att det finns tre verktyg. Det finns massor att välja på.

Efter att vi har rättat till allt och sett till att allt är bra måste vi veta hur vi kan förhindra denna situation i framtiden:

  • Det kan förebyggas ganska enkelt. Du måste övervaka sessionernas varaktighet på masterservern. Särskilt farliga sessioner i viloläge i transaktionstillstånd. Det här är de som precis har öppnat en transaktion, gjort något och lämnat, eller helt enkelt hängt, gått vilse i koden.
  • Och för dig som utvecklare är det viktigt att testa din kod när dessa situationer uppstår. Det är inte svårt att göra. Detta kommer att vara en användbar kontroll. Du slipper ett stort antal "barnsliga" problem i samband med långa transaktioner.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

I dessa grafer ville jag visa hur tecknet och databasens beteende förändrades efter att jag gick igenom skylten med VACUUM FULL i det här fallet. Det här är inte produktion för mig.

Tabellstorleken återgick omedelbart till sitt normala driftläge på ett par megabyte. Detta påverkade inte nämnvärt den genomsnittliga svarstiden för servern.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Men specifikt för vår testskylt, där vi uppdaterade kontosaldon, ser vi att den genomsnittliga svarstiden för en begäran om att uppdatera data i skylten reducerades till nivåer före nödsituationer. Resurserna som förbrukades av processorn för att slutföra denna begäran sjönk också till nivåerna före kraschen. Och den nedre högra grafen visar att nu hittar vi exakt den linje som vi behöver direkt, utan att gå igenom högarna med döda linjer som fanns innan bordet komprimerades. Och den genomsnittliga förfrågningstiden förblev på ungefär samma nivå. Men här har jag snarare ett fel i min hårdvara.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Det är här den första historien slutar. Det är det vanligaste. Och det händer alla, oavsett kundens erfarenhet och hur kvalificerade programmerarna är. Förr eller senare händer detta.

Den andra historien, där vi fördelar belastningen och optimerar serverresurser

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

  • Vi har redan vuxit upp och blivit seriösa killar. Och vi förstår att vi har en kopia och det skulle vara bra för oss att balansera belastningen: skriv till Mästaren och läs från repliken. Och vanligtvis uppstår denna situation när vi vill förbereda några rapporter eller ETL. Och näringslivet är mycket glada över detta. Han vill verkligen ha en mängd olika rapporter med mycket komplexa analyser.
  • Rapporter tar många timmar, eftersom komplexa analyser inte kan beräknas i millisekunder. Vi, som modiga killar, skriver kod. I insättningsapplikationen gör vi inspelningen på mastern och utför rapporterna på repliken.
  • Fördelning av lasten.
  • Allt fungerar perfekt. Var bra.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Och hur ser den här situationen ut? Specifikt på dessa grafer lade jag också till varaktigheten för transaktioner från repliken för transaktionslängden. Alla andra grafer hänvisar endast till masterservern.

Vid det här laget hade min rapporttavla växt. Det finns fler av dem. Vi ser att den genomsnittliga serverns svarstid är stabil. Vi ser att på repliken har vi en långvarig transaktion som pågår i 2 timmar. Vi ser den tysta driften av autovakuum, som behandlar deadlines. Och allt är bra med oss.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Specifikt, enligt den testade plattan, fortsätter vi att uppdatera kontosaldon där. Och vi har även en stabil svarstid för förfrågningar, stabil resursförbrukning. Allt är bra med oss.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Allt är bra tills det ögonblick dessa rapporter börjar skickas tillbaka på grund av en konflikt med replikering. Och de skjuter tillbaka med jämna mellanrum.

Vi går online och börjar läsa varför detta händer. Och vi hittar en lösning.

Den första lösningen är att öka replikeringslatensen. Vi vet att vår rapport löper i 3 timmar. Vi ställer in replikeringsfördröjningen till 3 timmar. Vi lanserar allt, men vi har fortfarande problem med att rapporter ibland ställs in.

Vi vill att allt ska vara perfekt. Vi klättrar vidare. Och vi hittade en cool inställning på Internet - hot_standby_feedback. Låt oss slå på den. Hot_standby_feedback tillåter oss att hålla tillbaka autovakuumet på Mastern. Därmed blir vi helt av med replikeringskonflikter. Och allt fungerar bra för oss med rapporter.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Och vad händer med Master-servern just nu? Och vi har totalt problem med masterservern. Nu ser vi graferna när jag har båda dessa inställningar aktiverade. Och vi ser att sessionen på vår replik på något sätt började påverka situationen på Master-servern. Hon har en effekt eftersom hon pausade autovakuumet, vilket rensar ut deadlines. Vår bordsstorlek har skjutit i höjden igen. Den genomsnittliga exekveringstiden för frågor över hela databasen sköt också i höjden. Autodammsugarna stramade till lite.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Specifikt, från vår skylt, ser vi att datauppdateringen på den också hoppade till skyarna. CPU-förbrukningen har på samma sätt ökat kraftigt. Vi går återigen igenom ett stort antal döda, värdelösa rader. Och svarstiden för denna skylt och antalet transaktioner har sjunkit.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Hur kommer det se ut om vi inte vet vad jag pratade om innan?

  • Vi börjar leta efter problem. Om vi ​​stötte på problem i den första delen vet vi att detta kan bero på en lång transaktion och gå till Mästaren. Vi har ett problem med Mästaren. Korvar honom. Den värms upp, dess belastningsmedelvärde är ungefär hundra.
  • Förfrågningar där är långsamma, men vi ser inga långvariga transaktioner där. Och vi förstår inte vad som gäller. Vi förstår inte var vi ska leta.
  • Vi kontrollerar serverutrustning. Kanske kraschade vår raid. Kanske är vårt minne utbränt. Ja, allt kan hända. Men nej, servrarna är nya, allt fungerar bra.
  • Alla är igång: administratörer, utvecklare och regissören. Ingenting hjälper.
  • Och någon gång börjar allt plötsligt rätta till sig.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Vid denna tidpunkt bearbetades begäran om vår replik och lämnades. Vi fick rapporten. Affärerna är fortfarande nöjda. Som ni ser har vår skylt växt igen och kommer inte att krympa. På grafen med sessioner lämnade jag en bit av denna långa transaktion från en replika så att du kan uppskatta hur lång tid det tar tills situationen stabiliseras.

Sessionen är över. Och först efter en tid kommer servern mer eller mindre i ordning. Och den genomsnittliga svarstiden för förfrågningar på masterservern återgår till det normala. För äntligen har autovacuum möjligheten att rensa ut och markera dessa dödlinjer. Och han började göra sitt jobb. Och hur snabbt han gör det, så snabbt kommer vi att få ordning.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Enligt den testade surfplattan, där vi uppdaterar kontosaldon, ser vi exakt samma bild. Den genomsnittliga kontouppdateringstiden normaliseras också gradvis. Resurserna som förbrukas av processorn minskar också. Och antalet transaktioner per sekund återgår till det normala. Men återigen är vi tillbaka till det normala, inte samma som vi var innan olyckan.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Vi får i alla fall en prestationsavdrag, som i det första fallet, med en och en halv till två gånger, och ibland mer.

Vi verkar ha gjort allt rätt. Fördela belastningen. Utrustningen är inte ledig. Vi delade upp förfrågningarna efter våra sinnen, men ändå blev allt dåligt.

  • Aktivera inte hot_standby_feedback? Ja, det rekommenderas inte att slå på den utan särskilt starka skäl. Eftersom denna vridning direkt påverkar Master-servern och avbryter driften av autovakuum där. Genom att aktivera det på någon replik och glömma det kan du döda mästaren och få stora problem med applikationen.
  • Öka max_standby_streaming_delay? Ja, för rapporter är detta sant. Om du har en tretimmarsrapport och du inte vill att den ska krascha på grund av replikeringskonflikter, öka bara fördröjningen. En långtidsrapport kräver aldrig data som har kommit in i databasen just nu. Om du har den i tre timmar kör du den under en gammal dataperiod. Och för dig kommer det inte att göra någon skillnad om det är tre timmars försening eller sex timmars försening, men du kommer att få rapporter konsekvent och kommer inte att ha några problem med att de faller.
  • Naturligtvis måste du kontrollera långa sessioner på repliker, särskilt om du bestämmer dig för att aktivera hot_standby_feedback på en replik. För vad som helst kan hända. Vi gav denna replik till utvecklaren så att han kunde testa förfrågningarna. Han skrev en galen begäran. Han lanserade den och gick iväg för att dricka te, och vi fick den etablerade Mästaren. Eller så kanske vi lägger in fel applikation där. Situationerna är varierande. Sessioner på repliker måste övervakas lika noggrant som på Mastern.
  • Och om du har snabba och långa frågor om repliker, är det i det här fallet bättre att dela upp dem för att fördela belastningen. Det här är en länk till streaming_delay. För snabba, ha en replika med en liten replikeringsfördröjning. För långvariga rapporteringsförfrågningar, ha en replik som kan fördröjas med 6 timmar eller en dag. Detta är en helt normal situation.

Vi eliminerar konsekvenserna på samma sätt:

  • Vi hittar uppblåsta bord.
  • Och vi komprimerar den med det bekvämaste verktyget som passar oss.

Den andra historien slutar här. Låt oss gå vidare till den tredje historien.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Också ganska vanligt för oss där vi gör migrering.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

  • Alla mjukvaruprodukter växer. Kraven på det förändras. Vi vill i alla fall utvecklas. Och det händer att vi behöver uppdatera data i tabellen, nämligen att köra en uppdatering vad gäller vår migrering för den nya funktionalitet som vi inför som en del av vår utveckling.
  • Det gamla dataformatet är inte tillfredsställande. Låt oss säga att vi nu övergår till den andra tabellen, där jag har transaktioner på dessa konton. Och låt oss säga att de var i rubel, och vi bestämde oss för att öka noggrannheten och göra det i kopek. Och för detta måste vi göra en uppdatering: multiplicera fältet med transaktionsbeloppet med hundra.
  • I dagens värld använder vi automatiserade verktyg för databasversionskontroll. Låt oss säga Liquibase. Vi registrerar vår migration dit. Vi testar det på vår testbas. Allt är bra. Uppdateringen går igenom. Det blockerar arbete ett tag, men vi får uppdaterad data. Och vi kan lansera ny funktionalitet på detta. Allt testades och kontrollerades. Allt bekräftades.
  • Vi genomförde planerade arbeten och genomförde migrering.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Här är migreringen med uppdateringen som presenteras framför dig. Eftersom det här är mina kontotransaktioner var plattan 15 GB. Och eftersom vi uppdaterar varje rad fördubblade vi tabellens storlek med uppdateringen, eftersom vi skrev om varje rad.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Under migreringen kunde vi inte göra något med den här plattan, eftersom alla förfrågningar till den ställdes i kö och väntade tills den här uppdateringen var klar. Men här vill jag uppmärksamma er på siffrorna som finns på den vertikala axeln. Det vill säga, vi har en genomsnittlig förfrågningstid före migrering på cirka 5 millisekunder och processorbelastningen är antalet blockoperationer för att läsa diskminne mindre än 7,5.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Vi genomförde migreringen och fick problem igen.

Migreringen lyckades, men:

  • Den gamla funktionen tar nu längre tid att slutföra.
  • Bordet växte i storlek igen.
  • Belastningen på servern blev återigen större än tidigare.
  • Och vi pysslar såklart fortfarande med funktionaliteten som fungerade bra, vi har förbättrat den lite.

Och detta är återigen uppsvälldhet, som återigen förstör våra liv.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Här visar jag att tabellen, liksom de två föregående fallen, inte kommer att återgå till sina tidigare storlekar. Den genomsnittliga serverbelastningen verkar vara tillräcklig.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Och om vi vänder oss till tabellen med konton kommer vi att se att den genomsnittliga begärandetiden har fördubblats för denna tabell. Belastningen på processorn och antalet rader som sorterats ut i minnet hoppade över 7,5, men var lägre. Och det hoppade 2 gånger när det gäller processorer, 1,5 gånger när det gäller blockoperationer, dvs vi fick en försämring av serverns prestanda. Och som ett resultat - försämring av prestandan för vår applikation. Samtidigt låg antalet samtal ungefär på samma nivå.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Och det viktigaste här är att förstå hur man gör sådana migreringar korrekt. Och de måste göras. Vi gör dessa migrationer ganska konsekvent.

  • Så stora migrationer sker inte automatiskt. De måste alltid vara under kontroll.
  • Handledning av en kunnig person krävs. Om du har en DBA i ditt lag, låt DBA göra det. Det är hans jobb. Om inte, låt den mest erfarna personen göra det, som vet hur man arbetar med databaser.
  • Ett nytt databasschema, även om vi uppdaterar en kolumn, förbereder vi oss alltid i etapper, dvs i förväg innan den nya versionen av applikationen rullas ut:
  • Nya fält läggs till där vi kommer att registrera de uppdaterade uppgifterna.
  • Vi överför data från det gamla fältet till det nya fältet i små delar. Varför gör vi det här? För det första kontrollerar vi alltid processen för denna process. Vi vet att vi redan har överfört så många partier och vi har så många kvar.
  • Och den andra positiva effekten är att mellan varje sådan sats stänger vi transaktionen, öppnar en ny, och detta gör att autovakuumet kan fungera enligt plattan, markera tidsfrister för återanvändning.
  • För raderna som kommer att visas medan applikationen körs (vi har fortfarande den gamla applikationen igång) lägger vi till en utlösare som skriver nya värden till nya fält. I vårt fall är detta multiplikation med hundra av det gamla värdet.
  • Om vi ​​är helt envisa och vill ha samma fält, så byter vi helt enkelt namn på fälten efter att alla migreringar är klara och innan vi rullar ut en ny version av applikationen. De gamla får något påhittat namn, och de nya fälten döps om till de gamla.
  • Och först efter det lanserar vi en ny version av applikationen.

Och samtidigt kommer vi inte att få en svullnad och inte lida prestationsmässigt.

Det är här den tredje historien slutar.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

https://github.com/dataegret/pg-utils/blob/master/sql/table_bloat.sql

https://github.com/dataegret/pg-utils/blob/master/sql/table_bloat_approx.sql

Och nu lite mer detaljer om verktygen som jag nämnde i den allra första historien.

Innan du söker efter bloat måste du installera tillägget pgstattuple.

För att du inte ska behöva komma med frågor har vi redan skrivit dessa frågor i vårt arbete. Du kan använda dem. Det finns två önskemål här.

  • Den första tar ganska lång tid att fungera, men den visar dig de exakta uppblåsningsvärdena från tabellen.
  • Den andra fungerar snabbare och är mycket effektiv när du snabbt ska bedöma om det finns en uppblåsthet eller inte enligt tabellen. Och du bör också förstå att bloat alltid finns i ett Postgres-bord. Detta är en egenskap hos dess MVCC-modell.
  • Och 20% uppblåsthet är normalt för bord i de flesta fall. Det vill säga, du bör inte oroa dig och komprimera den här tabellen.

Vi kom på hur man identifierar tabeller som är svullna med värdelös data.

Nu om hur man fixar uppsvälldhet:

  • Har vi en liten surfplatta och bra diskar, det vill säga på en surfplatta upp till en gigabyte, är det fullt möjligt att använda VACUUM FULL. Han kommer att ta ett exklusivt lås från dig på bordet i några sekunder och okej, men han kommer att göra allt snabbt och hårt. Vad gör VACUUM FULL? Den tar ett exklusivt lås på bordet och skriver om liverader från de gamla borden till det nya bordet. Och till slut ersätter han dem. Det tar bort gamla filer och ersätter de gamla med nya. Men under hela sitt arbete tar den ett exklusivt lås på bordet. Det betyder att du inte kan göra någonting med den här tabellen: varken skriva till den, läsa in i den eller ändra den. Och VACUUM FULL kräver ytterligare diskutrymme för att skriva data.
  • Nästa verktyg pg_repack. I sin princip är den väldigt lik VACUUM FULL, eftersom den också skriver om data från gamla filer till nya och ersätter dem i tabellen. Men samtidigt tar den inte ett exklusivt lås på bordet i början av sitt arbete, utan tar det bara i det ögonblick då den redan har klara data för att ersätta filerna. Dess diskresurskrav liknar dem för VACUUM FULL. Du behöver ytterligare diskutrymme, och detta är ibland avgörande om du har terabytetabeller. Och den är ganska processorhungrig eftersom den aktivt arbetar med I/O.
  • Det tredje verktyget är pgcompacttable. Det är mer försiktigt med resurser eftersom det fungerar efter lite olika principer. Huvudidén med pgcompacttable är att den flyttar alla liverader till början av tabellen med hjälp av uppdateringar i tabellen. Och sedan kör det ett vakuum på det här bordet, eftersom vi vet att vi har levande rader i början och döda rader i slutet. Och själva vakuumet skär av denna svans, det vill säga det kräver inte mycket extra diskutrymme. Och samtidigt kan det fortfarande pressas resursmässigt.

Allt med verktyg.

Typiska fel i applikationer som leder till uppblåsthet i postgresql. Andrey Salnikov

Om du tycker att ämnet för uppblåsthet är intressant när det gäller att fördjupa dig längre in i det, här är några användbara länkar:

Jag försökte mer att visa en skräckhistoria för utvecklare, eftersom de är våra direkta kunder till databaser och måste förstå vad och vilka handlingar leder till. Jag hoppas att jag lyckades. Tack för din uppmärksamhet!

frågor

Tack för rapporten! Du pratade om hur du kan identifiera problem. Hur kan de varnas? Det vill säga, jag hade en situation där förfrågningar hängde inte bara för att de fick tillgång till vissa externa tjänster. Det här var bara några vilda sammanfogningar. Det var några små, ofarliga förfrågningar som hängde kvar i en dag, och sedan började göra några dumheter. Det vill säga väldigt likt det du beskriver. Hur spårar man detta? Sitt och titta hela tiden på vilken begäran som har fastnat? Hur kan detta förhindras?

I det här fallet är detta en uppgift för administratörerna på ditt företag, inte nödvändigtvis för DBA.

Jag är administratör.

PostgreSQL har en vy som heter pg_stat_activity som visar dinglande frågor. Och du kan se hur länge den hänger där.

Måste jag komma in och titta var 5:e minut?

Ställ in cron och kolla. Om du har en långvarig förfrågan, skriv ett brev och det är allt. Det vill säga, du behöver inte titta med ögonen, det kan automatiseras. Du får ett brev, du reagerar på det. Eller så kan du fotografera automatiskt.

Finns det några uppenbara orsaker till att detta händer?

Jag har listat några. Andra mer komplexa exempel. Och det kan bli ett samtal under lång tid.

Tack för rapporten! Jag ville förtydliga om verktyget pg_repack. Om hon inte gör ett exklusivt lås, då...

Hon gör ett exklusivt lås.

. då kan jag potentiellt förlora data. Ska min ansökan inte spela in något under denna tid?

Nej, det fungerar smidigt med tabellen, dvs pg_repack överför först alla live-linjer som finns. Naturligtvis sker där någon form av inträde i tabellen. Han kastar bara ut den här hästsvansen.

Det vill säga att han faktiskt gör det till slut?

Till slut tar han ett exklusivt lås för att byta dessa filer.

Kommer det att gå snabbare än VAKUUM FULL?

VAKUUM FULL, så fort den startade, tog genast ett exklusivt lås. Och tills han gör allt kommer han inte att släppa henne. Och pg_repack tar ett exklusivt lås endast vid tidpunkten för filbyte. För närvarande kommer du inte att skriva där, men data kommer inte att gå förlorade, allt kommer att bli bra.

Hallå! Du pratade om hur en bildammsugare fungerar. Det fanns en graf med röda, gula och gröna registreringsceller. Det vill säga gula - han markerade dem som raderade. Och som ett resultat kan något nytt skrivas in i dem?

Ja. Postgres tar inte bort rader. Han har en sådan specificitet. Om vi ​​uppdaterade en rad markerade vi den gamla som raderad. Id för transaktionen som ändrade denna rad visas där, och vi skriver en ny rad. Och vi har sessioner som potentiellt kan läsa dem. Någon gång blir de ganska gamla. Och kärnan i hur autovakuum fungerar är att det går igenom dessa linjer och markerar dem som onödiga. Och du kan skriva över data där.

Jag förstår. Men det är inte det frågan handlar om. Jag blev inte klar. Låt oss anta att vi har ett bord. Den har fält av varierande storlek. Och om jag försöker infoga något nytt kanske det helt enkelt inte passar in i den gamla cellen.

Nej, hela raden uppdateras i alla fall där. Postgres har två datalagringsmodeller. Den väljer från datatypen. Det finns data som lagras direkt i tabellen, och det finns även tos-data. Det här är stora mängder data: text, json. De förvaras i separata tallrikar. Och enligt dessa tabletter uppstår samma historia med uppblåsthet, d.v.s. allt är sig likt. De är bara listade separat.

Tack för rapporten! Är det acceptabelt att använda satser timeout-frågor för att begränsa varaktigheten?

Mycket acceptabelt. Vi använder detta överallt. Och eftersom vi inte har våra egna tjänster tillhandahåller vi fjärrsupport, vi har en mängd olika kunder. Och alla är helt nöjda med detta. Det vill säga vi har cron-jobb som kollar. Sessionernas längd avtalas helt enkelt med kunden, innan vi kommer inte överens. Det kan vara en minut, det kan vara 10 minuter. Det beror på belastningen på basen och dess syfte. Men vi använder alla pg_stat_activity.

Tack för rapporten! Jag försöker tillämpa din rapport på mina ansökningar. Och det verkar som att vi startar en transaktion överallt, och klart slutför den överallt. Om det finns något undantag sker återställning fortfarande. Och så började jag tänka. När allt kommer omkring kanske transaktionen inte startar explicit. Detta är förmodligen en ledtråd till flickan. Om jag bara uppdaterar en post, kommer transaktionen att starta i PostgreSQL och slutföras först när anslutningen kopplas bort?

Om du nu talar om applikationsnivån, så beror det på drivrutinen du använder, på den ORM som används. Det finns många inställningar där. Om du har aktiverat automatisk commit på, startar en transaktion där och stängs omedelbart.

Det vill säga, den stänger direkt efter uppdateringen?

Det beror på inställningarna. Jag namngav en inställning. Detta är automatisk commit på. Det är ganska vanligt. Om det är aktiverat har transaktionen öppnats och stängts. Såvida du inte uttryckligen sa "starta transaktionen" och "avsluta transaktionen", men helt enkelt startade en begäran i sessionen.

Hallå! Tack för rapporten! Låt oss föreställa oss att vi har en databas som sväller och sväller och sedan tar utrymmet på servern slut. Finns det några verktyg för att fixa denna situation?

Utrymmet på servern måste övervakas ordentligt.

Till exempel gick DBA för te, var på en resort osv.

När ett filsystem skapas skapas åtminstone något slags backuputrymme där data inte skrivs.

Tänk om det är helt under noll?

Där kallas det reserverat utrymme, det vill säga det kan frigöras och beroende på hur stort det skapats får du ledigt utrymme. Som standard vet jag inte hur många det finns. Och i ett annat fall, leverera diskar så att du har utrymme att utföra en rekonstruktiv operation. Du kan ta bort någon tabell som du garanterat inte behöver.

Finns det några andra verktyg?

Den är alltid handgjord. Och lokalt blir det tydligt vad som är bäst att göra där, eftersom vissa data är kritiska och andra är icke-kritiska. Och för varje databas och applikationen som fungerar med den beror det på verksamheten. Det avgörs alltid lokalt.

Tack för rapporten! Jag har två frågor. Först visade du bilder som visade att när transaktioner har fastnat växer både tabellutrymmesstorleken och indexstorleken. Och längre fram i rapporten fanns det ett gäng verktyg som paketerar surfplattan. Hur är det med indexet?

De packar dem också.

Men vakuumet påverkar inte indexet?

Vissa arbetar med ett index. Till exempel, pg_rapack, pgcompacttable. Vakuumet återskapar indexen och påverkar dem. Med VACUUM FULL är tanken att skriva över allt, dvs det fungerar med alla.

Och den andra frågan. Jag förstår inte varför rapporter om repliker beror så mycket på själva replikeringen. Det verkade för mig att rapporter läses och replikering är att skriva.

Vad orsakar en replikeringskonflikt? Vi har en Master på vilka processer sker. Vi har en bildammsugare på gång. Vad gör en autovacuum egentligen? Han klipper ut några gamla rader. Om vi ​​vid denna tidpunkt har en förfrågan på repliken som läser dessa gamla rader, och på mästaren en situation inträffade att autovakuumet markerade dessa rader som möjliga för överskrivning, så skrev vi över dem. Och vi fick ett datapaket, när vi behöver skriva om de rader som begäran behöver på repliken, kommer replikeringsprocessen att vänta på timeouten som du har konfigurerat. Och sedan kommer PostgreSQL att avgöra vad som är viktigare för den. Och replikering är viktigare för honom än begäran, och han kommer att skjuta begäran för att göra dessa ändringar på repliken.

Andrey, jag har en fråga. Dessa underbara grafer som du visade under presentationen, är dessa resultatet av arbetet med någon form av hjälpmedel? Hur gjordes graferna?

Detta är en tjänst Okmeter.

Är detta en kommersiell produkt?

Ja. Detta är en kommersiell produkt.

Källa: will.com

Lägg en kommentar