SRE: Performans Təhlili. Go-da sadə veb serverdən istifadə edərək konfiqurasiya üsulu

Performans təhlili və tənzimləmə müştərilər üçün performans uyğunluğunu yoxlamaq üçün güclü vasitədir.

Performans təhlili tənzimləmə təcrübələrini sınaqdan keçirmək üçün elmi yanaşma tətbiq etməklə proqramda darboğazları yoxlamaq üçün istifadə edilə bilər. Bu məqalə, nümunə kimi Go veb serverindən istifadə edərək, performans təhlili və tənzimləmə üçün ümumi yanaşmanı müəyyən edir.

Go burada xüsusilə yaxşıdır, çünki onun profil alətləri var pprof standart kitabxanada.

SRE: Performans Təhlili. Go-da sadə veb serverdən istifadə edərək konfiqurasiya üsulu

strategiya

Struktur təhlilimiz üçün ümumi siyahı yaradaq. İntuisiyaya və ya təxminlərə əsaslanaraq dəyişiklik etmək əvəzinə qərar qəbul etmək üçün bəzi məlumatlardan istifadə etməyə çalışacağıq. Bunu etmək üçün bunu edəcəyik:

  • Biz optimallaşdırma sərhədlərini (tələblərini) müəyyən edirik;
  • Sistem üçün əməliyyat yükünü hesablayırıq;
  • Testi həyata keçiririk (məlumat yaradırıq);
  • Biz müşahidə edirik;
  • Təhlil edirik - bütün tələblər yerinə yetirilirmi?
  • Biz bunu elmi şəkildə qururuq, fərziyyə edirik;
  • Bu fərziyyəni yoxlamaq üçün təcrübə aparırıq.

SRE: Performans Təhlili. Go-da sadə veb serverdən istifadə edərək konfiqurasiya üsulu

Sadə HTTP Server Arxitekturası

Bu məqalə üçün Golang-da kiçik HTTP serverindən istifadə edəcəyik. Bu məqalədəki bütün kodları tapa bilərsiniz burada.

Təhlil edilən proqram hər sorğu üçün Postgresql-i sorğulayan HTTP serveridir. Bundan əlavə, proqram və sistem ölçülərini toplamaq və göstərmək üçün Prometheus, node_exporter və Grafana mövcuddur.

SRE: Performans Təhlili. Go-da sadə veb serverdən istifadə edərək konfiqurasiya üsulu

Sadələşdirmək üçün hesab edirik ki, üfüqi miqyaslama (və hesablamaların sadələşdirilməsi) üçün hər bir xidmət və verilənlər bazası birlikdə yerləşdirilir:

SRE: Performans Təhlili. Go-da sadə veb serverdən istifadə edərək konfiqurasiya üsulu

Məqsədlərin müəyyənləşdirilməsi

Bu mərhələdə məqsədə qərar veririk. Nəyi təhlil etməyə çalışırıq? Bitmə vaxtının nə vaxt olduğunu necə bilirik? Bu yazıda müştərilərimizin olduğunu və xidmətimizin saniyədə 10 sorğunu emal edəcəyini təsəvvür edəcəyik.

В Google SRE Kitabı Seçim və modelləşdirmə üsulları ətraflı müzakirə olunur. Gəlin eyni şeyi edək və modellər yaradaq:

  • Gecikmə: sorğuların 99%-i 60 ms-dən az müddətdə tamamlanmalıdır;
  • Xərc: Xidmət ağlabatan mümkün hesab etdiyimiz minimum məbləği istehlak etməlidir. Bunun üçün ötürmə qabiliyyətini maksimuma çatdırırıq;
  • Bacarıqların planlaşdırılması: Ümumi miqyaslama funksionallığı da daxil olmaqla, tətbiqin neçə nümunəsinin işə salınmalı olduğunu və ilkin yükləmə və təminat tələblərinə cavab vermək üçün neçə nümunənin lazım olacağını başa düşmək və sənədləşdirmək tələb olunur. artıqlıq n+1.

Gecikmə təhlilə əlavə olaraq optimallaşdırma tələb edə bilər, lakin ötürmə qabiliyyəti aydın şəkildə təhlil edilməlidir. SRE SLO prosesindən istifadə edərkən gecikmə tələbi məhsul sahibi tərəfindən təmsil olunan müştəri və ya biznesdən gəlir. Xidmətimiz isə bu öhdəliyi heç bir parametr olmadan əvvəldən yerinə yetirəcək!

Test mühitinin qurulması

Test mühitinin köməyi ilə sistemimizə ölçülmüş yük yerləşdirə biləcəyik. Təhlil üçün veb xidmətin performansı haqqında məlumatlar yaradılacaq.

