Waaroor EXPLAIN swyg en hoe om dit aan die praat te kry

Die klassieke vraag wat 'n ontwikkelaar na sy DBA of 'n sake-eienaar bring aan 'n PostgreSQL-konsultant, klink amper altyd dieselfde: "Hoekom neem versoeke so lank om op die databasis te voltooi?"

Tradisionele stel redes:

  • ondoeltreffende algoritme
    wanneer jy besluit om by verskeie CTE's aan te sluit oor 'n paar tienduisende rekords
  • verouderde statistieke
    as die werklike verspreiding van data in die tabel reeds baie verskil van die een wat die vorige keer deur ANALISE ingesamel is
  • hulpbronne in te "prop".
    en daar is nie meer genoeg toegewyde rekenaarkrag van die SVE nie, gigagrepe geheue word voortdurend gepomp, of die skyf kan nie tred hou met al die "begeertes" van die databasis nie
  • blokkeer van mededingende prosesse

En as blokkasies redelik moeilik is om te vang en te ontleed, dan vir alles wat ons nodig het navraagplan, wat verkry kan word met behulp van VERDUIDELIK operateur (Dit is natuurlik beter om dadelik te VERDUIDELIK (ANALISEER, BUFFERS) ...) of outo_verduidelik module.

Maar, soos in dieselfde dokumentasie gesΓͺ,

"Om 'n plan te verstaan ​​is 'n kuns, en om dit te bemeester verg 'n sekere hoeveelheid ervaring ..."

Maar jy kan daarsonder klaarkom as jy die regte hulpmiddel gebruik!

Hoe lyk 'n navraagplan tipies? Iets soos dit:

Index Scan using pg_class_relname_nsp_index on pg_class (actual time=0.049..0.050 rows=1 loops=1)
  Index Cond: (relname = $1)
  Filter: (oid = $0)
  Buffers: shared hit=4
  InitPlan 1 (returns $0,$1)
    ->  Limit (actual time=0.019..0.020 rows=1 loops=1)
          Buffers: shared hit=1
          ->  Seq Scan on pg_class pg_class_1 (actual time=0.015..0.015 rows=1 loops=1)
                Filter: (relkind = 'r'::"char")
                Rows Removed by Filter: 5
                Buffers: shared hit=1

of soos volg:

"Append  (cost=868.60..878.95 rows=2 width=233) (actual time=0.024..0.144 rows=2 loops=1)"
"  Buffers: shared hit=3"
"  CTE cl"
"    ->  Seq Scan on pg_class  (cost=0.00..868.60 rows=9972 width=537) (actual time=0.016..0.042 rows=101 loops=1)"
"          Buffers: shared hit=3"
"  ->  Limit  (cost=0.00..0.10 rows=1 width=233) (actual time=0.023..0.024 rows=1 loops=1)"
"        Buffers: shared hit=1"
"        ->  CTE Scan on cl  (cost=0.00..997.20 rows=9972 width=233) (actual time=0.021..0.021 rows=1 loops=1)"
"              Buffers: shared hit=1"
"  ->  Limit  (cost=10.00..10.10 rows=1 width=233) (actual time=0.117..0.118 rows=1 loops=1)"
"        Buffers: shared hit=2"
"        ->  CTE Scan on cl cl_1  (cost=0.00..997.20 rows=9972 width=233) (actual time=0.001..0.104 rows=101 loops=1)"
"              Buffers: shared hit=2"
"Planning Time: 0.634 ms"
"Execution Time: 0.248 ms"

Maar die lees van die plan in teks "van die blad" is baie moeilik en onduidelik:

  • word in die nodus vertoon som deur subboombronne
    dit wil sΓͺ, om te verstaan ​​hoeveel tyd dit geneem het om 'n spesifieke nodus uit te voer, of hoeveel presies hierdie lesing van die tabel data van die skyf af opgebring het, moet jy op een of ander manier die een van die ander aftrek
  • node tyd is nodig vermenigvuldig met lusse
    ja, aftrekking is nie die mees komplekse bewerking wat "in die kop" gedoen moet word nie - die uitvoeringstyd word immers aangedui as die gemiddelde vir een uitvoering van 'n nodus, en daar kan honderde van hulle wees
  • wel, en dit alles saam verhoed ons om die hoofvraag te beantwoord - so wie "die swakste skakel"?

