Ku kaydi dinaar tiro badan gudaha PostgreSQL

Sii wadida mawduuca duubista xogaha waaweyn ee ay soo kiciyeen maqaal hore oo ku saabsan qaybinta, tan waxaan ku eegi doonaa siyaabaha aad awooddo yaree cabbirka "jirka" ee kaydinta gudaha PostgreSQL, iyo saamaynta ay ku leeyihiin waxqabadka server-ka.

Waan ka hadli doonaa Dejinta TOAST iyo toosinta xogta. " Celcelis ahaan," hababkani ma badbaadin doonaan kheyraad aad u badan, laakiin iyada oo aan wax laga beddelin koodhka codsiga gabi ahaanba.

Ku kaydi dinaar tiro badan gudaha PostgreSQL
Si kastaba ha ahaatee, waayo-aragnimadayadu waxay u soo baxday inay noqoto mid wax soo saar leh oo arrintan ku saabsan, tan iyo kaydinta ku dhawaad ​​kasta oo la socodka dabeecadeeda inta badan lifaaq-kaliya marka la eego xogta la duubay. Oo haddii aad la yaabban tahay sida aad u bari karto kaydka kaydka in loo qoro saxanka beddelkeeda 200MB / s kala badh - fadlan bisad hoosteeda.

Siraha yar ee xogta weyn

By profile shaqada adeegeena, si joogto ah ayay isaga uga soo duulaan godadka xirmooyinka qoraalka.

Oo tan iyo adag VLSIXogtooda aan la socono waa badeeco ka kooban qaybo badan oo leh qaab dhismeed xog adag, ka dibna su'aalo waxqabadka ugu badan u noqda sida tan "Mug-mug badan" oo leh caqli-gal algorithmic adag. Markaa mugga tusaale kasta oo shakhsi ah oo codsi ah ama qorshaha fulinta ee ka soo baxa ee ku jira log-ka noo soo baxaa waxa uu noqonayaa “celcelis ahaan” aad u weyn.

Aan eegno qaab-dhismeedka mid ka mid ah jaantusyada aan ku qorno xogta "ceeriin" - taas oo ah, halkan waa qoraalka asalka ah ee gelitaanka log:

CREATE TABLE rawdata_orig(
  pack -- PK
    uuid NOT NULL
, recno -- PK
    smallint NOT NULL
, dt -- ключ секции
    date
, data -- самое главное
    text
, PRIMARY KEY(pack, recno)
);

Calaamadda caadiga ah (horta loo qaybiyay, dabcan, markaa tani waa qaab-dhismeedka qaybta), halkaasoo waxa ugu muhiimsani yahay qoraalka. Mararka qaarkood aad u cod badan.

Xusuusnow in cabbirka "jirka" ee hal rikoodh oo ku jira PG uusan hayn karin wax ka badan hal bog oo xog ah, laakiin cabbirka "macquul ah" waa arrin gebi ahaanba ka duwan. Si aad ugu qorto qiimaha mugga (varchar/text/bytea) goobta, isticmaal Tignoolajiyada TOAST:

PostgreSQL waxay isticmaashaa cabbir go'an oo bogag ah (sida caadiga ah 8 KB), mana ogola in tuples ay ku fidiyaan bogag badan. Sidaa darteed, suurtagal maaha in si toos ah loo kaydiyo qiyamka goobta aad u weyn. Si looga gudbo xaddidan, qiyamka weyn ee goobta ayaa la cufan iyo/ama loo kala qaybiyaa khadadka badan ee jirka. Tani waxay dhacdaa iyada oo aan la dareemin isticmaaluhu waxayna saameyn yar ku leedahay inta badan koodka serverka. Habkan waxa loo yaqaan TOAST...

Dhab ahaantii, miis kasta oo leh "awood weyn" beero, si toos ah miis lammaane ah oo leh "jeexid" ayaa la abuuray Rikoor kasta oo "weyn" oo ah qaybaha 2KB:

TOAST(
  chunk_id
    integer
, chunk_seq
    integer
, chunk_data
    bytea
, PRIMARY KEY(chunk_id, chunk_seq)
);