Əməliyyat yükü

Bu mühit istifadə edir Vegeta dayandırılana qədər xüsusi HTTP sorğu dərəcəsi yaratmaq üçün:

$ make load-test LOAD_TEST_RATE=50
echo "POST http://localhost:8080" | vegeta attack -body tests/fixtures/age_no_match.json -rate=50 -duration=0 | tee results.bin | vegeta report

Müşahidə

Əməliyyat yükü icra zamanı tətbiq olunacaq. Tətbiq (sorğuların sayı, cavab gecikməsi) və əməliyyat sistemi (yaddaş, CPU, IOPS) ölçülərinə əlavə olaraq, harada problemlərin olduğunu və CPU vaxtının necə sərf edildiyini anlamaq üçün proqram profili işlənəcək.

Profilləşdirmə

Profilləşdirmə, proqram işləyərkən CPU vaxtının hara getdiyini görməyə imkan verən ölçmə növüdür. Bu, prosessorun hara və nə qədər vaxt sərf olunduğunu dəqiq müəyyən etməyə imkan verir:

SRE: Performans Təhlili. Go-da sadə veb serverdən istifadə edərək konfiqurasiya üsulu

Bu məlumatlar boş CPU vaxtı və yerinə yetirilən lazımsız iş haqqında məlumat əldə etmək üçün təhlil zamanı istifadə edilə bilər. Go (pprof) standart alətlər dəstindən istifadə edərək profillər yarada və onları alov qrafikləri kimi görüntüləyə bilər. Onların istifadəsi və quraşdırma təlimatı haqqında daha sonra məqalədə danışacağam.

İcra, müşahidə, təhlil.

Bir təcrübə edək. Tamaşadan razı qalana qədər ifa edəcəyik, müşahidə edəcəyik və təhlil edəcəyik. İlk müşahidələrin nəticələrini əldə etmək üçün onu tətbiq etmək üçün özbaşına aşağı yük dəyəri seçək. Hər bir sonrakı addımda yükü müəyyən bir dəyişikliklə seçilmiş müəyyən bir miqyas amili ilə artıracağıq. Hər bir yük testi tələblərin sayına uyğun olaraq həyata keçirilir: make load-test LOAD_TEST_RATE=X.

Saniyədə 50 sorğu

SRE: Performans Təhlili. Go-da sadə veb serverdən istifadə edərək konfiqurasiya üsulu

Üst iki qrafikə diqqət yetirin. Yuxarı sol tərəf proqramımızın saniyədə 50 sorğu emal etdiyini (düşünür) və yuxarı sağda hər sorğunun müddətini göstərir. Hər iki parametr bizim performans sərhədlərimiz daxilində olub-olmadığımıza baxmağa və təhlil etməyə kömək edir. Qrafikdə qırmızı xətt HTTP Sorğunun Gecikməsi 60ms-də SLO göstərir. Xətt göstərir ki, biz maksimum cavab müddətimizdən xeyli aşağıyıq.

Gəlin xərc tərəfinə baxaq:

Saniyədə 10000 sorğu / server başına 50 sorğu = 200 server + 1

Biz bu rəqəmi hələ də yaxşılaşdıra bilərik.

Saniyədə 500 sorğu

Yük saniyədə 500 sorğuya çatdıqda daha maraqlı şeylər baş verməyə başlayır:

SRE: Performans Təhlili. Go-da sadə veb serverdən istifadə edərək konfiqurasiya üsulu

Yenə yuxarı sol qrafikdə proqramın normal yükü qeyd etdiyini görə bilərsiniz. Əgər belə deyilsə, proqramın işlədiyi serverdə problem var. Cavab gecikmə qrafiki yuxarı sağda yerləşir və saniyədə 500 sorğunun 25-40 ms cavab gecikməsi ilə nəticələndiyini göstərir. 99-cu faiz hələ də yuxarıda seçilmiş 60 ms SLO-ya gözəl uyğun gəlir.

Xərc baxımından:

Saniyədə 10000 sorğu / server başına 500 sorğu = 20 server + 1

Hər şeyi hələ də yaxşılaşdırmaq olar.

Saniyədə 1000 sorğu

SRE: Performans Təhlili. Go-da sadə veb serverdən istifadə edərək konfiqurasiya üsulu