Toe ons dit alles aan 'n paar honderd van ons ontwikkelaars probeer verduidelik het, het ons besef dat dit van buite so iets lyk:

Waaroor EXPLAIN swyg en hoe om dit aan die praat te kry

En dit beteken ons moet...

Tool

Daarin het ons probeer om al die sleutelwerktuigkundiges te versamel wat volgens die plan en versoek help om te verstaan ​​"wie is die skuldige en wat om te doen." Wel, en deel 'n deel van jou ervaring met die gemeenskap.
Ontmoet en gebruik - verduidelik.tensor.ru

Sigbaarheid van planne

Is dit maklik om die plan te verstaan ​​as dit so lyk?

Seq Scan on pg_class (actual time=0.009..1.304 rows=6609 loops=1)
  Buffers: shared hit=263
Planning Time: 0.108 ms
Execution Time: 1.800 ms

Nie regtig nie.

Maar soos hierdie, in verkorte vormwanneer die sleutelaanwysers geskei word, is dit baie duideliker:

Waaroor EXPLAIN swyg en hoe om dit aan die praat te kry

Maar as die plan meer ingewikkeld is, sal hy tot die redding kom sirkeldiagram tyd verspreiding deur nodusse:

Waaroor EXPLAIN swyg en hoe om dit aan die praat te kry

Wel, vir die moeilikste opsies is hy haastig om te help vorderingskaart:

Waaroor EXPLAIN swyg en hoe om dit aan die praat te kry

Byvoorbeeld, daar is redelik nie-triviale situasies wanneer 'n plan meer as een werklike wortel kan hΓͺ:

Waaroor EXPLAIN swyg en hoe om dit aan die praat te kryWaaroor EXPLAIN swyg en hoe om dit aan die praat te kry

Strukturele leidrade

Wel, as die hele struktuur van die plan en sy swak punte reeds uiteengesit en sigbaar is, waarom dit nie aan die ontwikkelaar uitlig en in "Russiese taal" verduidelik nie?

Waaroor EXPLAIN swyg en hoe om dit aan die praat te kryOns het reeds 'n paar dosyn sulke aanbevelingsjablone versamel.

ReΓ«l-vir-lyn navraagprofieler

Nou, as jy die oorspronklike navraag op die geanaliseerde plan plaas, kan jy sien hoeveel tyd aan elke individuele stelling bestee is - iets soos hierdie:

Waaroor EXPLAIN swyg en hoe om dit aan die praat te kry

... of selfs so:

Waaroor EXPLAIN swyg en hoe om dit aan die praat te kry

Vervang parameters in 'n versoek

As u nie net 'n versoek aan die plan "aangeheg" het nie, maar ook die parameters daarvan vanaf die DETAIL-lyn van die logboek, kan u dit ook in een van die opsies kopieer:

  • met waardevervanging in die versoek
    vir direkte uitvoering op jou basis en verdere profilering

    SELECT 'const', 'param'::text;
  • met waardevervanging via VOORBEREI/UITVOER
    om die werk van die skeduleerder na te boots, wanneer die parametriese deel geΓ―gnoreer kan word - byvoorbeeld wanneer aan gepartisioneerde tabelle gewerk word

    DEALLOCATE ALL;
    PREPARE q(text) AS SELECT 'const', $1::text;
    EXECUTE q('param'::text);
    

Argief van planne

Plak, ontleed, deel met kollegas! Die planne sal in die argief bly en jy kan later daarna terugkeer: verduidelik.tensor.ru/archive

Maar as jy nie wil hΓͺ ander moet jou plan sien nie, moenie vergeet om die blokkie "moenie in argief publiseer nie" te merk nie.

In die volgende artikels sal ek praat oor die probleme en besluite wat ontstaan ​​wanneer 'n plan ontleed word.

Bron: will.com

Voeg 'n opmerking