Taasi waa, haddii ay tahay inaan qorno xarig leh qiime "weyn". data, ka dibna duubista dhabta ah ayaa dhici doonta kaliya maaha miiska weyn iyo PK-giisa, laakiin sidoo kale TOAST iyo PK-ga.

Yaraynta saamaynta TOAST

Laakin inta badan diiwaanadayada wali sidaas uma weyna, waa in ay ahaataa 8KB Sideen lacag ugu kaydsan karaa tan?..

Tani waa halka ay sifadu ku timaado gargaarkeena STORAGE Tiirka miiska:

  • DHAMMAAN ogolaanaya isku-buufin iyo kaydinta kala duwan labadaba. Tani ikhtiyaarka caadiga ah badi noocyada xogta ee waafaqsan TOAST. Waxay marka hore isku daydaa inay samayso cadaadis, ka dibna waxay ku kaydisaa bannaanka miiska haddii safku weli aad u weyn yahay.
  • MAIN ogolaanaya isku-duubid laakiin ma kaydin gaar ah. (Xaqiiqdii, kaydin gaar ah ayaa wali loo samayn doonaa tiirarkaas, laakiin kaliya sida ugu dambeeya, marka aysan jirin si kale oo loo yareeyo xadhigga si ay ugu habboonaato bogga.)

Dhab ahaantii, tani waa dhab ahaan waxa aan ugu baahanahay qoraalka - cadaadi inta ugu badan ee suurtogalka ah, oo haddii aysan ku habboonayn, geli TOAST. Tan waxaa si toos ah loo samayn karaa duulista, iyadoo leh hal amar:

ALTER TABLE rawdata_orig ALTER COLUMN data SET STORAGE MAIN;

Sida loo qiimeeyo saamaynta

Maadaama socodka xogtu is beddesho maalin kasta, ma barbardhigi karno tirooyinka dhammaystiran, laakiin marka la eego shuruudaha qayb yar Waxaan ku qornay TOAST - si aad u wanaagsan. Laakiin halkan waxaa ka jira khatar - mugga "jidhka" ee diiwaanka kasta, "ballaaran" tusmuhu wuxuu noqonayaa, sababtoo ah waa inaan daboolnaa bogag badan oo xog ah.

Qaybta ka hor inta aan isbedelin:

heap  = 37GB (39%)
TOAST = 54GB (57%)
PK    =  4GB ( 4%)

Qaybta isbedel ka dib:

heap  = 37GB (67%)
TOAST = 16GB (29%)
PK    =  2GB ( 4%)

Dhab ahaantii, waxaan bilaabay wax u qorida TOAST 2 jeer in ka yar marar badan, kaas oo aan soo dejin kaliya diskka, laakiin sidoo kale CPU:

Ku kaydi dinaar tiro badan gudaha PostgreSQL
Ku kaydi dinaar tiro badan gudaha PostgreSQL
Waxaan ogaan doonaa in aan sidoo kale ku yareynay "akhrinta" saxanka, kaliya maahan "qorista" - sababtoo ah marka la gelinayo rikoodhka miiska, waa inaan sidoo kale "akhrinaa" qayb ka mid ah geedka index kasta si loo go'aamiyo booska mustaqbalka iyaga.

Yaa si fiican ugu noolaan kara PostgreSQL 11

Ka dib markii aan cusbooneysiinay PG11, waxaan go'aansanay inaan sii wadno "daawaynta" TOAST waxaana ogaanay in laga bilaabo noocaan cabbirku uu noqday mid diyaar u ah hagaajinta toast_tuple_target:

Koodhka habaynta TOAST kaliya wuu guba marka qiimaha safka lagu kaydinayo shaxda uu ka weyn yahay TOAST_TUPLE_THRESHOLD bytes (badanaa 2 KB). Koodhka TOAST wuxuu cadaadi doonaa oo/ama ka saari doonaa qiyamka goobta miiska ilaa qiimaha safku uu ka noqonayo wax ka yar TOAST_TUPLE_TARGET bytes (qiimaha kala duwan, sidoo kale badanaa 2 KB) ama cabbirka lama yarayn karo.