Əla buraxılış! Tətbiq göstərir ki, o, saniyədə 1000 sorğu emal edib, lakin gecikmə limiti SLO tərəfindən pozulub. Bunu yuxarı sağdakı qrafikdə p99 sətirində görmək olar. p100 xəttinin daha yüksək olmasına baxmayaraq, faktiki gecikmələr maksimum 60ms-dən yüksəkdir. Tətbiqin əslində nə etdiyini öyrənmək üçün profilləşdirməyə başlayaq.

Profilləşdirmə

Profil yaratmaq üçün yükü saniyədə 1000 sorğuya təyin edirik, sonra istifadə edirik pprof proqramın CPU vaxtını hara xərclədiyini öyrənmək üçün məlumatları ələ keçirmək. Bu, HTTP son nöqtəsini aktivləşdirməklə edilə bilər pprof, və sonra yük altında, curl istifadə edərək nəticələri qeyd edin:

$ curl http://localhost:8080/debug/pprof/profile?seconds=29 > cpu.1000_reqs_sec_no_optimizations.prof

Nəticələr bu şəkildə göstərilə bilər:

$ go tool pprof -http=:12345 cpu.1000_reqs_sec_no_optimizations.prof

SRE: Performans Təhlili. Go-da sadə veb serverdən istifadə edərək konfiqurasiya üsulu

Qrafik proqramın CPU vaxtını hara və nə qədər sərf etdiyini göstərir. Təsvirdən Brendan Gregg:

X oxu əlifba sırası ilə çeşidlənmiş yığın profilinin əhalisidir (bu vaxt deyil), Y oxu [yuxarıda] sıfırdan saymaqla yığının dərinliyini göstərir. Hər bir düzbucaqlı bir yığın çərçivəsidir. Çərçivə nə qədər geniş olsa, yığınlarda bir o qədər tez-tez olur. Üstündəkilər CPU-da işləyir, aşağıda olanlar isə uşaq elementlərdir. Rənglər adətən heç nə demək deyil, sadəcə olaraq çərçivələri fərqləndirmək üçün təsadüfi seçilir.

Təhlil - fərziyyə

Sazlama üçün biz boş CPU vaxtını tapmağa çalışacağıq. Biz faydasız xərclərin ən böyük mənbələrini axtaracağıq və onları aradan qaldıracağıq. Yaxşı, profilin tətbiqin prosessor vaxtını tam olaraq harada sərf etdiyini çox dəqiq şəkildə ortaya qoyduğunu nəzərə alsaq, bunu bir neçə dəfə etməli ola bilərsiniz, həmçinin tətbiqin mənbə kodunu dəyişdirməli, testləri təkrar keçirməli və performansın hədəfə yaxınlaşdığını görməli olacaqsınız.

Brendan Qreqin tövsiyələrinə əməl edərək, qrafiki yuxarıdan aşağı oxuyacağıq. Hər bir sətir yığın çərçivəsini (funksiya çağırışı) göstərir. Birinci sətir proqrama giriş nöqtəsidir, bütün digər zənglərin əsas hissəsidir (başqa sözlə, bütün digər zənglər öz yığınında olacaq). Növbəti sətir artıq fərqlidir:

SRE: Performans Təhlili. Go-da sadə veb serverdən istifadə edərək konfiqurasiya üsulu

Kursoru qrafikdəki funksiyanın adının üzərinə gətirsəniz, onun sazlama zamanı yığında olduğu ümumi vaxt göstəriləcək. HTTPServe funksiyası vaxtın 65%-də, digər iş vaxtı funksiyaları var idi runtime.mcall, mstart и gc, qalan vaxtını aldı. Əyləncəli fakt: ümumi vaxtın 5%-i DNS sorğularına sərf olunur:

SRE: Performans Təhlili. Go-da sadə veb serverdən istifadə edərək konfiqurasiya üsulu

Proqramın axtardığı ünvanlar Postgresql-ə aiddir. Basın FindByAge:

SRE: Performans Təhlili. Go-da sadə veb serverdən istifadə edərək konfiqurasiya üsulu

Maraqlıdır ki, proqram, prinsipcə, gecikmələri əlavə edən üç əsas mənbənin olduğunu göstərir: əlaqələri açmaq və bağlamaq, məlumat tələb etmək və verilənlər bazasına qoşulmaq. Qrafik göstərir ki, DNS sorğuları, bağlantıların açılması və bağlanması ümumi icra vaxtının təxminən 13%-ni təşkil edir.

Hipotez: Birləşmədən istifadə edərək əlaqələrin təkrar istifadəsi daha yüksək ötürmə qabiliyyətinə və daha az gecikməyə imkan verən tək HTTP sorğusunun vaxtını azaltmalıdır..

Tətbiqin qurulması - sınaq

