{"id":32353,"date":"2019-10-31T21:46:32","date_gmt":"2019-10-31T18:46:32","guid":{"rendered":"https:\/\/prohoster.info\/blog\/monitoring-proizvoditelnosti-zaprosov-postgresql-chast-1-reporting\/"},"modified":"2019-10-31T21:46:32","modified_gmt":"2019-10-31T18:46:32","slug":"monitoring-proizvoditelnosti-zaprosov-postgresql-chast-1-reporting","status":"publish","type":"post","link":"https:\/\/prohoster.info\/pl\/blog\/administrirovanie\/monitoring-proizvoditelnosti-zaprosov-postgresql-chast-1-reporting","title":{"rendered":"Monitorowanie wydajno\u015bci zapyta\u0144 PostgreSQL. Cz\u0119\u015b\u0107 1 \u2014 raportowanie","gt_translate_keys":[{"key":"rendered","format":"text"}]},"content":{"rendered":"<p>In\u017cynier \u2014 t\u0142umacz\u0105c z \u0142aciny \u2014 jest natchniony.<br \/>\nIn\u017cynier potrafi wszystko. (c) R.Dizel.<br \/>\n<i>Epigrafy.<\/i><br \/>\n<img decoding=\"async\" alt=\"Monitorowanie wydajno\u015bci zapyta\u0144 PostgreSQL. Cz\u0119\u015b\u0107 1 \u2014 raportowanie\" src=\"\/wp-content\/uploads\/2019\/04\/9a2640267ea05006b94e03642b864ddc.jpeg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n<i>Lub historia o tym, dlaczego administrator baz danych powinien przypomina\u0107 sobie swoje programistyczne przesz\u0142o\u015b\u0107. <\/i><\/p>\n<h2>Wst\u0119p<\/h2>\n<p>\nWszystkie imiona zosta\u0142y zmienione. Zbiegi okoliczno\u015bci s\u0105 przypadkowe. Materia\u0142 przedstawia wy\u0142\u0105cznie osobiste zdanie autora.<\/p>\n<blockquote><p><b>Zastrze\u017cenie dotycz\u0105ce gwarancji:<\/b> <i>w planowanym cyklu artyku\u0142\u00f3w nie b\u0119dzie szczeg\u00f3\u0142owego i dok\u0142adnego opisu u\u017cywanych tabel i skrypt\u00f3w. Materia\u0142y nie b\u0119d\u0105 mog\u0142y by\u0107 od razu u\u017cyte \"TAK JAK S\u0104\". <br \/>\nPo pierwsze, z powodu du\u017cej obj\u0119to\u015bci materia\u0142u, <br \/>\npo drugie, z powodu dostosowania do produkcyjnej bazy rzeczywistego klienta. <br \/>\nDlatego w artyku\u0142ach b\u0119d\u0105 podane tylko pomys\u0142y i opisy w najbardziej og\u00f3lnym uj\u0119ciu. <br \/>\nMo\u017ce w przysz\u0142o\u015bci system osi\u0105gnie poziom publikacji na GitHubie, a mo\u017ce i nie. Czas poka\u017ce.<\/i><\/p><\/blockquote>\n<p>\nPocz\u0105tek historii \u2013 \u201e<noindex><a rel=\"nofollow\" href=\"https:\/\/habr.com\/ru\/company\/icl_services\/blog\/446314\/\">Czy pami\u0119tasz, jak to wszystko si\u0119 zacz\u0119\u0142o?<\/a><\/noindex>\u00bb.<br \/>\nCo powsta\u0142o w wyniku, w najbardziej og\u00f3lnych zarysach \u2013 \u201e<noindex><a rel=\"nofollow\" href=\"https:\/\/habr.com\/ru\/post\/444988\/\">Synteza jako jedna z metod poprawy wydajno\u015bci PostgreSQL<\/a><\/noindex>\u00bb<\/p>\n<h2>Po co mi to wszystko?<\/h2>\n<p>\nNo, po pierwsze, aby samemu nie zapomnie\u0107, wspominaj\u0105c na emeryturze dawne, chwalebne dni. <br \/>\nPo drugie, aby usystematyzowa\u0107 to, co napisa\u0142em. Bowiem ju\u017c sam, czasami, zaczynam si\u0119 myli\u0107 i zapomina\u0107 o poszczeg\u00f3lnych cz\u0119\u015bciach. <\/p>\n<p>No i najwa\u017cniejsze \u2014 nagle mo\u017ce to komu\u015b si\u0119 przyda i pomo\u017ce nie wynajdywa\u0107 na nowo ko\u0142a ani nie zbiera\u0107 \u0142opat. Innymi s\u0142owy, poprawi\u0107 swoj\u0105 karm\u0119 (nie hubrowsk\u0105). Bo najcenniejsze w tym \u015bwiecie to idee. Najwa\u017cniejsze to znale\u017a\u0107 pomys\u0142. A zrealizowa\u0107 pomys\u0142 w rzeczywisto\u015bci to ju\u017c kwestia czysto techniczna.<\/p>\n<p>Tak wi\u0119c, zaczynamy, powoli...<\/p>\n<h2>Postawienie zadania.<\/h2>\n<p><\/p>\n<h3>Mamy: <\/h3>\n<p>\nBaza danych PostgreSQL (10.5), mieszany typ obci\u0105\u017cenia (OLTP+DSS), \u015brednie-niskie obci\u0105\u017cenie, umieszczona w chmurze AWS. <br \/>\nMonitoring bazy danych nie istnieje, monitoring infrastruktury przedstawiony jest w postaci standardowych narz\u0119dzi AWS w minimalnej konfiguracji.<\/p>\n<h3>Wymagane:<\/h3>\n<p>\nMonitorowanie wydajno\u015bci i stanu bazy danych, znajdowanie i posiadanie pocz\u0105tkowych informacji do optymalizacji ci\u0119\u017ckich zapyta\u0144 do bazy danych.<br \/>\n<noindex><a rel=\"nofollow\" name=\"habracut\"><\/a><\/noindex><\/p>\n<h2>Kr\u00f3tka przedmowa lub analiza opcji rozwi\u0105zania<\/h2>\n<p>\nNa pocz\u0105tek spr\u00f3bujemy przeanalizowa\u0107 mo\u017cliwo\u015bci rozwi\u0105zania zadania z punktu widzenia analizy por\u00f3wnawczej korzy\u015bci i niedogodno\u015bci dla in\u017cyniera, a korzy\u015bciami i stratami w zarz\u0105dzaniu niech zajm\u0105 si\u0119 ci, kt\u00f3rzy s\u0105 do tego wyznaczeni zgodnie z etatem.<\/p>\n<h3>Opcja 1 \u2013 \"Praca na \u017c\u0105danie\"<\/h3>\n<p>\nZostawiamy wszystko jak jest. Je\u015bli zleceniodawca ma jakie\u015b zastrze\u017cenia co do funkcjonowania, wydajno\u015bci bazy danych lub aplikacji, powiadomi in\u017cynier\u00f3w DBA za pomoc\u0105 e-maila lub tworz\u0105c incydent w systemie zg\u0142osze\u0144. <br \/>\nIn\u017cynier, otrzymawszy powiadomienie, zajmie si\u0119 problemem, zaproponuje rozwi\u0105zanie lub od\u0142o\u017cy spraw\u0119 na p\u00f3\u017aniej, maj\u0105c nadziej\u0119, \u017ce sama si\u0119 rozwi\u0105\u017ce, a i tak wkr\u00f3tce wszystko zostanie zapomniane.<br \/>\n<b class=\"spoiler_title\">Pierniki i p\u0105czki, siniaki i guzki<\/b><b>Pierniki i p\u0105czki:<\/b><br \/>\n1. Nie ma potrzeby robi\u0107 nic zb\u0119dnego<br \/>\n2. Zawsze mo\u017cna si\u0119 wykr\u0119ci\u0107 i odpu\u015bci\u0107. <br \/>\n3. Mn\u00f3stwo czasu, kt\u00f3ry mo\u017cna wykorzysta\u0107 wed\u0142ug w\u0142asnego uznania.<br \/>\n<b>Siniaki i guzki:<\/b><br \/>\n1. Pr\u0119dzej czy p\u00f3\u017aniej zleceniodawca zacznie si\u0119 zastanawia\u0107 nad istot\u0105 bytu i kosmiczn\u0105 sprawiedliwo\u015bci\u0105 w tym \u015bwiecie i po raz kolejny zada sobie pytanie \u2014 za co p\u0142ac\u0119 im swoje pieni\u0105dze? Skutek zawsze jest ten sam \u2014 chodzi tylko o to, kiedy zleceniodawca si\u0119 znudzi i machnie r\u0119k\u0105 na po\u017cegnanie. A \u017c\u0142\u00f3b si\u0119 opr\u00f3\u017cni. To smutne.<br \/>\n2. Rozw\u00f3j in\u017cyniera \u2014 zero.<br \/>\n3. Trudno\u015bci w planowaniu pracy i obci\u0105\u017cenia <\/p>\n<h3>Opcja 2 - \u201eTa\u0144czymy z b\u0119bnem, wciskamy i obuwamy\u201d<\/h3>\n<p>\n<b>Punkt 1<\/b>-Po co nam system monitorowania, b\u0119dziemy wszystko dostawa\u0107 poprzez zapytania. Uruchamiamy mn\u00f3stwo r\u00f3\u017cnych zapyta\u0144 do s\u0142ownika danych i dynamicznych widok\u00f3w, w\u0142\u0105czamy r\u00f3\u017cne liczniki, zestawiamy wszystko w tabelach, okresowo analizujemy listy i tabele. W rezultacie mamy \u0142adne lub mniej \u0142adne wykresy, tabele, raporty. Wa\u017cne, \u017ceby by\u0142o jak najwi\u0119cej.<br \/>\n<b>Punkt 2<\/b>-Generujemy aktywno\u015b\u0107 - uruchamiamy analiz\u0119 tego wszystkiego.<br \/>\n<b>Punkt 3<\/b>-Przygotowujemy jaki\u015b dokument, nazywamy go po prostu - \u201ejak mamy urz\u0105dzi\u0107 baz\u0119 danych\u201d.<br \/>\n<b>Punkt 4<\/b>-Zleceniodawca, widz\u0105c to wszystko wspania\u0142o\u015b\u0107 wykres\u00f3w i liczb jest w dzieci\u0119cej naiwnej pewno\u015bci \u2014 oto teraz wszystko zacznie dzia\u0142a\u0107, wkr\u00f3tce. I \u0142atwo i bezbole\u015bnie rozstaje si\u0119 ze swoimi zasobami finansowymi. Zarz\u0105d r\u00f3wnie\u017c jest pewien \u2014 in\u017cynierowie u nas pracuj\u0105 na pe\u0142nych obrotach. Obci\u0105\u017cenie na maksymalnym poziomie. <br \/>\n<b>Punkt 5<\/b>-Regularnie powt\u00f3rzy\u0107 Punkt 1.<br \/>\n<b class=\"spoiler_title\">Pierniki i p\u0105czki, siniaki i guzki<\/b><b>Pierniki i p\u0105czki: <\/b><br \/>\n1. \u017bycie mened\u017cer\u00f3w i in\u017cynier\u00f3w \u2014 proste, przewidywalne i pe\u0142ne aktywno\u015bci. Wszystko brz\u0119czy, wszyscy zaj\u0119ci. <br \/>\n2. \u017bycie zleceniodawcy te\u017c nie jest z\u0142e \u2014 zawsze jest pewny, \u017ce wystarczy troch\u0119 poczeka\u0107 i wszystko si\u0119 u\u0142o\u017cy. Nie uk\u0142ada si\u0119, no co\u017c \u2014 \u015bwiat jest niesprawiedliwy, w nast\u0119pnym \u017cyciu si\u0119 uda.<br \/>\n<b>Siniaki i guzki:<\/b><br \/>\n1. Pr\u0119dzej czy p\u00f3\u017aniej znajdzie si\u0119 szybszy dostawca podobnej us\u0142ugi, kt\u00f3ry zrobi to samo, ale za nieco ni\u017csz\u0105 cen\u0119. A je\u015bli wynik jest ten sam, to po co p\u0142aci\u0107 wi\u0119cej? To znowu doprowadzi do znikni\u0119cia \u017ar\u00f3d\u0142a dochodu.<br \/>\n2. To nudne. Jak ka\u017cda ma\u0142o sensowna aktywno\u015b\u0107.<br \/>\n3. Jak w poprzedniej wersji \u2014 brak jakiegokolwiek rozwoju. Ale dla in\u017cyniera minusem jest to, \u017ce w przeciwie\u0144stwie do pierwszej opcji, tutaj trzeba nieustannie generowa\u0107 baz\u0119 danych. A to zajmuje czas. Kt\u00f3ry mo\u017cna wykorzysta\u0107 dla siebie. Bo je\u015bli sam o siebie nie zadbasz, nikt si\u0119 o ciebie nie troszczy.<\/p>\n<h3>Opcja 3 \u2014 nie trzeba wymy\u015bla\u0107 ko\u0142a na nowo, wystarczy je kupi\u0107 i je\u017adzi\u0107.<\/h3>\n<p>\nIn\u017cynierowie z innych firm nie bez powodu jedz\u0105 pizz\u0119 popijaj\u0105c piwem (ach, wspania\u0142e czasy w Petersburgu lat 90.). U\u017cyjmy system\u00f3w monitoruj\u0105cych, kt\u00f3re s\u0105 ju\u017c stworzone, dopracowane i dzia\u0142aj\u0105, i przynosz\u0105 korzy\u015bci (przynajmniej ich tw\u00f3rcom).<br \/>\n<b class=\"spoiler_title\">Pierniki i p\u0105czki, siniaki i guzki<\/b><b>Pierniki i p\u0105czki:<\/b><br \/>\n1. Nie trzeba traci\u0107 czasu na wymy\u015blanie czego\u015b, co ju\u017c zosta\u0142o wymy\u015blone. We\u017a i korzystaj.<br \/>\n2. Systemy monitorowania nie s\u0105 pisan\u0105 przez idiot\u00f3w i na pewno s\u0105 u\u017cyteczne.<br \/>\n3. Dzia\u0142aj\u0105ce systemy monitorowania zazwyczaj dostarczaj\u0105 przydatne, przefiltrowane informacje. <br \/>\n<b>Siniaki i guzki:<\/b><br \/>\n1. In\u017cynier w tej sytuacji nie jest in\u017cynierem, a jedynie u\u017cytkownikiem cudzej produkcji. Albo u\u017cytkownikiem.<br \/>\n2. Klienta trzeba przekona\u0107 do konieczno\u015bci zakupu czego\u015b, w co w og\u00f3le nie chce si\u0119 zag\u0142\u0119bia\u0107, a nie powinien. Bud\u017cet na rok zosta\u0142 zatwierdzony i si\u0119 nie zmieni. Nast\u0119pnie trzeba przypisa\u0107 osobny zas\u00f3b, skonfigurowa\u0107 pod konkretny system. Tzn. najpierw trzeba p\u0142aci\u0107, p\u0142aci\u0107 i jeszcze raz p\u0142aci\u0107. A klient jest sk\u0105py. To norma \u017cycia.<\/p>\n<h2>Co zrobi\u0107 - Czernyszewski? Twoje pytanie jest bardzo zasadne. (c)<\/h2>\n<p>\nW tej konkretnej sytuacji mo\u017cna post\u0105pi\u0107 troch\u0119 inaczej \u2014 <b>a mo\u017ce zr\u00f3bmy nasz w\u0142asny system monitorowania. <\/b><br \/>\n<img decoding=\"async\" alt=\"Monitorowanie wydajno\u015bci zapyta\u0144 PostgreSQL. Cz\u0119\u015b\u0107 1 \u2014 raportowanie\" src=\"\/wp-content\/uploads\/2019\/04\/b59a3ad9e16b68c0fbc962a61d571c52.jpeg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\nNo nie system oczywi\u015bcie, w pe\u0142nym tego s\u0142owa znaczeniu, to zbyt patetyczne i zuchwa\u0142e, ale przynajmniej w jaki\u015b spos\u00f3b u\u0142atwmy sobie zadanie i zbierzmy jak najwi\u0119cej informacji do rozwi\u0105zania incydent\u00f3w wydajno\u015bci. \u017beby nie znale\u017a\u0107 si\u0119 w sytuacji \u2014 \"id\u017a tam, nie wiem gdzie, znajd\u017a to, nie wiem co\".<\/p>\n<h4>Jakie s\u0105 plusy i minusy tej opcji:<\/h4>\n<p><b>Zalety:<\/b><br \/>\n1. To ciekawe. Przynajmniej ciekawsze ni\u017c ci\u0105g\u0142e \u201eshrink datafile, alter tablespace, itp.\u201d <br \/>\n2. To nowe umiej\u0119tno\u015bci i nowe mo\u017cliwo\u015bci rozwoju. Co w przysz\u0142o\u015bci da zas\u0142u\u017cone nagrody i przyjemno\u015bci.<br \/>\n<b>Wady:<\/b><br \/>\n1. B\u0119dzie trzeba pracowa\u0107. Pracowa\u0107 du\u017co. <br \/>\n2. B\u0119dzie trzeba regularnie wyja\u015bnia\u0107 sens i mo\u017cliwo\u015bci ca\u0142ej aktywno\u015bci.<br \/>\n3. Czego\u015b b\u0119dzie trzeba si\u0119 wyrzec, poniewa\u017c jedynym zasobem dost\u0119pnym in\u017cynierowi \u2013 czasem \u2013 jest ograniczony przez Wszech\u015bwiat. <br \/>\n<b>4. Najgorsze i najbardziej nieprzyjemne<\/b> \u2013 w wyniku mo\u017ce powsta\u0107 co\u015b w rodzaju \"Nie mysz, nie \u017caba, a nieznane zwierz\u0105tko\".<\/p>\n<p><b>Kto nie ryzykuje, ten nie pije szampana.<\/b><br \/>\nI tak \u2013 zaczyna si\u0119 to, co najciekawsze.<\/p>\n<h2>Og\u00f3lna idea \u2013 schematycznie<\/h2>\n<p>\n<img decoding=\"async\" alt=\"Monitorowanie wydajno\u015bci zapyta\u0144 PostgreSQL. Cz\u0119\u015b\u0107 1 \u2014 raportowanie\" src=\"\/wp-content\/uploads\/2019\/04\/d1ae2ddc1d4c43353fe93eebdaa8b81a.jpeg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n(<i>Ilustracja pochodzi z artyku\u0142u<\/i> \u00ab<noindex><a rel=\"nofollow\" href=\"https:\/\/habr.com\/ru\/post\/444988\/\">Synteza jako jedna z metod poprawy wydajno\u015bci PostgreSQL<\/a><\/noindex>\u00bb)<\/p>\n<p>Wyja\u015bnienie:<\/p>\n<ul>\n<li> W docelowej bazie instalowane jest standardowe rozszerzenie PostgreSQL \u2013 \"pg_stat_statements\". <\/li>\n<li>W bazie danych monitoruj\u0105cej tworzymy zestaw tabel serwisowych do przechowywania historii pg_stat_statements na wczesnym etapie oraz do konfigurowania metryk i monitorowania p\u00f3\u017aniej.<\/li>\n<li> Na ho\u015bcie monitoruj\u0105cym tworzymy zestaw skrypt\u00f3w bash, w tym do generowania incydent\u00f3w w systemie zg\u0142osze\u0144. <\/li>\n<\/ul>\n<h2>Tabele serwisowe<\/h2>\n<p>\nNa pocz\u0105tek schematyczna uproszczona ERD, co nam ostatecznie wysz\u0142o:<br \/>\n<img decoding=\"async\" alt=\"Monitorowanie wydajno\u015bci zapyta\u0144 PostgreSQL. Cz\u0119\u015b\u0107 1 \u2014 raportowanie\" src=\"\/wp-content\/uploads\/2019\/04\/03d29f4d6932d470d9d88651cbf0c715.jpeg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n<b class=\"spoiler_title\">Kr\u00f3tki opis tabel<\/b><b>endpoint <\/b> \u2013 host, punkt po\u0142\u0105czenia z instancj\u0105<br \/>\n<b>database <\/b> \u2013 parametry bazy danych<br \/>\n<b>pg_stat_history <\/b> \u2013 tabela historyczna do przechowywania czasowych zrzut\u00f3w widoku pg_stat_statements docelowej bazy danych<br \/>\n<b>metric_glossary <\/b> \u2013 s\u0142ownik metryk wydajno\u015bci<br \/>\n<b>metric_config <\/b> \u2013 konfiguracja poszczeg\u00f3lnych metryk<br \/>\n<b>metric <\/b> \u2013 konkretna metryka dla monitorowanego zapytania<br \/>\n<b>metric_alert_history <\/b> \u2013 historia ostrze\u017ce\u0144 wydajno\u015bci<br \/>\n<b>log_query <\/b> \u2013 tabela serwisowa do przechowywania sparsowanych wpis\u00f3w z pliku dziennika PostgreSQL wgrywanego z AWS<br \/>\n<b>baseline <\/b> \u2013 parametry okresu czasu u\u017cywanego jako bazowy <br \/>\n<b>checkpoint <\/b> \u2013 konfiguracja metryk sprawdzaj\u0105cych stan bazy danych<br \/>\n<b>checkpoint_alert_history <\/b> \u2013 historia ostrze\u017ce\u0144 metryk sprawdzaj\u0105cych stan bazy danych<br \/>\n<b>pg_stat_db_queries <\/b> \u2013 tabela serwisowa aktywnych zapyta\u0144 <br \/>\n<b>activity_log <\/b> \u2013 tabela serwisowa dziennika aktywno\u015bci <br \/>\n<b>trap_oid <\/b> \u2013 tabela serwisowa konfiguracji pu\u0142apki<\/p>\n<p><\/p>\n<h2>Etap 1 \u2013 zbieramy informacje statystyczne o wydajno\u015bci i uzyskujemy raporty<\/h2>\n<p>\nDo przechowywania informacji statystycznych s\u0142u\u017cy tabela <b>pg_stat_history<\/b><br \/>\n<b class=\"spoiler_title\">Struktura tabeli pg_stat_history<\/b><\/p>\n<pre>\n                                          Tabela \"public.pg_stat_history\"\n       Kolumna       |            Typ              |                          Modyfikatory\n---------------------+-----------------------------+-------------------------------------------\n id                  | liczba ca\u0142kowita            | not null domy\u015blnie nextval('pg_stat_history_id_seq'::regclass)\n snapshot_timestamp  | znacznik czasu bez strefy   |\n database_id         | liczba ca\u0142kowita            |\n dbid                | oid                         |\n userid              | oid                         |\n queryid             | bigint                      |\n query               | tekst                       |\n calls               | bigint                      |\n total_time          | podw\u00f3jna precyzja           |\n min_time            | podw\u00f3jna precyzja           |\n max_time            | podw\u00f3jna precyzja           |\n mean_time           | podw\u00f3jna precyzja           |\n stddev_time         | podw\u00f3jna precyzja           |\n rows                | bigint                      |\n shared_blks_hit     | bigint                      |\n shared_blks_read    | bigint                      |\n shared_blks_dirtied | bigint                      |\n shared_blks_written | bigint                      |\n local_blks_hit      | bigint                      |\n local_blks_read     | bigint                      |\n local_blks_dirtied  | bigint                      |\n local_blks_written  | bigint                      |\n temp_blks_read      | bigint                      |\n temp_blks_written   | bigint                      |\n blk_read_time       | podw\u00f3jna precyzja           |\n blk_write_time      | podw\u00f3jna precyzja           |\n baseline_id         | liczba ca\u0142kowita            |\nIndeksy:\n    \"pg_stat_history_pkey\" KLUCZ G\u0141\u00d3WNY, btree (id)\n    \"database_idx\" btree (database_id)\n    \"queryid_idx\" btree (queryid)\n    \"snapshot_timestamp_idx\" btree (snapshot_timestamp)\nOgraniczenia kluczy obcych:\n    \"database_id_fk\" KLUCZ OBCE (database_id) ODNIESIENIA database(id) W USU\u0143 KASKADOWO<\/pre>\n<p>\nJak wida\u0107, tabela jest jedynie akumulacj\u0105 danych widoku <b>pg_stat_statements <\/b> w docelowej bazie danych.<\/p>\n<h3>U\u017cycie tej tabeli jest bardzo proste<\/h3>\n<p>\n<b>pg_stat_history<\/b> b\u0119dzie stanowi\u0107 skumulowan\u0105 statystyk\u0119 wykonania zapyta\u0144 dla ka\u017cdej godziny. Na pocz\u0105tku ka\u017cdej godziny, po wype\u0142nieniu tabeli, statystyka <b>pg_stat_statements<\/b> jest resetowana za pomoc\u0105 <b>pg_stat_statements_reset()<\/b>.<br \/>\nUwaga: <i>statystyka jest zbierana dla zapyta\u0144 o czasie wykonania przekraczaj\u0105cym 1 sekund\u0119.<\/i><br \/>\n<b class=\"spoiler_title\">Wype\u0142nienie tabeli pg_stat_history<\/b><\/p>\n<pre><code class=\"plaintext\">--pg_stat_history.sql\nCREATE OR REPLACE FUNCTION pg_stat_history( ) RETURNS boolean AS $$\nDECLARE\n  endpoint_rec record ;\n  database_rec record ;\n  pg_stat_snapshot record ;\n  current_snapshot_timestamp timestamp without time zone;\nBEGIN\n  current_snapshot_timestamp = date_trunc('minute',now());  \n  \n  FOR endpoint_rec IN SELECT * FROM endpoint \n  LOOP\n    FOR database_rec IN SELECT * FROM database WHERE endpoint_id = endpoint_rec.id \n\t  LOOP\n\t    \n\t\tRAISE NOTICE 'NOWY ZR\u00d3D\u0141O JEST TWORZONE';\n\t\t\n\t\t--Po\u0142\u0105cz z docelow\u0105 baz\u0105 danych\t  \n\t    EXECUTE 'SELECT dblink_connect(''LINK1'',''host='||endpoint_rec.host||' dbname='||database_rec.name||' user=USER password=PASSWORD '')';\n \n        RAISE NOTICE 'host % i dbname % ',endpoint_rec.host,database_rec.name;\n\t\tRAISE NOTICE 'Tworzenie zrzutu pg_stat_statements dla bazy danych %',database_rec.name;\n\t\t\n\t\tSELECT \n\t      *\n\t\tINTO \n\t\t  pg_stat_snapshot\n\t    FROM dblink('LINK1',\n\t      'SELECT \n\t       dbid , SUM(calls),SUM(total_time),SUM(rows) ,SUM(shared_blks_hit) ,SUM(shared_blks_read) ,SUM(shared_blks_dirtied) ,SUM(shared_blks_written) , \n           SUM(local_blks_hit) , SUM(local_blks_read) , SUM(local_blks_dirtied) , SUM(local_blks_written) , SUM(temp_blks_read) , SUM(temp_blks_written) , SUM(blk_read_time) , SUM(blk_write_time)\n\t       FROM pg_stat_statements WHERE dbid=(SELECT oid from pg_database where datname=current_database() ) \n\t\t   GROUP BY dbid\n  \t      '\n\t               )\n\t      AS t\n\t       ( dbid oid , calls bigint , \n  \t         total_time double precision , \n\t         rows bigint , shared_blks_hit bigint , shared_blks_read bigint ,shared_blks_dirtied bigint ,shared_blks_written\t bigint ,\n             local_blks_hit\t bigint ,local_blks_read bigint , local_blks_dirtied bigint ,local_blks_written bigint ,\n             temp_blks_read\t bigint ,temp_blks_written bigint ,\n             blk_read_time double precision , blk_write_time double precision\t  \n\t       );\n\t\t \n\t\tINSERT INTO pg_stat_history\n          ( \n\t\t    snapshot_timestamp  ,database_id  ,\n\t\t\tdbid , calls  ,total_time ,\n            rows ,shared_blks_hit  ,shared_blks_read  ,shared_blks_dirtied  ,shared_blks_written ,local_blks_hit , \t \t\n            local_blks_read,local_blks_dirtied,local_blks_written,temp_blks_read,temp_blks_written, \t\n            blk_read_time, blk_write_time \n\t\t  )\t\t  \n\t    VALUES\n\t      (\n\t       current_snapshot_timestamp ,\n\t\t   database_rec.id ,\n\t       pg_stat_snapshot.dbid ,pg_stat_snapshot.calls,\n\t       pg_stat_snapshot.total_time,\n\t       pg_stat_snapshot.rows ,pg_stat_snapshot.shared_blks_hit ,pg_stat_snapshot.shared_blks_read ,pg_stat_snapshot.shared_blks_dirtied ,pg_stat_snapshot.shared_blks_written , \n           pg_stat_snapshot.local_blks_hit , pg_stat_snapshot.local_blks_read , pg_stat_snapshot.local_blks_dirtied , pg_stat_snapshot.local_blks_written , \n\t       pg_stat_snapshot.temp_blks_read , pg_stat_snapshot.temp_blks_written , pg_stat_snapshot.blk_read_time , pg_stat_snapshot.blk_write_time \t   \n\t      );\t\t   \n\t\t  \n        RAISE NOTICE 'Tworzenie zrzutu pg_stat_statements dla zapyta\u0144 z min_time wi\u0119kszym ni\u017c 1000ms';\n\t\n        FOR pg_stat_snapshot IN\n          --Wszystkie zapytania z max_time wi\u0119kszym ni\u017c 1000 ms\n\t      SELECT \n\t        *\n\t      FROM dblink('LINK1',\n\t        'SELECT \n\t         dbid , userid ,queryid,query,calls,total_time,min_time ,max_time,mean_time, stddev_time ,rows ,shared_blks_hit ,\n\t\t\t shared_blks_read ,shared_blks_dirtied ,shared_blks_written , \n             local_blks_hit , local_blks_read , local_blks_dirtied , \n\t\t\t local_blks_written , temp_blks_read , temp_blks_written , blk_read_time , \n\t\t\t blk_write_time\n\t         FROM pg_stat_statements \n\t\t\t WHERE dbid=(SELECT oid from pg_database where datname=current_database() AND min_time &gt;= 1000 ) \n  \t        '\n\n\t                  )\n\t        AS t\n\t         ( dbid oid , userid oid , queryid bigint ,query text , calls bigint , \n  \t           total_time double precision ,min_time double precision\t ,max_time double precision\t , mean_time double precision\t ,  stddev_time double precision\t , \n\t           rows bigint , shared_blks_hit bigint , shared_blks_read bigint ,shared_blks_dirtied bigint ,shared_blks_written\t bigint ,\n               local_blks_hit\t bigint ,local_blks_read bigint , local_blks_dirtied bigint ,local_blks_written bigint ,\n               temp_blks_read\t bigint ,temp_blks_written bigint ,\n               blk_read_time double precision , blk_write_time double precision\t  \n\t         )\n\t    LOOP\n\t\t  INSERT INTO pg_stat_history\n          ( \n\t\t    snapshot_timestamp  ,database_id  ,\n\t\t\tdbid ,userid  , queryid  , query  , calls  ,total_time ,min_time ,max_time ,mean_time ,stddev_time ,\n            rows ,shared_blks_hit  ,shared_blks_read  ,shared_blks_dirtied  ,shared_blks_written ,local_blks_hit , \t \t\n            local_blks_read,local_blks_dirtied,local_blks_written,temp_blks_read,temp_blks_written, \t\n            blk_read_time, blk_write_time \n\t\t  )\t\t  \n\t      VALUES\n\t      (\n\t       current_snapshot_timestamp ,\n\t\t   database_rec.id ,\n\t       pg_stat_snapshot.dbid ,pg_stat_snapshot.userid ,pg_stat_snapshot.queryid,pg_stat_snapshot.query,pg_stat_snapshot.calls,\n\t       pg_stat_snapshot.total_time,pg_stat_snapshot.min_time ,pg_stat_snapshot.max_time,pg_stat_snapshot.mean_time, pg_stat_snapshot.stddev_time ,\n\t       pg_stat_snapshot.rows ,pg_stat_snapshot.shared_blks_hit ,pg_stat_snapshot.shared_blks_read ,pg_stat_snapshot.shared_blks_dirtied ,pg_stat_snapshot.shared_blks_written , \n           pg_stat_snapshot.local_blks_hit , pg_stat_snapshot.local_blks_read , pg_stat_snapshot.local_blks_dirtied , pg_stat_snapshot.local_blks_written , \n\t       pg_stat_snapshot.temp_blks_read , pg_stat_snapshot.temp_blks_written , pg_stat_snapshot.blk_read_time , pg_stat_snapshot.blk_write_time \t   \n\t      );\n\t\t  \n        END LOOP;\n\n        PERFORM dblink_disconnect('LINK1');  \n\t\t\t\t\n\t  END LOOP ;--FOR database_rec IN SELECT * FROM database WHERE endpoint_id = endpoint_rec.id \n    \n  END LOOP;\n\nRETURN TRUE;  \nEND\n$$ LANGUAGE plpgsql;<\/code><\/pre>\n<p>W rezultacie, po pewnym okresie czasu w tabeli <b>pg_stat_history<\/b> b\u0119dziemy mieli zestaw zrzut\u00f3w zawarto\u015bci tabeli <b>pg_stat_statements <\/b>docelowej bazy danych. <\/p>\n<h2>Faktyczne raportowanie<\/h2>\n<p>\nU\u017cywaj\u0105c prostych zapyta\u0144, mo\u017cna uzyska\u0107 ca\u0142kiem przydatne i interesuj\u0105ce raporty.<\/p>\n<h2>Zaggregowane dane za podany okres czasu<\/h2>\n<p><b class=\"spoiler_title\">Zapytanie<\/b><\/p>\n<pre><code class=\"plaintext\">SELECT \n  database_id , \n  SUM(calls) AS calls ,SUM(total_time)  AS total_time ,\n  SUM(rows) AS rows , SUM(shared_blks_hit)  AS shared_blks_hit,\n  SUM(shared_blks_read) AS shared_blks_read ,\n  SUM(shared_blks_dirtied) AS shared_blks_dirtied,\n  SUM(shared_blks_written)  AS shared_blks_written , \n  SUM(local_blks_hit) AS local_blks_hit , \n  SUM(local_blks_read) AS local_blks_read , \n  SUM(local_blks_dirtied) AS local_blks_dirtied , \n  SUM(local_blks_written)  AS local_blks_written,\n  SUM(temp_blks_read) AS temp_blks_read, \n  SUM(temp_blks_written) temp_blks_written , \n  SUM(blk_read_time) AS blk_read_time , \n  SUM(blk_write_time) AS blk_write_time\nFROM \n  pg_stat_history\nWHERE \n  queryid IS NULL AND\n  database_id = DATABASE_ID  AND\n  snapshot_timestamp BETWEEN BEGIN_TIMEPOINT AND END_TIMEPOINT\nGROUP BY database_id ;<\/code><\/pre>\n<p><\/p>\n<h4>Czas DB<\/h4>\n<blockquote><p>to_char(interval '1 millisecond' * pg_total_stat_history_rec.total_time, 'HH24:MI:SS.MS')<\/p><\/blockquote>\n<p><\/p>\n<h4>Czas I\/O<\/h4>\n<blockquote><p>to_char(interval '1 millisecond' * (pg_total_stat_history_rec.blk_read_time + pg_total_stat_history_rec.blk_write_time), 'HH24:MI:SS.MS')<\/p><\/blockquote>\n<h3>TOP10 SQL wed\u0142ug total_time<\/h3>\n<p><b class=\"spoiler_title\">Zapytanie<\/b><\/p>\n<pre><code class=\"plaintext\">SELECT \n  queryid , \n  SUM(calls) AS calls ,\n  SUM(total_time)  AS total_time  \t\nFROM \n  pg_stat_history\nWHERE \n  queryid IS NOT NULL AND \n  database_id = DATABASE_ID AND\n  snapshot_timestamp BETWEEN BEGIN_TIMEPOINT AND END_TIMEPOINT \nGROUP BY queryid \nORDER BY 3 DESC \nLIMIT 10<\/code><\/pre>\n<pre>-------------------------------------------------------------------------------------\n| TOP10 SQL WED\u0141UG CA\u0141KOWITEGO CZASU WYKONANIA\n|   #|    queryid|      calls|    calls %|                total_time (ms) |  dbtime %\n+----+-----------+-----------+-----------+--------------------------------+----------\n|   1|  821760255|          2|     .00001|00:03:23.141(    203141.681 ms.)|      5.42\n|   2| 4152624390|          2|     .00001|00:03:13.929(    193929.215 ms.)|      5.17\n|   3| 1484454471|          4|     .00001|00:02:09.129(    129129.057 ms.)|      3.44\n|   4|  655729273|          1|     .00000|00:02:01.869(    121869.981 ms.)|      3.25\n|   5| 2460318461|          1|     .00000|00:01:33.113(     93113.835 ms.)|      2.48\n|   6| 2194493487|          4|     .00001|00:00:17.377(     17377.868 ms.)|       .46\n|   7| 1053044345|          1|     .00000|00:00:06.156(      6156.352 ms.)|       .16\n|   8| 3644780286|          1|     .00000|00:00:01.063(      1063.830 ms.)|       .03\n<\/pre>\n<h4>TOP10 SQL wed\u0142ug ca\u0142kowitego czasu I\/O<\/h4>\n<p><b class=\"spoiler_title\">Zapytanie<\/b><\/p>\n<pre><code class=\"plaintext\">SELECT \n  queryid , \n  SUM(calls) AS calls ,\n  SUM(blk_read_time + blk_write_time)  AS io_time\nFROM \n  pg_stat_history\nWHERE \n  queryid IS NOT NULL AND \n  database_id = DATABASE_ID  AND\n  snapshot_timestamp BETWEEN BEGIN_TIMEPOINT AND END_TIMEPOINT\nGROUP BY  queryid \nORDER BY 3 DESC \nLIMIT 10<\/code><\/pre>\n<pre>----------------------------------------------------------------------------------------\n| TOP10 SQL WED\u0141UG CA\u0141KOWYTEGO CZASU I\/O\n|   #|    queryid|      wywo\u0142ania|    % wywo\u0142a\u0144|                   czas I\/O (ms)|% czasu I\/O bazy danych\n+----+-----------+-----------+-----------+--------------------------------+-------------\n|   1| 4152624390|          2|     .00001|00:08:31.616(    511616.592 ms.)|        31.06\n|   2|  821760255|          2|     .00001|00:08:27.099(    507099.036 ms.)|        30.78\n|   3|  655729273|          1|     .00000|00:05:02.209(    302209.137 ms.)|        18.35\n|   4| 2460318461|          1|     .00000|00:04:05.981(    245981.117 ms.)|        14.93\n|   5| 1484454471|          4|     .00001|00:00:39.144(     39144.221 ms.)|         2.38\n|   6| 2194493487|          4|     .00001|00:00:18.182(     18182.816 ms.)|         1.10\n|   7| 1053044345|          1|     .00000|00:00:16.611(     16611.722 ms.)|         1.01\n|   8| 3644780286|          1|     .00000|00:00:00.436(       436.205 ms.)|          .03\n<\/pre>\n<h4>TOP10 SQL wed\u0142ug maksymalnego czasu wykonania<\/h4>\n<p><b class=\"spoiler_title\">Zapytanie<\/b><\/p>\n<pre><code class=\"plaintext\">WYBIERZ \n  id AS snapshotid , \n  queryid , \n  snapshot_timestamp ,  \n  max_time \nZ \n  pg_stat_history \nGDZIE \n  queryid NIE JEST NULL I \n  database_id = DATABASE_ID  I\n  snapshot_timestamp POMI\u0118DZY BEGIN_TIMEPOINT A END_TIMEPOINT\nZAM\u00d3W WED\u0141UG 4 DESC \nLIMIT 10<\/code><\/pre>\n<p><\/p>\n<pre>-----------------------------------------------------------------------------------------\n| TOP10 SQL WED\u0141UG MAKSYMALNEGO CZASU WYKONANIA\n|   #|          snapshot| snapshotID|    queryid|                           max_time (ms)\n+----+------------------+-----------+-----------+----------------------------------------\n|   1|  05.04.2019 01:03|       4169|  655729273|        00:02:01.869(    121869.981 ms.)\n|   2|  04.04.2019 17:00|       4153|  821760255|        00:01:41.570(    101570.841 ms.)\n|   3|  04.04.2019 16:00|       4146|  821760255|        00:01:41.570(    101570.841 ms.)\n|   4|  04.04.2019 16:00|       4144| 4152624390|        00:01:36.964(     96964.607 ms.)\n|   5|  04.04.2019 17:00|       4151| 4152624390|        00:01:36.964(     96964.607 ms.)\n|   6|  05.04.2019 10:00|       4188| 1484454471|        00:01:33.452(     93452.150 ms.)\n|   7|  04.04.2019 17:00|       4150| 2460318461|        00:01:33.113(     93113.835 ms.)\n|   8|  04.04.2019 15:00|       4140| 1484454471|        00:00:11.892(     11892.302 ms.)\n|   9|  04.04.2019 16:00|       4145| 1484454471|        00:00:11.892(     11892.302 ms.)\n|  10|  04.04.2019 17:00|       4152| 1484454471|        00:00:11.892(     11892.302 ms.)\n<\/pre>\n<h4>TOP10 SQL wed\u0142ug odczytu\/zapisu bufora SHARED<\/h4>\n<p><b class=\"spoiler_title\">Zapytanie<\/b><\/p>\n<pre><code class=\"plaintext\">WYBIERZ \n  id AS snapshotid , \n  queryid ,\n  snapshot_timestamp , \n  shared_blks_read , \n  shared_blks_written \nZ \n  pg_stat_history\nGDZIE \n  queryid NIE JEST NULL I \n  database_id = DATABASE_ID  I\n  snapshot_timestamp POMI\u0118DZY BEGIN_TIMEPOINT A END_TIMEPOINT I\n  ( shared_blks_read &gt; 0 LUB shared_blks_written &gt; 0 )\nZAM\u00d3W WED\u0141UG 4 DESC  , 5 DESC \nLIMIT 10<\/code><\/pre>\n<pre>--------------------------------------------------------------------------------------------\n| TOP10 SQL ZA ODCZYT\/ZAPIS BUFRA WDZIELONEGO\n|   #|          zrzut| snapshotID|    queryid|   odczytane bloki wsp\u00f3\u0142dzielone|  zapisane bloki wsp\u00f3\u0142dzielone\n+----+------------------+-----------+-----------+---------------------+---------------------\n|   1|  04.04.2019 17:00|       4153|  821760255|               797308|                    0\n|   2|  04.04.2019 16:00|       4146|  821760255|               797308|                    0\n|   3|  05.04.2019 01:03|       4169|  655729273|               797158|                    0\n|   4|  04.04.2019 16:00|       4144| 4152624390|               756514|                    0\n|   5|  04.04.2019 17:00|       4151| 4152624390|               756514|                    0\n|   6|  04.04.2019 17:00|       4150| 2460318461|               734117|                    0\n|   7|  04.04.2019 17:00|       4155| 3644780286|                52973|                    0\n|   8|  05.04.2019 01:03|       4168| 1053044345|                52818|                    0\n|   9|  04.04.2019 15:00|       4141| 2194493487|                52813|                    0\n|  10|  04.04.2019 16:00|       4147| 2194493487|                52813|                    0\n--------------------------------------------------------------------------------------------\n<\/pre>\n<h4>Histogram rozk\u0142adu zapyta\u0144 wed\u0142ug maksymalnego czasu wykonania<\/h4>\n<p><b class=\"spoiler_title\">Zapytania<\/b><\/p>\n<pre><code class=\"plaintext\">SELECT  \n  MIN(max_time) AS hist_min  , \n  MAX(max_time) AS hist_max , \n  (( MAX(max_time) - MIN(min_time) ) \/ hist_columns ) as hist_width\nFROM \n  pg_stat_history \nWHERE \n  queryid IS NOT NULL AND\n  database_id = DATABASE_ID  AND\n  snapshot_timestamp BETWEEN BEGIN_TIMEPOINT AND END_TIMEPOINT ;\n\nSELECT \n  SUM(calls) AS calls\nFROM \n  pg_stat_history \nWHERE \n  queryid IS NOT NULL AND\n  database_id = DATABASE_ID  AND\n  snapshot_timestamp BETWEEN BEGIN_TIMEPOINT AND END_TIMEPOINT AND \n  ( max_time &gt;= hist_current_min AND  max_time &lt; hist_current_max ) ;\n<\/code><\/pre>\n<pre>|-----------------------------------------------------------------------------------------------\n| HISTOGRAM CZASU MAX_TIME\n| \u0141\u0104CZNA LICZBA ZDA\u0143 : 33851920\n| MIN CZAS  : 00:00:01.063\n| MAKS CZAS  : 00:02:01.869\n---------------------------------------------------------------------------------\n|                      minimalny czas trwania|                      maksymalny czas trwania|     liczba zda\u0144\n+----------------------------------+----------------------------------+----------\n| 00:00:01.063(      1063.830 ms.) | 00:00:13.144(     13144.445 ms.) | 9\n| 00:00:13.144(     13144.445 ms.) | 00:00:25.225(     25225.060 ms.) | 0\n| 00:00:25.225(     25225.060 ms.) | 00:00:37.305(     37305.675 ms.) | 0\n| 00:00:37.305(     37305.675 ms.) | 00:00:49.386(     49386.290 ms.) | 0\n| 00:00:49.386(     49386.290 ms.) | 00:01:01.466(     61466.906 ms.) | 0\n| 00:01:01.466(     61466.906 ms.) | 00:01:13.547(     73547.521 ms.) | 0\n| 00:01:13.547(     73547.521 ms.) | 00:01:25.628(     85628.136 ms.) | 0\n| 00:01:25.628(     85628.136 ms.) | 00:01:37.708(     97708.751 ms.) | 4\n| 00:01:37.708(     97708.751 ms.) | 00:01:49.789(    109789.366 ms.) | 2\n| 00:01:49.789(    109789.366 ms.) | 00:02:01.869(    121869.981 ms.) | 0\n<\/pre>\n<h4>TOP10 Zrzut\u00f3w wed\u0142ug Zapytania na Sekund\u0119<\/h4>\n<p><b class=\"spoiler_title\">Zapytania<\/b><\/p>\n<pre><code class=\"plaintext\">--pg_qps.sql\n--Oblicz zapytania na sekund\u0119\nCREATE OR REPLACE FUNCTION pg_qps( pg_stat_history_id integer ) RETURNS double precision AS $$\nDECLARE\n pg_stat_history_rec record ;\n prev_pg_stat_history_id integer ;\n prev_pg_stat_history_rec record;\n total_seconds double precision ;\n result double precision;\nBEGIN \n  result = 0 ;\n  \n  SELECT *\n  INTO pg_stat_history_rec\n  FROM \n    pg_stat_history\n  WHERE id = pg_stat_history_id ;\n\n  IF pg_stat_history_rec.snapshot_timestamp IS NULL \n  THEN\n    RAISE EXCEPTION 'B\u0141\u0104D - Nie znaleziono pg_stat_history dla id = %',pg_stat_history_id;\n  END IF ;  \n  \n --RAISE NOTICE 'pg_stat_history_id = % , snapshot_timestamp = %', pg_stat_history_id , \n pg_stat_history_rec.snapshot_timestamp ;\n  \n  SELECT \n    MAX(id)   \n  INTO\n    prev_pg_stat_history_id\n  FROM\n    pg_stat_history\n  WHERE \n    database_id = pg_stat_history_rec.database_id AND\n\tqueryid IS NULL AND\n\tid  0 \n  THEN\n    result = pg_stat_history_rec.calls \/ total_seconds ;\n  ELSE\n   result = 0 ; \n  END IF;\n   \n RETURN result ;\nEND\n$$ LANGUAGE plpgsql;\n\n\nSELECT \n  id , \n  snapshot_timestamp ,\n  calls , \t\n  total_time , \n  ( select pg_qps( id )) AS QPS ,\n  blk_read_time ,\n  blk_write_time\nFROM \n  pg_stat_history\nWHERE \n  queryid IS NULL AND \n  database_id = DATABASE_ID  AND\n  snapshot_timestamp BETWEEN BEGIN_TIMEPOINT AND END_TIMEPOINT AND\n  ( select pg_qps( id )) IS NOT NULL \nORDER BY 5 DESC \nLIMIT 10\n<\/code><\/pre>\n<pre>|-----------------------------------------------------------------------------------------------\n| TOP10 Zrzut\u00f3w zam\u00f3wionych wed\u0142ug liczby QPS\n-----------------------------------------------------------------------------------------------------------------------------------------------\n|    #|          zrzut| ID zrzutu|      wywo\u0142ania|                      ca\u0142kowity czas db|        QPS|                          Czas I\/O| % Czasu I\/O\n+-----+------------------+-----------+-----------+----------------------------------+-----------+----------------------------------+-----------\n|    1|  04.04.2019 20:04|       4161|    5758631|  00:06:30.513(    390513.926 ms.)|   1573.396|  00:00:01.470(      1470.110 ms.)|       .376\n|    2|  04.04.2019 17:00|       4149|    3529197|  00:11:48.830(    708830.618 ms.)|    980.332|  00:12:47.834(    767834.052 ms.)|    108.324\n|    3|  04.04.2019 16:00|       4143|    3525360|  00:10:13.492(    613492.351 ms.)|    979.267|  00:08:41.396(    521396.555 ms.)|     84.988\n|    4|  04.04.2019 21:03|       4163|    2781536|  00:03:06.470(    186470.979 ms.)|    785.745|  00:00:00.249(       249.865 ms.)|       .134\n|    5|  04.04.2019 19:03|       4159|    2890362|  00:03:16.784(    196784.755 ms.)|    776.979|  00:00:01.441(      1441.386 ms.)|       .732\n|    6|  04.04.2019 14:00|       4137|    2397326|  00:04:43.033(    283033.854 ms.)|    665.924|  00:00:00.024(        24.505 ms.)|       .009\n|    7|  04.04.2019 15:00|       4139|    2394416|  00:04:51.435(    291435.010 ms.)|    665.116|  00:00:12.025(     12025.895 ms.)|      4.126\n|    8|  04.04.2019 13:00|       4135|    2373043|  00:04:26.791(    266791.988 ms.)|    659.179|  00:00:00.064(        64.261 ms.)|       .024\n|    9|  05.04.2019 01:03|       4167|    4387191|  00:06:51.380(    411380.293 ms.)|    609.332|  00:05:18.847(    318847.407 ms.)|     77.507\n|   10|  04.04.2019 18:01|       4157|    1145596|  00:01:19.217(     79217.372 ms.)|    313.004|  00:00:01.319(      1319.676 ms.)|      1.666\n<\/pre>\n<h4>Godzinowa historia wykonania z QPS i czasem I\/O<\/h4>\n<p><b class=\"spoiler_title\">Zapytanie<\/b><\/p>\n<pre><code class=\"plaintext\">SELECT \n  id , \n  timestamp_zrzutu ,\n  wywo\u0142ania , \t\n  ca\u0142kowity_czas , \n  ( select pg_qps( id )) AS QPS ,\n  czas_czytania_blk ,\n  czas_zapisu_blk\nFROM \n  pg_stat_history\nWHERE \n  queryid IS NULL AND \n  database_id = DATABASE_ID  AND\n  timestamp_zrzutu BETWEEN BEGIN_TIMEPOINT AND END_TIMEPOINT\nORDER BY 2\n<\/code><\/pre>\n<pre>|-----------------------------------------------------------------------------------------------\n| HISTORIA WYKONANIA CO GODZIN\u0118 Z QueryPerSeconds i Czasem I\/O\n-----------------------------------------------------------------------------------------------------------------------------------------------\n| HISTORIA ZAPYTANIA NA SEKUND\u0118\n|    #|          zrzut| snapshotID|      wywo\u0142ania|                      ca\u0142kowity czas db|        QPS|                          czas I\/O| % czasu I\/O\n+-----+------------------+-----------+-----------+----------------------------------+-----------+----------------------------------+-----------\n|    1|  04.04.2019 11:00|       4131|       3747|  00:00:00.835(       835.374 ms.)|      1.041|  00:00:00.000(          .000 ms.)|       .000\n|    2|  04.04.2019 12:00|       4133|    1002722|  00:01:52.419(    112419.376 ms.)|    278.534|  00:00:00.149(       149.105 ms.)|       .133\n|    3|  04.04.2019 13:00|       4135|    2373043|  00:04:26.791(    266791.988 ms.)|    659.179|  00:00:00.064(        64.261 ms.)|       .024\n|    4|  04.04.2019 14:00|       4137|    2397326|  00:04:43.033(    283033.854 ms.)|    665.924|  00:00:00.024(        24.505 ms.)|       .009\n|    5|  04.04.2019 15:00|       4139|    2394416|  00:04:51.435(    291435.010 ms.)|    665.116|  00:00:12.025(     12025.895 ms.)|      4.126\n|    6|  04.04.2019 16:00|       4143|    3525360|  00:10:13.492(    613492.351 ms.)|    979.267|  00:08:41.396(    521396.555 ms.)|     84.988\n|    7|  04.04.2019 17:00|       4149|    3529197|  00:11:48.830(    708830.618 ms.)|    980.332|  00:12:47.834(    767834.052 ms.)|    108.324\n|    8|  04.04.2019 18:01|       4157|    1145596|  00:01:19.217(     79217.372 ms.)|    313.004|  00:00:01.319(      1319.676 ms.)|      1.666\n|    9|  04.04.2019 19:03|       4159|    2890362|  00:03:16.784(    196784.755 ms.)|    776.979|  00:00:01.441(      1441.386 ms.)|       .732\n|   10|  04.04.2019 20:04|       4161|    5758631|  00:06:30.513(    390513.926 ms.)|   1573.396|  00:00:01.470(      1470.110 ms.)|       .376\n|   11|  04.04.2019 21:03|       4163|    2781536|  00:03:06.470(    186470.979 ms.)|    785.745|  00:00:00.249(       249.865 ms.)|       .134\n|   12|  04.04.2019 23:03|       4165|    1443155|  00:01:34.467(     94467.539 ms.)|    200.438|  00:00:00.015(        15.287 ms.)|       .016\n|   13|  05.04.2019 01:03|       4167|    4387191|  00:06:51.380(    411380.293 ms.)|    609.332|  00:05:18.847(    318847.407 ms.)|     77.507\n|   14|  05.04.2019 02:03|       4171|     189852|  00:00:10.989(     10989.899 ms.)|     52.737|  00:00:00.539(       539.110 ms.)|      4.906\n|   15|  05.04.2019 03:01|       4173|       3627|  00:00:00.103(       103.000 ms.)|      1.042|  00:00:00.004(         4.131 ms.)|      4.010\n|   16|  05.04.2019 04:00|       4175|       3627|  00:00:00.085(        85.235 ms.)|      1.025|  00:00:00.003(         3.811 ms.)|      4.471\n|   17|  05.04.2019 05:00|       4177|       3747|  00:00:00.849(       849.454 ms.)|      1.041|  00:00:00.006(         6.124 ms.)|       .721\n|   18|  05.04.2019 06:00|       4179|       3747|  00:00:00.849(       849.561 ms.)|      1.041|  00:00:00.000(          .051 ms.)|       .006\n|   19|  05.04.2019 07:00|       4181|       3747|  00:00:00.839(       839.416 ms.)|      1.041|  00:00:00.000(          .062 ms.)|       .007\n|   20|  05.04.2019 08:00|       4183|       3747|  00:00:00.846(       846.382 ms.)|      1.041|  00:00:00.000(          .007 ms.)|       .001\n|   21|  05.04.2019 09:00|       4185|       3747|  00:00:00.855(       855.426 ms.)|      1.041|  00:00:00.000(          .065 ms.)|       .008\n|   22|  05.04.2019 10:00|       4187|       3797|  00:01:40.150(    100150.165 ms.)|      1.055|  00:00:21.845(     21845.217 ms.)|     21.812\n<\/pre>\n<h4>Tekst wszystkich zapyta\u0144 SQL<\/h4>\n<p><b class=\"spoiler_title\">Zapytanie<\/b><\/p>\n<pre><code class=\"plaintext\">SELECT \n  queryid , \n  query \nFROM \n  pg_stat_history\nWHERE \n  queryid IS NOT NULL AND \n  database_id = DATABASE_ID  AND\n  snapshot_timestamp BETWEEN BEGIN_TIMEPOINT AND END_TIMEPOINT\nGROUP BY queryid , query\n<\/code><\/pre>\n<h2>Podsumowanie<\/h2>\n<p>\nJak wida\u0107, stosunkowo prostymi \u015brodkami mo\u017cna uzyska\u0107 stosunkowo du\u017co u\u017cytecznych informacji o obci\u0105\u017ceniu i stanie bazy. <\/p>\n<p><b>Uwaga:<\/b>Je\u015bli w zapytaniach zarejestrujemy queryid, otrzymamy histori\u0119 dla poszczeg\u00f3lnych zapyta\u0144 (w celu zaoszcz\u0119dzenia miejsca, raporty dla osobnych zapyta\u0144 zosta\u0142y pomini\u0119te).<\/p>\n<p>Tak wi\u0119c, dane statystyczne dotycz\u0105ce wydajno\u015bci zapyta\u0144 s\u0105 dost\u0119pne i zbierane.<br \/>\nPierwszy etap \"zbierania danych statystycznych\" \u2014 zako\u0144czony.<\/p>\n<p>Mo\u017cna przej\u015b\u0107 do drugiego etapu - \"konfiguracja metryk wydajno\u015bci\".<br \/>\n<img decoding=\"async\" alt=\"Monitorowanie wydajno\u015bci zapyta\u0144 PostgreSQL. Cz\u0119\u015b\u0107 1 \u2014 raportowanie\" src=\"\/wp-content\/uploads\/2019\/04\/a893e49280d4cb425e4667a5c51d2397.jpeg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n<br \/>\n<b>Ale to ju\u017c zupe\u0142nie inna historia.<\/b><\/p>\n<p><i>Ci\u0105g dalszy nast\u0105pi\u2026<\/i><br \/>\n<br \/>\u0179r\u00f3d\u0142o: <a content=\"nofollow\" rel=\"nofollow\" href=\"https:\/\/habr.com\/ru\/company\/icl_services\/blog\/446734\/\">habr.com<\/a><\/p>","protected":false,"gt_translate_keys":[{"key":"rendered","format":"html"}]},"excerpt":{"rendered":"<p>\u0418\u043d\u0436\u0435\u043d\u0435\u0440 \u2014 \u0432 \u043f\u0435\u0440\u0435\u0432\u043e\u0434\u0435 \u0441 \u043b\u0430\u0442\u044b\u043d\u0438 \u2014 \u0432\u0434\u043e\u0445\u043d\u043e\u0432\u0435\u043d\u043d\u044b\u0439. \u0418\u043d\u0436\u0435\u043d\u0435\u0440 \u043c\u043e\u0436\u0435\u0442 \u0432\u0441\u0451. (\u0441) \u0420.\u0414\u0438\u0437\u0435\u043b\u044c. \u042d\u043f\u0438\u0433\u0440\u0430\u0444\u044b. \u0418\u043b\u0438 \u0438\u0441\u0442\u043e\u0440\u0438\u044f \u043e \u0442\u043e\u043c, \u0437\u0430\u0447\u0435\u043c \u0430\u0434\u043c\u0438\u043d\u0438\u0441\u0442\u0440\u0430\u0442\u043e\u0440\u0443 \u0431\u0430\u0437 \u0434\u0430\u043d\u043d\u044b\u0445 \u0432\u0441\u043f\u043e\u043c\u0438\u043d\u0430\u0442\u044c \u0441\u0432\u043e\u0435 \u043f\u0440\u043e\u0433\u0440\u0430\u043c\u043c\u0438\u0441\u0442\u0441\u043a\u043e\u0435 \u043f\u0440\u043e\u0448\u043b\u043e\u0435. \u041f\u0440\u0435\u0434\u0438\u0441\u043b\u043e\u0432\u0438\u0435 \u0412\u0441\u0435 \u0438\u043c\u0435\u043d\u0430 \u0438\u0437\u043c\u0435\u043d\u0435\u043d\u044b. \u0421\u043e\u0432\u043f\u0430\u0434\u0435\u043d\u0438\u044f \u0441\u043b\u0443\u0447\u0430\u0439\u043d\u044b. \u041c\u0430\u0442\u0435\u0440\u0438\u0430\u043b \u043f\u0440\u0435\u0434\u0441\u0442\u0430\u0432\u043b\u044f\u0435\u0442 \u0441\u043e\u0431\u043e\u0439 \u0438\u0441\u043a\u043b\u044e\u0447\u0438\u0442\u0435\u043b\u044c\u043d\u043e \u043b\u0438\u0447\u043d\u043e\u0435 \u043c\u043d\u0435\u043d\u0438\u0435 \u0430\u0432\u0442\u043e\u0440\u0430. Disclaimer of warranties: \u0432 \u043f\u043b\u0430\u043d\u0438\u0440\u0443\u0435\u043c\u043e\u043c \u0446\u0438\u043a\u043b\u0435 \u0441\u0442\u0430\u0442\u0435\u0439 \u043d\u0435 \u0431\u0443\u0434\u0435\u0442 \u043f\u043e\u0434\u0440\u043e\u0431\u043d\u043e\u0433\u043e \u0438 \u0442\u043e\u0447\u043d\u043e\u0433\u043e \u043e\u043f\u0438\u0441\u0430\u043d\u0438\u044f \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u043c\u044b\u0445 \u0442\u0430\u0431\u043b\u0438\u0446 \u0438 [&hellip;]<\/p>\n","protected":false,"gt_translate_keys":[{"key":"rendered","format":"html"}]},"author":1,"featured_media":24168,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[688],"tags":[],"class_list":["post-32353","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-administrirovanie"],"aioseo_notices":[],"aioseo_head":"\n\t\t<!-- All in One SEO 5.0.1.1 - aioseo.com -->\n\t<meta name=\"description\" content=\"\u0418\u043d\u0436\u0435\u043d\u0435\u0440 \u2014 \u0432 \u043f\u0435\u0440\u0435\u0432\u043e\u0434\u0435 \u0441 \u043b\u0430\u0442\u044b\u043d\u0438 \u2014 \u0432\u0434\u043e\u0445\u043d\u043e\u0432\u0435\u043d\u043d\u044b\u0439. \u0418\u043d\u0436\u0435\u043d\u0435\u0440 \u043c\u043e\u0436\u0435\u0442 \u0432\u0441\u0451. (\u0441) \u0420.\u0414\u0438\u0437\u0435\u043b\u044c. \u042d\u043f\u0438\u0433\u0440\u0430\u0444\u044b.\" \/>\n\t<meta name=\"robots\" content=\"max-image-preview:large\" \/>\n\t<meta name=\"author\" content=\"Yuri Gagarin\"\/>\n\t<link rel=\"canonical\" href=\"https:\/\/prohoster.info\/pl\/blog\/administrirovanie\/monitoring-proizvoditelnosti-zaprosov-postgresql-chast-1-reporting\" \/>\n\t<meta name=\"generator\" content=\"All in One SEO (AIOSEO) 5.0.1.1\" \/>\n\t\t<meta property=\"og:locale\" content=\"pl_PL\" \/>\n\t\t<meta property=\"og:site_name\" content=\"ProHoster | \u041a\u0443\u043f\u0438\u0442\u044c \u043d\u0430\u0434\u0435\u0436\u043d\u044b\u0439 \u0445\u043e\u0441\u0442\u0438\u043d\u0433 \u0434\u043b\u044f \u0441\u0430\u0439\u0442\u043e\u0432 \u0441 \u0437\u0430\u0449\u0438\u0442\u043e\u0439 \u043e\u0442 DDoS, VPS VDS \u0441\u0435\u0440\u0432\u0435\u0440\u044b\" \/>\n\t\t<meta property=\"og:type\" content=\"article\" \/>\n\t\t<meta property=\"og:title\" content=\"\ud83e\udd47\u041c\u043e\u043d\u0438\u0442\u043e\u0440\u0438\u043d\u0433 \u043f\u0440\u043e\u0438\u0437\u0432\u043e\u0434\u0438\u0442\u0435\u043b\u044c\u043d\u043e\u0441\u0442\u0438 \u0437\u0430\u043f\u0440\u043e\u0441\u043e\u0432 PostgreSQL. \u0427\u0430\u0441\u0442\u044c 1 \u2014 \u0440\u0435\u043f\u043e\u0440\u0442\u0438\u043d\u0433 | ProHoster\" \/>\n\t\t<meta property=\"og:description\" content=\"\u0418\u043d\u0436\u0435\u043d\u0435\u0440 \u2014 \u0432 \u043f\u0435\u0440\u0435\u0432\u043e\u0434\u0435 \u0441 \u043b\u0430\u0442\u044b\u043d\u0438 \u2014 \u0432\u0434\u043e\u0445\u043d\u043e\u0432\u0435\u043d\u043d\u044b\u0439. \u0418\u043d\u0436\u0435\u043d\u0435\u0440 \u043c\u043e\u0436\u0435\u0442 \u0432\u0441\u0451. (\u0441) \u0420.\u0414\u0438\u0437\u0435\u043b\u044c. \u042d\u043f\u0438\u0433\u0440\u0430\u0444\u044b.\" \/>\n\t\t<meta property=\"og:url\" content=\"https:\/\/prohoster.info\/pl\/blog\/administrirovanie\/monitoring-proizvoditelnosti-zaprosov-postgresql-chast-1-reporting\" \/>\n\t\t<meta property=\"og:image\" content=\"https:\/\/prohoster.info\/wp-content\/uploads\/2021\/11\/logo-350.jpg\" \/>\n\t\t<meta property=\"og:image:secure_url\" content=\"https:\/\/prohoster.info\/wp-content\/uploads\/2021\/11\/logo-350.jpg\" \/>\n\t\t<meta property=\"og:image:width\" content=\"350\" \/>\n\t\t<meta property=\"og:image:height\" content=\"350\" \/>\n\t\t<meta property=\"article:published_time\" content=\"2019-10-31T18:46:32+00:00\" \/>\n\t\t<meta property=\"article:modified_time\" content=\"2019-10-31T18:46:32+00:00\" \/>\n\t\t<meta property=\"article:publisher\" content=\"https:\/\/www.facebook.com\/prohoster\" \/>\n\t\t<meta property=\"article:author\" content=\"https:\/\/www.facebook.com\/prohoster\" \/>\n\t\t<!-- All in One SEO -->\n\n","aioseo_head_json":{"title":"\ud83e\udd47Monitoring wydajno\u015bci zapyta\u0144 PostgreSQL. Cz\u0119\u015b\u0107 1 \u2014 raportowanie | ProHoster","description":"In\u017cynier \u2014 w t\u0142umaczeniu z \u0142aciny \u2014 natchniony. In\u017cynier mo\u017ce wszystko. (c) R.Dizel. Epigrafy.","canonical_url":"https:\/\/prohoster.info\/pl\/blog\/administrirovanie\/monitoring-proizvoditelnosti-zaprosov-postgresql-chast-1-reporting","robots":"max-image-preview:large","keywords":"","webmasterTools":{"miscellaneous":""},"schema":null,"og:locale":"pl_PL","og:site_name":"ProHoster | \u041a\u0443\u043f\u0438\u0442\u044c \u043d\u0430\u0434\u0435\u0436\u043d\u044b\u0439 \u0445\u043e\u0441\u0442\u0438\u043d\u0433 \u0434\u043b\u044f \u0441\u0430\u0439\u0442\u043e\u0432 \u0441 \u0437\u0430\u0449\u0438\u0442\u043e\u0439 \u043e\u0442 DDoS, VPS VDS \u0441\u0435\u0440\u0432\u0435\u0440\u044b","og:type":"article","og:title":"\ud83e\udd47\u041c\u043e\u043d\u0438\u0442\u043e\u0440\u0438\u043d\u0433 \u043f\u0440\u043e\u0438\u0437\u0432\u043e\u0434\u0438\u0442\u0435\u043b\u044c\u043d\u043e\u0441\u0442\u0438 \u0437\u0430\u043f\u0440\u043e\u0441\u043e\u0432 PostgreSQL. \u0427\u0430\u0441\u0442\u044c 1 \u2014 \u0440\u0435\u043f\u043e\u0440\u0442\u0438\u043d\u0433 | ProHoster","og:description":"\u0418\u043d\u0436\u0435\u043d\u0435\u0440 \u2014 \u0432 \u043f\u0435\u0440\u0435\u0432\u043e\u0434\u0435 \u0441 \u043b\u0430\u0442\u044b\u043d\u0438 \u2014 \u0432\u0434\u043e\u0445\u043d\u043e\u0432\u0435\u043d\u043d\u044b\u0439. \u0418\u043d\u0436\u0435\u043d\u0435\u0440 \u043c\u043e\u0436\u0435\u0442 \u0432\u0441\u0451. (\u0441) \u0420.\u0414\u0438\u0437\u0435\u043b\u044c. \u042d\u043f\u0438\u0433\u0440\u0430\u0444\u044b.","og:url":"https:\/\/prohoster.info\/pl\/blog\/administrirovanie\/monitoring-proizvoditelnosti-zaprosov-postgresql-chast-1-reporting","og:image":"https:\/\/prohoster.info\/wp-content\/uploads\/2021\/11\/logo-350.jpg","og:image:secure_url":"https:\/\/prohoster.info\/wp-content\/uploads\/2021\/11\/logo-350.jpg","og:image:width":350,"og:image:height":350,"article:published_time":"2019-10-31T18:46:32+00:00","article:modified_time":"2019-10-31T18:46:32+00:00","article:publisher":"https:\/\/www.facebook.com\/prohoster","article:author":"https:\/\/www.facebook.com\/prohoster"},"aioseo_meta_data":{"post_id":"32353","title":null,"description":null,"keywords":null,"keyphrases":null,"primary_term":null,"canonical_url":null,"og_title":null,"og_description":null,"og_object_type":"default","og_image_type":"default","og_image_url":null,"og_image_width":null,"og_image_height":null,"og_image_custom_url":null,"og_image_custom_fields":null,"og_video":null,"og_custom_url":null,"og_article_section":null,"og_article_tags":null,"twitter_use_og":false,"twitter_card":"default","twitter_image_type":"default","twitter_image_url":null,"twitter_image_custom_url":null,"twitter_image_custom_fields":null,"twitter_title":null,"twitter_description":null,"schema":{"blockGraphs":[],"customGraphs":[],"default":{"data":{"Article":[],"Course":[],"Dataset":[],"FAQPage":[],"Movie":[],"Person":[],"Product":[],"ProductReview":[],"Car":[],"Recipe":[],"Service":[],"SoftwareApplication":[],"WebPage":[]},"graphName":"","isEnabled":true},"graphs":[]},"schema_type":null,"schema_type_options":null,"pillar_content":false,"robots_default":true,"robots_noindex":false,"robots_noarchive":false,"robots_nosnippet":false,"robots_nofollow":false,"robots_noimageindex":false,"robots_noodp":false,"robots_notranslate":false,"robots_max_snippet":null,"robots_max_videopreview":null,"robots_max_imagepreview":"large","priority":null,"frequency":null,"local_seo":null,"seo_analyzer_scan_date":"2026-01-21 10:28:19","breadcrumb_settings":null,"limit_modified_date":false,"reviewed_by":null,"ai":null,"created":"2021-02-28 19:13:42","updated":"2026-01-21 10:28:19","focus_keyword":null,"additional_keywords":null,"truseo_locale":null},"gt_translate_keys":[{"key":"link","format":"url"}],"_links":{"self":[{"href":"https:\/\/prohoster.info\/pl\/wp-json\/wp\/v2\/posts\/32353","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/prohoster.info\/pl\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/prohoster.info\/pl\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/prohoster.info\/pl\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/prohoster.info\/pl\/wp-json\/wp\/v2\/comments?post=32353"}],"version-history":[{"count":0,"href":"https:\/\/prohoster.info\/pl\/wp-json\/wp\/v2\/posts\/32353\/revisions"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/prohoster.info\/pl\/wp-json\/wp\/v2\/media\/24168"}],"wp:attachment":[{"href":"https:\/\/prohoster.info\/pl\/wp-json\/wp\/v2\/media?parent=32353"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/prohoster.info\/pl\/wp-json\/wp\/v2\/categories?post=32353"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/prohoster.info\/pl\/wp-json\/wp\/v2\/tags?post=32353"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}