Waxaan go'aansanay in xogta aan sida caadiga ah hayno ay tahay "mid aad u gaaban" ama "aad u dheer", sidaa darteed waxaan go'aansanay inaan nafteena ku koobno ​​qiimaha ugu yar ee suurtogalka ah:

ALTER TABLE rawplan_orig SET (toast_tuple_target = 128);

Aynu aragno sida goobaha cusub ay u saameeyeen rarista diskka ka dib dib-u-habaynta:

Ku kaydi dinaar tiro badan gudaha PostgreSQL
Ma xuma! Celcelis ahaan safka saxanka ayaa hoos u dhacay qiyaastii 1.5 jeer, iyo diskka "mashquul" waa boqolkiiba 20! Laakiin waxaa laga yaabaa in tani ay si uun u saamaysay CPU?

Ku kaydi dinaar tiro badan gudaha PostgreSQL
Ugu yaraan waxba kamay sii xumaan. In kasta oo, way adag tahay in la xukumo haddii xitaa mugga noocan oo kale ah aysan weli kor u qaadi karin celceliska culeyska CPU sare 5%.

Beddelidda meelaha ereyada, wadarta... isbedelay!

Sidaad ogtahay, dinaarku wuxuu badbaadiyaa ruble, iyo qiyaasta kaydintayadu waxay ku saabsan tahay 10TB/bishii xitaa wax yar oo hagaajin ah ayaa ku siin kara faa'iido wanaagsan. Sidaa darteed, waxaan fiiro gaar ah u siinnay qaabka jireed ee xogtayada - sida saxda ah Garoomada "isku-duuban" ee ku dhex jira diiwaanka mid kasta oo ka mid ah miisaska.

Sababtoo ah toosinta xogta Tani waa toos hore waxay saamaysaa mugga natiijada:

Nashqado badan ayaa bixiya isku dheelitirka xogta ee xuduudaha erayada mashiinka. Tusaale ahaan, nidaamka x32 ee 86-bit ah, isugeynta (nooca isku-dhafka ah, 4-bytes) ayaa la waafajin doonaa xudduud kelmad 4-byte ah, sidoo kale waxay labanlaabmi doonaan tirooyinka sabbeynaya ee saxda ah (laba jeer saxan sabbeynaya, 8 bytes). Iyo nidaamka 64-bit, qiimaha labajibbaaran ayaa la waafajin doonaa xuduudaha erayada 8-byte. Tani waa sabab kale oo la'aanta.

Isku toosinta awgeed, cabbirka safka miisku wuxuu ku xidhan yahay siday u kala horreeyaan beeruhu. Caadi ahaan saameyntani maaha mid la dareemo, laakiin xaaladaha qaarkood waxay keeni kartaa koror weyn oo cabbir ah. Tusaale ahaan, haddii aad isku darto char(1) iyo beero isku dhaf ah, waxaa caadi ahaan jiri doona 3 bytes oo dhexda ku dhumi doona.

Aan ku bilowno moodooyinka synthetic:

SELECT pg_column_size(ROW(
  '0000-0000-0000-0000-0000-0000-0000-0000'::uuid
, 0::smallint
, '2019-01-01'::date
));
-- 48 байт

SELECT pg_column_size(ROW(
  '2019-01-01'::date
, '0000-0000-0000-0000-0000-0000-0000-0000'::uuid
, 0::smallint
));
-- 46 байт

Xagee bay ka yimaaddeen dhowr bayt oo dheeraad ah kiiskii ugu horreeyay? Way fududahay - 2-byte yar oo ku toosan xadka 4-byte ka hor beerta soo socota, iyo marka ay tahay midda ugu dambeysa, ma jiraan wax loo baahan yahay in la isku hagaajiyo.

Aragti ahaan, wax walbaa way fiican yihiin oo waxaad dib u habeyn kartaa beeraha sidaad rabto. Aynu ku hubino xogta dhabta ah inagoo tusaale u ah mid ka mid ah miisaska, qaybta maalinlaha ah ee ka kooban 10-15GB.