Mənbə kodunu yeniləyirik, hər sorğu üçün Postgresql ilə əlaqəni aradan qaldırmağa çalışırıq. Birinci seçim istifadə etməkdir əlaqə hovuzu tətbiq səviyyəsində. Bu təcrübədə biz onu quraq getmək üçün sql sürücüsündən istifadə edərək əlaqənin birləşdirilməsi:

db, err := sql.Open("postgres", dbConnectionString)
db.SetMaxOpenConns(8)

if err != nil {
   return nil, err
}

İcra, müşahidə, təhlil

Testi saniyədə 1000 sorğu ilə yenidən başlatdıqdan sonra aydın olur ki, p99-un gecikmə səviyyələri 60 ms SLO ilə normal vəziyyətə qayıdır!

Xerci necedi?

Saniyədə 10000 sorğu / server başına 1000 sorğu = 10 server + 1

Gəlin bunu daha da yaxşı edək!

Saniyədə 2000 sorğu

SRE: Performans Təhlili. Go-da sadə veb serverdən istifadə edərək konfiqurasiya üsulu

Yükün ikiqat artması eyni şeyi göstərir, yuxarı sol qrafik proqramın saniyədə 2000 sorğu emal etməyi bacardığını göstərir, p100 60ms-dən aşağıdır, p99 SLO-nu təmin edir.

Xərc baxımından:

Saniyədə 10000 sorğu / server başına 2000 sorğu = 5 server + 1

Saniyədə 3000 sorğu

SRE: Performans Təhlili. Go-da sadə veb serverdən istifadə edərək konfiqurasiya üsulu

Burada proqram p3000 gecikmə müddəti 99 ms-dən az olan 60 sorğunu emal edə bilər. SLO pozulmur və xərc aşağıdakı kimi qəbul edilir:

Saniyədə 10000 3000 sorğu / server başına 4 1 sorğu = XNUMX server + XNUMX (müəllif tamamladı, təqribən. tərcüməçi)

Gəlin başqa bir təhlil mərhələsinə cəhd edək.

Təhlil - fərziyyə

Biz saniyədə 3000 sorğu ilə tətbiqin sazlanmasının nəticələrini toplayırıq və nümayiş etdiririk:

SRE: Performans Təhlili. Go-da sadə veb serverdən istifadə edərək konfiqurasiya üsulu

Hələ də vaxtın 6%-i əlaqələrin qurulmasına sərf olunur. Hovuzun qurulması performansı yaxşılaşdırdı, lakin siz hələ də proqramın verilənlər bazasına yeni bağlantılar yaratmaq üzərində işləməyə davam etdiyini görə bilərsiniz.

Hipotez: Bağlantılar, hovuzun olmasına baxmayaraq, hələ də atılır və təmizlənir, buna görə də proqram onları yenidən qurmalıdır. Gözləyən bağlantıların sayını hovuz ölçüsünə təyin etmək, tətbiqin əlaqə yaratmaq üçün sərf etdiyi vaxtı minimuma endirməklə gecikmə ilə kömək etməlidir..

Tətbiqin qurulması - sınaq

Quraşdırmağa çalışır MaxIdleConns hovuz ölçüsünə bərabərdir (həmçinin təsvir edilmişdir burada):

db, err := sql.Open("postgres", dbConnectionString)
db.SetMaxOpenConns(8)
db.SetMaxIdleConns(8)
if err != nil {
   return nil, err
}

İcra, müşahidə, təhlil

Saniyədə 3000 sorğu

SRE: Performans Təhlili. Go-da sadə veb serverdən istifadə edərək konfiqurasiya üsulu

p99 əhəmiyyətli dərəcədə az p60 ilə 100ms-dən azdır!

SRE: Performans Təhlili. Go-da sadə veb serverdən istifadə edərək konfiqurasiya üsulu

Alov qrafikini yoxlamaq əlaqənin artıq nəzərə çarpmadığını göstərir! Daha ətraflı yoxlayaq pg(*conn).query - burada əlaqənin qurulduğunu da hiss etmirik.

SRE: Performans Təhlili. Go-da sadə veb serverdən istifadə edərək konfiqurasiya üsulu

Nəticə

Performans təhlili müştəri gözləntilərinin və qeyri-funksional tələblərin yerinə yetirildiyini başa düşmək üçün çox vacibdir. Müşahidələri müştəri gözləntiləri ilə müqayisə edərək təhlil nəyin məqbul, nəyin olmadığını müəyyən etməyə kömək edə bilər. Go analizi sadə və əlçatan edən standart kitabxanaya daxil edilmiş güclü alətlər təqdim edir.

Mənbə: www.habr.com

Добавить комментарий