Qaab dhismeedka hore:

CREATE TABLE public.plan_20190220
(
-- Унаследована from table plan:  pack uuid NOT NULL,
-- Унаследована from table plan:  recno smallint NOT NULL,
-- Унаследована from table plan:  host uuid,
-- Унаследована from table plan:  ts timestamp with time zone,
-- Унаследована from table plan:  exectime numeric(32,3),
-- Унаследована from table plan:  duration numeric(32,3),
-- Унаследована from table plan:  bufint bigint,
-- Унаследована from table plan:  bufmem bigint,
-- Унаследована from table plan:  bufdsk bigint,
-- Унаследована from table plan:  apn uuid,
-- Унаследована from table plan:  ptr uuid,
-- Унаследована from table plan:  dt date,
  CONSTRAINT plan_20190220_pkey PRIMARY KEY (pack, recno),
  CONSTRAINT chck_ptr CHECK (ptr IS NOT NULL),
  CONSTRAINT plan_20190220_dt_check CHECK (dt = '2019-02-20'::date)
)
INHERITS (public.plan)

Qaybta ka dib markii la beddelo nidaamka column - sax ah beero isku mid ah, kaliya kala nidaam duwan:

CREATE TABLE public.plan_20190221
(
-- Унаследована from table plan:  dt date NOT NULL,
-- Унаследована from table plan:  ts timestamp with time zone,
-- Унаследована from table plan:  pack uuid NOT NULL,
-- Унаследована from table plan:  recno smallint NOT NULL,
-- Унаследована from table plan:  host uuid,
-- Унаследована from table plan:  apn uuid,
-- Унаследована from table plan:  ptr uuid,
-- Унаследована from table plan:  bufint bigint,
-- Унаследована from table plan:  bufmem bigint,
-- Унаследована from table plan:  bufdsk bigint,
-- Унаследована from table plan:  exectime numeric(32,3),
-- Унаследована from table plan:  duration numeric(32,3),
  CONSTRAINT plan_20190221_pkey PRIMARY KEY (pack, recno),
  CONSTRAINT chck_ptr CHECK (ptr IS NOT NULL),
  CONSTRAINT plan_20190221_dt_check CHECK (dt = '2019-02-21'::date)
)
INHERITS (public.plan)

Tirada guud ee qaybta waxaa lagu go'aamiyaa tirada "xaqiiqda" waxayna ku xiran tahay kaliya hababka dibadda, markaa aynu kala qaybinno xajmiga tuubada (pg_relation_size) tirada diiwaannada ku jira - taas oo ah, waxaan helnaa celceliska cabbirka rikoorka dhabta ah ee kaydsan:

Ku kaydi dinaar tiro badan gudaha PostgreSQL
Laga jaray 6% mugga, Wayn!

Laakiin wax walba, dabcan, ma aha mid aad u qurux badan - ka dib oo dhan, tusmooyinka ma beddeli karno sida ay u kala horreeyaan, oo sidaas darteed "guud ahaan" (pg_total_relation_size) ...

Ku kaydi dinaar tiro badan gudaha PostgreSQL
... weli halkan sidoo kale badbaadiyay 1.5%iyada oo aan la beddelin hal xariiq oo kood ah. Haa, haa!

Ku kaydi dinaar tiro badan gudaha PostgreSQL

Waxaan ogsoonahay in doorashada kor ku xusan ee habaynta beeraha aysan ahayn xaqiiqda ah inay tahay tan ugu fiican. Sababtoo ah ma rabto inaad "jeexdo" qaybo ka mid ah beeraha sababo qurxoon dartood - tusaale ahaan, lamaane (pack, recno), kaas oo ah PK miiskaan.

Guud ahaan, go'aaminta habaynta "ugu yar" ee beeruhu waa hawl "xoog caasi ah" oo fudud. Sidaa darteed, waxaad xitaa ka heli kartaa natiijooyin ka wanaagsan xogtaada - isku day!

Source: www.habr.com

Add a comment