Bikaranîna Zabbix ji bo Çavdêriya Daneyên Servera MS SQL

Pêşniyar

Gelek caran hewce ye ku di wextê rast de derheqê pirsgirêkên girêdayî databasê (danûstandin) de ji rêveberê re rapor bikin.

Ev gotar dê rave bike ka çi hewce dike ku li Zabbix were mîheng kirin da ku databasek MS SQL Server çavdêrî bike.

Ji kerema xwe not bikin ku hûrguliyên li ser çawaniya mîhengkirinê nayên dayîn, lêbelê, formula û pêşniyarên gelemperî, û her weha ravekek berfireh a lêzêdekirina hêmanên daneya xwerû bi navgîniya prosedurên hilanîn de dê di vê gotarê de bêne dayîn.
Di heman demê de, tenê hejmarên performansa sereke dê li vir werin nîqaş kirin.

biryar

Pêşîn, ez ê hemî wan hejmarên performansê (bi hêmanên daneya Zabbix) ku ji me re hewce ne diyar bikim:

  1. Logical Disk
    1. Avg Disc sec / Xwendin
      Ji bo xwendina daneyên ji dîskê dema navînî, ku di çirkeyan de tê diyar kirin, nîşan dide. Nirxa navînî ya dijî performansa navîn. Divê saniyeya dîskê/Xwendin ji 10 milîsaniyeyan derbas nebe. Nirxa herî zêde ya pîvana performansê Avg. Divê saniyeya dîskê/xwendin ji 50 milî çirkeyan derbas nebe.

      Zabbix: perf_counter[LogicalDisk(_Total)Avg. Disk sec / Read], û di heman demê de girîng e ku meriv dîska xwestinê bişopîne, mînakî bi vî rengî: perf_counter[LogicalDisk(C:)Avg. Disk sec/Xwendin]

      Nimûneyên tehlikê:
      {NODE_NAME:perf_counter[LogicalDisk(_Total)Avg. Disk sec/Read].last()}>0.005, asta-bilind
      и
      {NODE_NAME:perf_counter[LogicalDisk(_Total)Avg. Disk sec/Read].last()}>0.0025, asta-navîn

    2. Avg Disc sec/Write
      Ji bo nivîsandina daneyan li ser dîskê dema navînî, ku bi çirkeyan tê diyar kirin, nîşan dide. Nirxa navîn a dijî performansa navîn. Divê saniyeya dîskê/Nivîs ji 10 milî çirkeyan derbas nebe. Nirxa herî zêde ya jimareya performansê Avg. Disk sec/Write divê ji 50 milîsaniyeyan derbas nebe.

      Zabbix: perf_counter[LogicalDisk(_Total)Avg. Disk sec/Write], û her weha girîng e ku meriv dîska xwestinê bişopîne, mînakî bi vî rengî: perf_counter[LogicalDisk(C:)Avg. Disk saniye/Nivîs]

      Nimûneyên tehlikê:
      {NODE_NAME:perf_counter[LogicalDisk(_Total)Avg. Disk sec/Write].last()}>0.005, asta-bilind
      и
      {NODE_NAME:perf_counter[LogicalDisk(_Total)Avg. Disk sec/Write].last()}>0.0025, asta-navîn

    3. Dirêjahiya rêza dîskê ya navîn

      Dirêjahiya rêza navîn a daxwazên li ser dîskê. Hejmara daxwazên dîskê yên li benda pêvajoyê di nav navberek demkî ya diyarkirî de nîşan dide. Ji bo yek dîskek ji 2-an bêtir rêzek normal tê hesibandin. Ger di dorê de ji du daxwaziyan zêdetir hebin, wê hingê dibe ku dîsk zêde were barkirin û nikaribe daxwazên hatinê bişopîne. Hûn dikarin bi rastî fêr bibin ka kîjan operasiyonên dîsk bi karanîna jimarvanên Avg nikare bi rê ve bibe. Dirêjahiya rêza xwendinê ya dîskê û navîn. Dirêjahiya Dora Disk Wright (doza daxwazên nivîsandinê).
      Nirxa navîn Dirêjahiya rêza dîskê nayê pîvandin, lê bi zagona Little ji teoriya matematîkî ya rêzê tê hesibandin. Li gorî vê qanûnê, hejmara daxwazên ku li benda pêvajoyê ne, bi navînî, bi rêjeya daxwaznameyên ku bi dema pêvajoykirina daxwazê ​​ve têne zêdekirin e. Ewan. di doza me de Avg. Dirêjahiya Dora Dîskê = (Veguhestina Dîskê/çirk) * (Navenda saniyeya dîskê/Transfer).

      Avg. Dirêjahiya rêza dîskê wekî yek ji jimarvanên sereke ji bo destnîşankirina barkirina li ser binepergala dîskê tê dayîn, lêbelê, ji bo ku wê bi têra xwe binirxînin, pêdivî ye ku bi awakî rast strukturên laşî yên pergala hilanînê were temsîl kirin. Mînakî, ji bo dîskêşek yekane nirxek ji 2-yê mezintir tê hesibandin krîtîk, û heke dîsk li ser rêzek RAID-ê ya 4 dîskan pêk tê, wê hingê divê hûn xeman bikin ger nirx ji 4*2=8 mezintir be.

      Zabbix: perf_counter[LogicalDisk(_Total)Avg. Dirêjahiya rêza dîskê], û di heman demê de girîng e ku meriv dîska xwestinê bişopîne, mînakî bi vî rengî: perf_counter[LogicalDisk(C:)Avg. Dirêjahiya rêza dîskê]

  2. Bîr
    1. Rûpel/sek
      Hejmara rûpelên ku SQL Server ji dîskê xwendiye an ji dîskê re nivîsandiye destnîşan dike da ku gihîştina rûpelên bîranînê yên ku di dema gihîştinê de li RAM-ê nehatine barkirin çareser bike. Ev nirx berhevoka Ketina Rûpelan/saniye û Rûpelên Derketina/saniyeyê ye, û ji bo gihîştina pelên daneya serîlêdanê jî rûpelkirin (rûpelandin/veguheztin) cacheya pergalê jî dihesibîne. Wekî din, ev rûpelkirina pelên ne-cached ên ku rasterast di nav bîranînê de têne nexşandin jî vedihewîne. Heke hûn bi karanîna bîranîna zêde û rûpela zêde ya têkildar re rû bi rû ne, ev hejmarê sereke ye ku divê were şopandin. Ev jimarvan mîqdara guheztinê diyar dike û nirxa wê ya normal (ne lûtkeyê) divê nêzî sifirê be. Zêdebûna guheztinê hewcedariya zêdekirina RAM an kêmkirina hejmara bernameyên serîlêdanê yên ku li ser serverê dixebitin destnîşan dike.

      Zabbix: perf_counter[MemoryPages/sec] Nimûneya tîrêjê:
      {NODE_NAME:perf_counter[MemoryPages/sec].min(5m)}>1000, asta-agahiya

    2. Çewtiyên Rûpelê/sek

      Ev nirxa dijberê xeletiya rûpelê ye. Xeletiyek rûpelê çêdibe dema ku pêvajoyek rûpelek bîranîna virtual ku ne di koma xebata RAM-ê de ye referans dike. Ev hejmar hem wan xeletiyên rûpelê yên ku hewceyê gihîştina dîskê hewce dike, hem jî yên ku ji ber ku rûpel li derveyî saziya xebatê ya RAM-ê ye têne hesibandin. Pir pêvajovan dikarin xeletiyên rûpela Tîpa 2 bêyî derengiyek zêde bi rê ve bibin. Lêbelê, birêvebirina xeletiyên rûpela celeb 1 ku hewceyê gihîştina dîskê hewce dike dikare bibe sedema derengiyên girîng.

      Zabbix: perf_counter[XerabiyênRûpela Bîra/Sec] Nimûneya tîrêjê:
      {NODE_NAME:perf_counter[MemoryPage Faults/sec].min(5m)}>1000, asta-agahiyê

    3. Bîtên berdest

      Ji bo ku pêvajoyên cihêreng bixebitin, mêjera bîranîna ku di byte de peyda dibe dişopîne. Xwendinên kêm bîranîna kêm nîşan dide. Çareserî zêdekirina bîrê ye. Divê ev metre di pir rewşan de bi berdewamî li ser 5000 kV be.
      Aqil e ku meriv berdêla ji bo Mbytên Berdest bi destan ji ber sedemên jêrîn destnîşan bike:

      •50% bîra belaş berdest = Baş e
      •25% hafizeya berdest = Pêdiviya baldariyê
      •10% belaş = Pirsgirêkên gengaz
      •Kêmtir ji 5% bîra berdest = Ji bo lezê krîtîk e, divê hûn mudaxele bikin.
      Zabbix: perf_counter[Bytên MemoryAvailable]

  3. Prosesor (Tevahî): % Dema Pêvajoyê
    Ev jimarvan rêjeya dema ku pêvajo ji bo mijarên ne-bêkar bi pêkanîna operasyonan mijûl bû nîşan dide. Ev nirx dikare wekî rêjeya dema ku ji bo karê kêrhatî derbas dibe were hesibandin. Her pêvajoyek dikare li ser mijarek bêkar were veqetandin, ku çerxên pêvajoyê yên nehilber ên ku ji hêla mijarên din ve nehatine bikar anîn vedixwe. Ev jimare bi lûtkeyên kurt ên ku dikarin ji sedî 100 bigihîjin ve tê destnîşan kirin. Lêbelê, heke heyamên dirêjkirî hebin ku karanîna pêvajoyê ji sedî 80 ji jortir e, wê hingê dê pergal bi karanîna bêtir pêvajoyan bikêrtir be.

    Zabbix: perf_counter[Processor(_Total)% Processor Time], li vir dikare ji hêla bingehîn ve jî were xuyang kirin
    Nimûneya tîrêjê:
    {NODE_NAME:perf_counter[Processor(_Total)% Processor Time].min(5m)}>80, asta-agahiya

  4. Navbera Torê (*): % Bytes Tevahiya/sek
    Hejmara giştî ya baytên ku di her çirkeyê de di hemî navbeynkaran de têne şandin û wergirtin. Ev firehiya navberê ye (bi byte). Pêdivî ye ku meriv nirxa vê hejmarê bi firehiya herî zêde ya qerta torê re bide berhev. Bi gelemperî, pêdivî ye ku ev hejmar ji %50-ê zêdetir karanîna bandê ya adapterê torê nîşan bide.
    Zabbix: perf_counter[Navbera Torê(*)Byt şandin/çirk]
  5. MS SQL Server: Rêbazên Gihîştinê
    Tişta Rêbazên Gihîştinê di SQL Server de jimarvan peyda dike ku ji bo şopandina gihîştina daneyên mantiqî di nav databasekê de bibe alîkar. Gihîştina laşî ya rûpelên databasê yên li ser dîskê bi karanîna jimareyên rêveberê tampon tê kontrol kirin. Şopandina awayên gihîştina daneyê di databasê de dibe alîkar ku hûn diyar bikin ka performansa pirsê dikare bi lê zêdekirin an guhartina nîşanan, lê zêdekirin an veguheztina dabeşan, lê zêdekirina pelan an komên pelan, defragmentkirina indexan, an guheztina nivîsa pirsê çêtir bibe. Digel vê yekê, hûn dikarin jimarvanên objektê yên Rêbazên Access-ê bikar bînin da ku mezinahiya daneyan, navnîşan, û cîhê belaş di databasa xwe de, çavdêrîkirina kapasîteya û perçebûnê ji bo her mînakek serverê bişopînin. Parçebûna îndeksê ya zêde dikare performansê bi girîngî kêm bike.

    1. Parçebûna Rûpel / sec
      Hejmara parçebûna rûpelan di çirkeyê de ji ber zêdebûna rûpela navnîşê pêk tê. Ji bo vê metrîkê nirxek bilind tê vê wateyê ku dema ku li ser daneyan operasyonên têxin û nûvekirinê pêk tîne, SQL Server divê hejmareke mezin operasyonên çavkanî-dijwar pêk bîne da ku rûpelan parçe bike û beşek ji rûpelek heyî biguhezîne cîhek nû. Dema ku dibe bila bibe divê ji operasyonên bi vî rengî dûr bikevin. Hûn dikarin bi du awayan hewl bidin ku pirsgirêkê çareser bikin:
      - ji bo stûnên xwe-zêdekirina îndekek komkirî biafirînin. Di vê rewşê de, tomarên nû dê di hundurê rûpelên ku berê ji hêla daneyê ve hatine dagir kirin neyên danîn, lê dê bi rêzê rûpelên nû dagir bikin;
      - bi zêdekirina nirxa parametreya Fillfactor-ê ji nû ve saz bikin. Ev vebijark dihêle hûn cîhê belaş di rûpelên navnîşan de veqetînin ku dê werin bikar anîn da ku daneyên nû bicîh bikin, bêyî ku hewcedariya operasyonên dabeşkirina rûpelan hebe.
      Zabbix: perf_counter["MSSQL$INSTANCE_NAME:Access MethodsPage Splits/sec",30] Nimûneya tîrêjê: {NODE_NAME:perf_counter["MSSQL$INSTANCE_NAME:Access MethodsPage Splits/sec",30].last()}>{NODE_NAME:perf_counter["MSSQL$INSTANCE_NAME:SQL StatisticsBatch Requests/last",(30]] /5, asta-agahdarî
    2. Scans Full / sec
      Hejmara bêsînor skanên tam di çirkeyê de. Di van operasyonan de şaneyên tabloya sereke û şaneyên tam îndeks hene. Zêdebûnek domdar a vê nîşankerê dibe ku hilweşîna pergalê nîşan bide (nebûna pêvekên pêwîst, perçebûna wan a giran, têkçûna optîmîzatorê di karanîna pêvekên heyî de, hebûna nîşaneyên neyên bikar anîn). Lêbelê, hêjayî gotinê ye ku şopandina tevahî di tabloyên piçûk de her gav ne xirab e, ji ber ku heke hûn bikarin tevahiya tabloyê di RAM-ê de bi cîh bikin, wê hingê şanek bêkêmasî dê zûtir be. Lê di pir rewşan de, zêdebûnek bi îstîqrar di vê hejmarê de dê hilweşîna pergalê nîşan bide. Hemî ev tenê ji bo pergalên OLTP derbasdar e. Di pergalên OLAP-ê de, şopandinên tijî yên domdar normal in.
      Zabbix: perf_counter["MSSQL$INSTANCE_NAME:Access MethodsFull Scans/sec",30]

  6. MS SQL Server: Rêvebirê Buffer
    Tişta Rêvebirê Buffer jimarvanan peyda dike ku ji we re dibe alîkar ku hûn çavdêriyê bikin ka SQL Server çawa çavkaniyên jêrîn bikar tîne:
    - bîra ji bo hilanîna rûpelên daneyê;
    - jimarkerên ku I/O ya laşî dişopînin wekî SQL Server rûpelên databasê dixwîne û dinivîse;
    - Berfirehkirina hewza tamponê ji bo berfirehkirina cacheya tamponê bi karanîna bîranîna bilez a nehilber, wek ajokarên dewleta zexm (SSD);
    - Şopandina bîr û hejmarên ku ji hêla SQL Server ve têne bikar anîn ji bo bidestxistina agahdariya jêrîn dibe alîkar;
    - gelo tengahiyên ku ji ber kêmbûna bîranîna laşî ve têne çêkirin hene. Ger daneyên ku pir caran têne gihîştin nikaribin di cache de werin hilanîn, SQL Server neçar dibe ku wê ji dîskê bixwîne;
    Ma gengaz e ku meriv performansa pirsê bi zêdekirina mîqdara bîranînê an veqetandina bîra zêde li daneya cache an hilanîna strukturên SQL Server-a hundurîn çêtir bike?
    - SQL Server çend caran daneyên ji dîskê dixwîne. Li gorî operasyonên din ên wekî gihîştina bîranînê, I/O ya laşî dirêjtir digire ku were temam kirin. Kêmkirina I/O dikare performansa pirsê baştir bike.

    1. Buffer Cache li radyoyê xist
      Nîşan dide ka çiqas daneya SQL Server dikare bikeve nav tampona cache. Ev nirx çiqas bilindtir be, ew çêtir e, ji ber ku Ji bo ku SQL Server bi bandor bigihîje rûpelên daneyê, divê ew di tamponek cache de bin, û pêdivî ye ku operasyonên têketin/derketina laşî (I/O) tune bin. Ger hûn di nirxa navînî ya vê hejmarê de kêmbûnek domdar dibînin, divê hûn RAM zêde bikin. Divê ev nîşanker her gav ji bo pergalên OLTP ji% 90 û ji bo pergalên OLAP ji% 50 jor be.
      Zabbix: perf_counter["MSSQL$INSTANCE_NAME:Buffer ManagerBuffer Rêjeya lêdana cache",30] Nimûneyên tehlikê: {NODE_NAME:perf_counter["MSSQL$INSTANCE_NAME:Buffer ManagerBuffer rêjeya lêdana cache",30].last()}<70, ast-bilind
      и
      {NODE_NAME:perf_counter["MSSQL$INSTANCE_NAME:Buffer ManagerBuffer ratio cache",30].last()}<80, asta-navîn
    2. Hêviya jiyanê ya rûpelê
      Nîşan dide ka dê rûpel di rewşa xweya heyî de çiqas dirêj di bîranînê de bimîne. Ger nirx her ku diçe dakeve, ev tê vê wateyê ku pergal hewza tamponê xirab dike. Ji ber vê yekê, performansa bîra potansiyel dikare bibe sedema pirsgirêkan ku di encamê de performansa nebaş be. Hêjayî gotinê ye ku li jêr nîşanek gerdûnî tune ku meriv bi zelalî dadbar bike ku pergal hewza tamponê xirab dike (nîşana 300 saniyeyan ji MS SQL Server 2012-an vir ve kevn e).
      Zabbix: perf_counter["MSSQL$INSTANCE_NAME:Buffer ManagerPage bendewariya jiyanê",30] Nimûneya tîrêjê: {NODE_NAME:perf_counter["MSSQL$INSTANCE_NAME:Buffer ManagerPage bendewariya jiyanê",30].last()}<5, asta-agahiya

  7. MS SQL Server: Statîstîkên Giştî
    Tişta Statîstîka Giştî ya di SQL Server de jimarvan peyda dike ku dihêle hûn çalakiya giştiya serverê bişopînin, wek mînak hejmara girêdanên hevdem û hejmara bikarhêneran di çirkeyê de ku bi komputera ku mînaka SQL Server-ê dixebitîne ve girêdidin an jê qut dibin. Van metrîkan di pergalên pêvajoyek danûstendina serhêl a mezin (OLTP) de bikêr in ku hejmareke mezin ji xerîdar bi domdarî ji mînakek SQL Server ve girêdayî ne û jê qut dibin.

    1. Pêvajo hate astengkirin
      Hejmara pêvajoyên ku niha hatine asteng kirin.
      Zabbix: perf_counter["MSSQL$INSTANCE_NAME:General StatisticsProcesses blocked",30] Nimûneya tîrêjê: ({NODE_NAME:perf_counter["MSSQL$INSTANCE_NAME:General StatisticsProcesses blocked",30].min(2m,0)}>=0)
      û ({NODE_NAME:perf_counter["MSSQL$INSTANCE_NAME:General StatisticsProcesses blocked",30].time(0)}>=50000)
      û ({NODE_NAME:perf_counter["MSSQL$INSTANCE_NAME:General StatisticsProcesses blocked",30].time(0)}<=230000), asta agahîyê (li vir ji 05:00 heta 23:00 sînordarkirina sînyalan heye)
    2. Têkiliyên Bikarhêner
      Hejmara bikarhênerên ku niha bi SQL Server ve girêdayî ne.
      Zabbix: perf_counter["MSSQL$INSTANCE_NAME:General StatisticsUser Connections",30]

  8. MS SQL Server: Locks
    Tişta Locks di Microsoft SQL Server de agahdarî li ser kilîtkirinên SQL Server-ê yên ku ji bo celebên çavkaniya kesane hatine wergirtin peyda dike. Girtî li ser çavkaniyên SQL Server-ê têne derxistin, wekî rêzikên ku ji hêla danûstendinê ve têne xwendin an jî têne guheztin, da ku pêşî li karanîna gelek danûstendinan di heman demê de bigire. Mînakî, heke kilîtek taybetî (X) ji hêla danûstendinek li ser rêzek di tabloyê de were bidestxistin, heya ku kilît neyê berdan ti danûstendinek din nikare wê rêzê biguhezîne. Kêmkirina karanîna qefleyan hevdengiyê zêde dike, ku dikare performansa giştî baştir bike. Gelek mînakên objeya Locks di heman demê de têne şopandin, ku her yek dê li ser celebek çavkaniyek cihê qeflek temsîl bike.

    1. Dema Rawestandina Navîn (ms)
      Demjimêra bendewariyê ya navîn (bi milî çirkeyan) ji bo hemî daxwazên qefilandinê yên ku li bendê bûn. Ev jimarvan destnîşan dike ka çiqas, bi navînî, pêvajoyên bikarhêner divê di rêzê de li bendê bin da ku li ser çavkaniyek kilît bi dest bixin. Nirxa destûr ya herî zêde ya vê hejmarê bi tevahî bi peywira we ve girêdayî ye ku meriv nirxek navînî ji bo hemî serlêdanan diyar bike. Ger ev hejmar pir zêde be, ew dikare pirsgirêkên girtina databasa we destnîşan bike.
      Zabbix: perf_counter["MSSQL$INSTANCE_NAME:Locks(_Total)Navanî Dema Rawestandinê (ms)",30] Nimûneya tîrêjê: {NODE_NAME:perf_counter["MSSQL$INSTANCE_NAME:Locks(_Total)Average Waita Wait (ms)",30].last()}>=500, asta-agahiya
    2. Demjimêra Rawestandinê Girt bike (ms)
      Tevahiya dema bendewariyê ya qefilandinê (bi milî çirkeyan) li ser saniya paşîn.
      Zabbix: perf_counter["MSSQL$INSTANCE_NAME:Locks(_Total)Dema bendê kilîtkirinê (ms)",30]
    3. Girtî Disekine/saniye
      Di saniyeya paşîn de çend caran ku mijarek ji ber daxwazek qefilandinê li bendê ma.
      Zabbix: perf_counter["MSSQL$INSTANCE_NAME:Locks(_Total)Lock Waits/sec",30]
    4. Demên Girtî / saniye
      Hejmara carên ku kilît bi dorhêlê nayê bidestxistin. Nirxa parametreya veavakirina jimarvana gerîdeya SQL Server çend caran diyar dike ku mijarek dikare bizivire berî ku wext biqede û xêz neçalak bibe.
      Zabbix: perf_counter["MSSQL$INSTANCE_NAME:Locks(_Total)Demên Girêdanê/sec",30] Nimûneya tîrêjê: {NODE_NAME:perf_counter["MSSQL$INSTANCE_NAME:Locks(_Total)Locks(_Total)Dema Girtkirinê/sec",30].last()}>1000, asta-agahiyê
    5. Daxwazên Lock / sec
      Hejmara daxwaznameyên serê çirkeyê yên cureya kilîtkirî ya diyarkirî.
      Zabbix: perf_counter["MSSQL$INSTANCE_NAME:Locks(_Total) Daxwazên Girtkirinê/sec",30] Nimûneya tîrêjê: {NODE_NAME:perf_counter["MSSQL$INSTANCE_NAME:Locks(_Total)Daxwazên Girêdanê/sec",30].last()}>500000, agahdariya astê
    6. Lock Hejmara Deadlocks / sec
      Hejmara daxwazên qefilandinê di çirkeyê de ku di encamê de xitimandinek çêdibe. Hebûna xitimandinê pirsnameyên nebaş hatine çêkirin destnîşan dike ku çavkaniyên hevpar asteng dikin.
      Zabbix: perf_counter["MSSQL$INSTANCE_NAME:Hejmara Deadlocks/sec",30] Nimûneya tîrêjê: {NODE_NAME:perf_counter["MSSQL$INSTANCE_NAME:Locks(_Total)Hejmarên Deadlocks/sec",30].last()}>1, ast-bilind

  9. MS SQL Server: Rêvebirê Bîrê
    Tişta Rêvebirê Bîrê di Microsoft SQL Server de jimarvan peyda dike da ku karanîna bîranîna li seranserê serverê bişopîne. Çavdêriya karanîna bîranînê ya tevahiya serverê ji bo nirxandina çalakiya bikarhêner û karanîna çavkaniyê dikare bibe alîkar ku astengiyên performansê nas bikin. Çavdêriya bîranînê ya ku ji hêla mînakek SQL Server ve hatî bikar anîn dikare destnîşan bike:
    - gelo kêmasiyên bîranîna laşî ya têr hene ku daneyên ku pir caran têne bikar anîn di cache de hilînin. Ger bîra têr nebe, divê SQL Server daneyan ji dîskê bigire;
    - Ger bîranîn were zêdekirin an hêjmara bîranîna berdest ji bo vekêşana daneyan an strukturên SQL Servera navxweyî zêde bibe performansa pirsê dikare baştir bibe.

    1. Grantên Bîrnebûnê Berbiçav
      Hejmara tevahî pêvajoyên ku bi serfirazî bîranîna cîhê xebatê bi dest xistine destnîşan dike. Ger nîşanker bi domdarî dakeve, pêdivî ye ku RAM zêde bibe.
      Zabbix: perf_counter["MSSQL$INSTANCE_NAME:Memory ManagerMemory Grants Outstanding",30]
    2. Grantên Bîrnebûnê li bendê ne
      Hejmara tevahî pêvajoyên ku li benda veqetandina bîranîna xebatê ne destnîşan dike. Bi mezinbûna stabîl a nîşankerê re, pêdivî ye ku RAM zêde bibe.
      Zabbix: perf_counter["MSSQL$INSTANCE_NAME:Rêveberê Bîrê Grantên Bîrê li bendê ne",30]

  10. MS SQL Server: Statîstîk
    Tişta Statîstîkan di Microsoft SQL Server de jimarvan peyda dike da ku berhevok û cûreyên pirsnameyên ku ji mînakek SQL Server re têne şandin bişopînin. Şopandina hejmara berhevkirin û ji nû ve berhevkirina pirsê û hejmara beşên ku ji hêla mînakek SQL Server ve hatî wergirtin têgihiştinê peyda dike ka SQL Server çiqas zû pirsên bikarhêner dimeşîne û optimîzatorê pirsê çiqas bi bandor wan pêvajoyê dike.

    1. Daxwazên Batch / sec
      Hejmara pakêtên fermana Transact-SQL ku di her çirkeyê de hatine wergirtin. Van statîstîkan ji hêla ti sînoran ve têne bandor kirin (I / O, hejmara bikarhêneran, mezinahiya cache, tevliheviya pirsê, hwd.). Hejmarek zêde ya daxwazên pakêtê karûbarê bilind nîşan dide.
      Zabbix: perf_counter["MSSQL$INSTANCE_NAME:SQL StatisticsBatch Requests/sec",30]

Digel van hemî jorîn, hûn dikarin hêmanên daneyê yên din jî mîheng bikin (û her weha bi agahdariyên paşîn li ser wan biafirînin).
1) mîqdara cîhê dîskê belaş
2) mezinahiyên pelên daneya databasê û têketin
û vî awayî.
Lêbelê, hemî van nîşanan pirsgirêka pirsên rast-dem nîşan nakin.
Ji bo vê yekê, hûn hewce ne ku jimarvanên xwe yên taybetî biafirînin.
Ji ber sedemên nepenîtiyê, ez ê mînakên van kontrayan bidim. Wekî din, ew ji bo her pergalê yekta têne mîheng kirin. Lê ez bala xwe didim ku ji bo pergalên wekî 1C, NAV û CRM, jimarvanên pispor dikarin bi pêşdebirên têkildar re werin afirandin.
Ez ê mînakek çêkirina nîşanek gelemperî bidim ku destnîşan dike ka çend daxwaz têne xebitandin û çend daxwaz li bendê ne (rawestandin an asteng kirin) di her kêliyê de.
Ji bo vê yekê, hûn hewce ne ku pêvajoyek hilanîn ava bikin:
code

USE [ИМЯ_БАЗЫ_ДАННЫХ]
GO

SET ANSI_NULLS ON
GO

SET QUOTED_IDENTIFIER ON
GO

CREATE PROCEDURE [nav].[ZabbixGetCountRequestStatus]
	@Status nvarchar(255)
AS
BEGIN
	/*
		возвращает кол-во запросов с заданным статусом
	*/
	SET NOCOUNT ON;

	select count(*) as [Count]
	from sys.dm_exec_requests ER with(readuncommitted)
	where [status]=@Status
END

Dûv re, hûn hewce ne ku biçin peldanka ku Zabbix lê ye (zabbixconfuserparams.d) û 2 pelan bi dirêjkirina ps1 (PowerShell) biafirînin û di her yek ji wan de kodên jêrîn binivîsin:
Koda ji bo xebitandina pirsan

$SQLServer = "НАЗВАНИЕ_ЭКЗЕМПЛЯРА";
$uid = "ЛОГИН"; 
$pwd = "ПАРОЛЬ";
$Status="running";

$connectionString = "Server = $SQLServer; Database=НАЗВАНИЕ_БД; Integrated Security = False; User ID = $uid; Password = $pwd;";

$connection = New-Object System.Data.SqlClient.SqlConnection;
$connection.ConnectionString = $connectionString;

#Создаем запрос непосредственно к MSSQL / Create a request directly to MSSQL
$SqlCmd = New-Object System.Data.SqlClient.SqlCommand;
$SqlCmd.CommandType = [System.Data.CommandType]::StoredProcedure;  
$SqlCmd.CommandText = "nav.ZabbixGetCountRequestStatus";
$SqlCmd.Connection = $Connection;

$paramStatus=$SqlCmd.Parameters.Add("@Status" , [System.Data.SqlDbType]::VarChar);
$paramStatus.Value = $Status;

$connection.Open();
$SqlAdapter = New-Object System.Data.SqlClient.SqlDataAdapter;
$SqlAdapter.SelectCommand = $SqlCmd;
$DataSet = New-Object System.Data.DataSet;
$SqlAdapter.Fill($DataSet) > $null;
$connection.Close();

$result = $DataSet.Tables[0].Rows[0]["Count"];

write-host $result;

Koda ji bo daxwazên li bendê

$SQLServer = "НАЗВАНИЕ_ЭКЗЕМПЛЯРА";
$uid = "ЛОГИН"; 
$pwd = "ПАРОЛЬ";
$Status="suspended";

$connectionString = "Server = $SQLServer; Database=НАЗВАНИЕ_БД; Integrated Security = False; User ID = $uid; Password = $pwd;";

$connection = New-Object System.Data.SqlClient.SqlConnection;
$connection.ConnectionString = $connectionString;

#Создаем запрос непосредственно к MSSQL / Create a request directly to MSSQL
$SqlCmd = New-Object System.Data.SqlClient.SqlCommand;
$SqlCmd.CommandType = [System.Data.CommandType]::StoredProcedure;  
$SqlCmd.CommandText = "nav.ZabbixGetCountRequestStatus";
$SqlCmd.Connection = $Connection;

$paramStatus=$SqlCmd.Parameters.Add("@Status" , [System.Data.SqlDbType]::VarChar);
$paramStatus.Value = $Status;

$connection.Open();
$SqlAdapter = New-Object System.Data.SqlClient.SqlDataAdapter;
$SqlAdapter.SelectCommand = $SqlCmd;
$DataSet = New-Object System.Data.DataSet;
$SqlAdapter.Fill($DataSet) > $null;
$connection.Close();

$result = $DataSet.Tables[0].Rows[0]["Count"];

write-host $result;

Naha hûn hewce ne ku pelek bi pîvanên bikarhêner û pêvekek .conf biafirînin (an jî xêzan li pelek bikarhênerek wusa ya heyî zêde bikin, heke yek berê hatî çêkirin) û rêzikên jêrîn têxin nav:
UserParameter=PARAMETER_NAME_NUMBER_of_QUERIES EXECUTED,powershell -NoProfile -ExecutionPolicy Bypass -Pel FULL_PATHzabbixconfuserparams.dFILE_NAME_FOR_EXECUTED_QUERYES.ps1
UserParameter=PARAMETER_NAME_NUMBER_WAITING_REQUESTS,powershell -NoProfile -ExecutionPolicy Bypass -Pel FULL_PATHzabbixconfuserparams.dFILE_NAME_FOR_WAITING_REQUESTS.ps1
Piştî vê yekê, pelê .conf hilînin û nûnerê Zabbix ji nû ve bidin destpêkirin.
Piştî vê yekê, em du hêmanên nû li Zabbix zêde dikin (di vê rewşê de, nav û mifteyê yek in):
PARAMETER_NAME_NUMBER OF_REQUESTS PERFORMED
PARAMETER_NAME_NUMBER OF_WAITING_REQUESTS
Naha hûn dikarin ji bo daneyên daneyên xwerû yên hatine afirandin grafîkan û pêkêşan biafirînin.

Ger hejmara daxwazên li bendê bi tundî zêde bibe, wê hingê lêpirsîna jêrîn dikare di demek diyar de hemî daxwazên xebitandinê û li bendê bi hûrguliyên ku daxwaz ji ku û di binê kîjan têketinê de hatî bicîh kirin, plansaziya nivîs û pirsê, û her weha hûrguliyên din nîşan bide:
code

/*Активные, готовые к выполнению и ожидающие запросы, а также те, что явно блокируют другие сеансы*/
with tbl0 as (
select ES.[session_id]
,ER.[blocking_session_id]
,ER.[request_id]
,ER.[start_time]
,ER.[status]
,ES.[status] as [status_session]
,ER.[command]
,ER.[percent_complete]
,DB_Name(coalesce(ER.[database_id], ES.[database_id])) as [DBName]
,(select top(1) [text] from sys.dm_exec_sql_text(ER.[sql_handle])) as [TSQL]
,(select top(1) [objectid] from sys.dm_exec_sql_text(ER.[sql_handle])) as [objectid]
,(select top(1) [query_plan] from sys.dm_exec_query_plan(ER.[plan_handle])) as [QueryPlan]
,ER.[wait_type]
,ES.[login_time]
,ES.[host_name]
,ES.[program_name]
,ER.[wait_time]
,ER.[last_wait_type]
,ER.[wait_resource]
,ER.[open_transaction_count]
,ER.[open_resultset_count]
,ER.[transaction_id]
,ER.[context_info]
,ER.[estimated_completion_time]
,ER.[cpu_time]
,ER.[total_elapsed_time]
,ER.[scheduler_id]
,ER.[task_address]
,ER.[reads]
,ER.[writes]
,ER.[logical_reads]
,ER.[text_size]
,ER.[language]
,ER.[date_format]
,ER.[date_first]
,ER.[quoted_identifier]
,ER.[arithabort]
,ER.[ansi_null_dflt_on]
,ER.[ansi_defaults]
,ER.[ansi_warnings]
,ER.[ansi_padding]
,ER.[ansi_nulls]
,ER.[concat_null_yields_null]
,ER.[transaction_isolation_level]
,ER.[lock_timeout]
,ER.[deadlock_priority]
,ER.[row_count]
,ER.[prev_error]
,ER.[nest_level]
,ER.[granted_query_memory]
,ER.[executing_managed_code]
,ER.[group_id]
,ER.[query_hash]
,ER.[query_plan_hash]
,EC.[most_recent_session_id]
,EC.[connect_time]
,EC.[net_transport]
,EC.[protocol_type]
,EC.[protocol_version]
,EC.[endpoint_id]
,EC.[encrypt_option]
,EC.[auth_scheme]
,EC.[node_affinity]
,EC.[num_reads]
,EC.[num_writes]
,EC.[last_read]
,EC.[last_write]
,EC.[net_packet_size]
,EC.[client_net_address]
,EC.[client_tcp_port]
,EC.[local_net_address]
,EC.[local_tcp_port]
,EC.[parent_connection_id]
,EC.[most_recent_sql_handle]
,ES.[host_process_id]
,ES.[client_version]
,ES.[client_interface_name]
,ES.[security_id]
,ES.[login_name]
,ES.[nt_domain]
,ES.[nt_user_name]
,ES.[memory_usage]
,ES.[total_scheduled_time]
,ES.[last_request_start_time]
,ES.[last_request_end_time]
,ES.[is_user_process]
,ES.[original_security_id]
,ES.[original_login_name]
,ES.[last_successful_logon]
,ES.[last_unsuccessful_logon]
,ES.[unsuccessful_logons]
,ES.[authenticating_database_id]
,ER.[sql_handle]
,ER.[statement_start_offset]
,ER.[statement_end_offset]
,ER.[plan_handle]
,ER.[dop]
,coalesce(ER.[database_id], ES.[database_id]) as [database_id]
,ER.[user_id]
,ER.[connection_id]
from sys.dm_exec_requests ER with(readuncommitted)
right join sys.dm_exec_sessions ES with(readuncommitted)
on ES.session_id = ER.session_id 
left join sys.dm_exec_connections EC  with(readuncommitted)
on EC.session_id = ES.session_id
)
, tbl as (
select [session_id]
,[blocking_session_id]
,[request_id]
,[start_time]
,[status]
,[status_session]
,[command]
,[percent_complete]
,[DBName]
,OBJECT_name([objectid], [database_id]) as [object]
,[TSQL]
,[QueryPlan]
,[wait_type]
,[login_time]
,[host_name]
,[program_name]
,[wait_time]
,[last_wait_type]
,[wait_resource]
,[open_transaction_count]
,[open_resultset_count]
,[transaction_id]
,[context_info]
,[estimated_completion_time]
,[cpu_time]
,[total_elapsed_time]
,[scheduler_id]
,[task_address]
,[reads]
,[writes]
,[logical_reads]
,[text_size]
,[language]
,[date_format]
,[date_first]
,[quoted_identifier]
,[arithabort]
,[ansi_null_dflt_on]
,[ansi_defaults]
,[ansi_warnings]
,[ansi_padding]
,[ansi_nulls]
,[concat_null_yields_null]
,[transaction_isolation_level]
,[lock_timeout]
,[deadlock_priority]
,[row_count]
,[prev_error]
,[nest_level]
,[granted_query_memory]
,[executing_managed_code]
,[group_id]
,[query_hash]
,[query_plan_hash]
,[most_recent_session_id]
,[connect_time]
,[net_transport]
,[protocol_type]
,[protocol_version]
,[endpoint_id]
,[encrypt_option]
,[auth_scheme]
,[node_affinity]
,[num_reads]
,[num_writes]
,[last_read]
,[last_write]
,[net_packet_size]
,[client_net_address]
,[client_tcp_port]
,[local_net_address]
,[local_tcp_port]
,[parent_connection_id]
,[most_recent_sql_handle]
,[host_process_id]
,[client_version]
,[client_interface_name]
,[security_id]
,[login_name]
,[nt_domain]
,[nt_user_name]
,[memory_usage]
,[total_scheduled_time]
,[last_request_start_time]
,[last_request_end_time]
,[is_user_process]
,[original_security_id]
,[original_login_name]
,[last_successful_logon]
,[last_unsuccessful_logon]
,[unsuccessful_logons]
,[authenticating_database_id]
,[sql_handle]
,[statement_start_offset]
,[statement_end_offset]
,[plan_handle]
,[dop]
,[database_id]
,[user_id]
,[connection_id]
from tbl0
where [status] in ('suspended', 'running', 'runnable')
)
, tbl_group as (
select [blocking_session_id]
from tbl
where [blocking_session_id]<>0
group by [blocking_session_id]
)
, tbl_res_rec as (
select [session_id]
,[blocking_session_id]
,[request_id]
,[start_time]
,[status]
,[status_session]
,[command]
,[percent_complete]
,[DBName]
,[object]
,[TSQL]
,[QueryPlan]
,[wait_type]
,[login_time]
,[host_name]
,[program_name]
,[wait_time]
,[last_wait_type]
,[wait_resource]
,[open_transaction_count]
,[open_resultset_count]
,[transaction_id]
,[context_info]
,[estimated_completion_time]
,[cpu_time]
,[total_elapsed_time]
,[scheduler_id]
,[task_address]
,[reads]
,[writes]
,[logical_reads]
,[text_size]
,[language]
,[date_format]
,[date_first]
,[quoted_identifier]
,[arithabort]
,[ansi_null_dflt_on]
,[ansi_defaults]
,[ansi_warnings]
,[ansi_padding]
,[ansi_nulls]
,[concat_null_yields_null]
,[transaction_isolation_level]
,[lock_timeout]
,[deadlock_priority]
,[row_count]
,[prev_error]
,[nest_level]
,[granted_query_memory]
,[executing_managed_code]
,[group_id]
,[query_hash]
,[query_plan_hash]
,[most_recent_session_id]
,[connect_time]
,[net_transport]
,[protocol_type]
,[protocol_version]
,[endpoint_id]
,[encrypt_option]
,[auth_scheme]
,[node_affinity]
,[num_reads]
,[num_writes]
,[last_read]
,[last_write]
,[net_packet_size]
,[client_net_address]
,[client_tcp_port]
,[local_net_address]
,[local_tcp_port]
,[parent_connection_id]
,[most_recent_sql_handle]
,[host_process_id]
,[client_version]
,[client_interface_name]
,[security_id]
,[login_name]
,[nt_domain]
,[nt_user_name]
,[memory_usage]
,[total_scheduled_time]
,[last_request_start_time]
,[last_request_end_time]
,[is_user_process]
,[original_security_id]
,[original_login_name]
,[last_successful_logon]
,[last_unsuccessful_logon]
,[unsuccessful_logons]
,[authenticating_database_id]
,[sql_handle]
,[statement_start_offset]
,[statement_end_offset]
,[plan_handle]
,[dop]
,[database_id]
,[user_id]
,[connection_id]
, 0 as [is_blocking_other_session]
from tbl
union all
select tbl0.[session_id]
,tbl0.[blocking_session_id]
,tbl0.[request_id]
,tbl0.[start_time]
,tbl0.[status]
,tbl0.[status_session]
,tbl0.[command]
,tbl0.[percent_complete]
,tbl0.[DBName]
,OBJECT_name(tbl0.[objectid], tbl0.[database_id]) as [object]
,tbl0.[TSQL]
,tbl0.[QueryPlan]
,tbl0.[wait_type]
,tbl0.[login_time]
,tbl0.[host_name]
,tbl0.[program_name]
,tbl0.[wait_time]
,tbl0.[last_wait_type]
,tbl0.[wait_resource]
,tbl0.[open_transaction_count]
,tbl0.[open_resultset_count]
,tbl0.[transaction_id]
,tbl0.[context_info]
,tbl0.[estimated_completion_time]
,tbl0.[cpu_time]
,tbl0.[total_elapsed_time]
,tbl0.[scheduler_id]
,tbl0.[task_address]
,tbl0.[reads]
,tbl0.[writes]
,tbl0.[logical_reads]
,tbl0.[text_size]
,tbl0.[language]
,tbl0.[date_format]
,tbl0.[date_first]
,tbl0.[quoted_identifier]
,tbl0.[arithabort]
,tbl0.[ansi_null_dflt_on]
,tbl0.[ansi_defaults]
,tbl0.[ansi_warnings]
,tbl0.[ansi_padding]
,tbl0.[ansi_nulls]
,tbl0.[concat_null_yields_null]
,tbl0.[transaction_isolation_level]
,tbl0.[lock_timeout]
,tbl0.[deadlock_priority]
,tbl0.[row_count]
,tbl0.[prev_error]
,tbl0.[nest_level]
,tbl0.[granted_query_memory]
,tbl0.[executing_managed_code]
,tbl0.[group_id]
,tbl0.[query_hash]
,tbl0.[query_plan_hash]
,tbl0.[most_recent_session_id]
,tbl0.[connect_time]
,tbl0.[net_transport]
,tbl0.[protocol_type]
,tbl0.[protocol_version]
,tbl0.[endpoint_id]
,tbl0.[encrypt_option]
,tbl0.[auth_scheme]
,tbl0.[node_affinity]
,tbl0.[num_reads]
,tbl0.[num_writes]
,tbl0.[last_read]
,tbl0.[last_write]
,tbl0.[net_packet_size]
,tbl0.[client_net_address]
,tbl0.[client_tcp_port]
,tbl0.[local_net_address]
,tbl0.[local_tcp_port]
,tbl0.[parent_connection_id]
,tbl0.[most_recent_sql_handle]
,tbl0.[host_process_id]
,tbl0.[client_version]
,tbl0.[client_interface_name]
,tbl0.[security_id]
,tbl0.[login_name]
,tbl0.[nt_domain]
,tbl0.[nt_user_name]
,tbl0.[memory_usage]
,tbl0.[total_scheduled_time]
,tbl0.[last_request_start_time]
,tbl0.[last_request_end_time]
,tbl0.[is_user_process]
,tbl0.[original_security_id]
,tbl0.[original_login_name]
,tbl0.[last_successful_logon]
,tbl0.[last_unsuccessful_logon]
,tbl0.[unsuccessful_logons]
,tbl0.[authenticating_database_id]
,tbl0.[sql_handle]
,tbl0.[statement_start_offset]
,tbl0.[statement_end_offset]
,tbl0.[plan_handle]
,tbl0.[dop]
,tbl0.[database_id]
,tbl0.[user_id]
,tbl0.[connection_id]
, 1 as [is_blocking_other_session]
from tbl_group as tg
inner join tbl0 on tg.blocking_session_id=tbl0.session_id
)
,tbl_res_rec_g as (
select [plan_handle],
[sql_handle],
cast([start_time] as date) as [start_time]
from tbl_res_rec
group by [plan_handle],
[sql_handle],
cast([start_time] as date)
)
,tbl_rec_stat_g as (
select qs.[plan_handle]
,qs.[sql_handle]
--,cast(qs.[last_execution_time] as date)	as [last_execution_time]
,min(qs.[creation_time])					as [creation_time]
,max(qs.[execution_count])				as [execution_count]
,max(qs.[total_worker_time])				as [total_worker_time]
,min(qs.[last_worker_time])				as [min_last_worker_time]
,max(qs.[last_worker_time])				as [max_last_worker_time]
,min(qs.[min_worker_time])				as [min_worker_time]
,max(qs.[max_worker_time])				as [max_worker_time]
,max(qs.[total_physical_reads])			as [total_physical_reads]
,min(qs.[last_physical_reads])			as [min_last_physical_reads]
,max(qs.[last_physical_reads])			as [max_last_physical_reads]
,min(qs.[min_physical_reads])				as [min_physical_reads]
,max(qs.[max_physical_reads])				as [max_physical_reads]
,max(qs.[total_logical_writes])			as [total_logical_writes]
,min(qs.[last_logical_writes])			as [min_last_logical_writes]
,max(qs.[last_logical_writes])			as [max_last_logical_writes]
,min(qs.[min_logical_writes])				as [min_logical_writes]
,max(qs.[max_logical_writes])				as [max_logical_writes]
,max(qs.[total_logical_reads])			as [total_logical_reads]
,min(qs.[last_logical_reads])				as [min_last_logical_reads]
,max(qs.[last_logical_reads])				as [max_last_logical_reads]
,min(qs.[min_logical_reads])				as [min_logical_reads]
,max(qs.[max_logical_reads])				as [max_logical_reads]
,max(qs.[total_clr_time])					as [total_clr_time]
,min(qs.[last_clr_time])					as [min_last_clr_time]
,max(qs.[last_clr_time])					as [max_last_clr_time]
,min(qs.[min_clr_time])					as [min_clr_time]
,max(qs.[max_clr_time])					as [max_clr_time]
,max(qs.[total_elapsed_time])				as [total_elapsed_time]
,min(qs.[last_elapsed_time])				as [min_last_elapsed_time]
,max(qs.[last_elapsed_time])				as [max_last_elapsed_time]
,min(qs.[min_elapsed_time])				as [min_elapsed_time]
,max(qs.[max_elapsed_time])				as [max_elapsed_time]
,max(qs.[total_rows])						as [total_rows]
,min(qs.[last_rows])						as [min_last_rows]
,max(qs.[last_rows])						as [max_last_rows]
,min(qs.[min_rows])						as [min_rows]
,max(qs.[max_rows])						as [max_rows]
,max(qs.[total_dop])						as [total_dop]
,min(qs.[last_dop])						as [min_last_dop]
,max(qs.[last_dop])						as [max_last_dop]
,min(qs.[min_dop])						as [min_dop]
,max(qs.[max_dop])						as [max_dop]
,max(qs.[total_grant_kb])					as [total_grant_kb]
,min(qs.[last_grant_kb])					as [min_last_grant_kb]
,max(qs.[last_grant_kb])					as [max_last_grant_kb]
,min(qs.[min_grant_kb])					as [min_grant_kb]
,max(qs.[max_grant_kb])					as [max_grant_kb]
,max(qs.[total_used_grant_kb])			as [total_used_grant_kb]
,min(qs.[last_used_grant_kb])				as [min_last_used_grant_kb]
,max(qs.[last_used_grant_kb])				as [max_last_used_grant_kb]
,min(qs.[min_used_grant_kb])				as [min_used_grant_kb]
,max(qs.[max_used_grant_kb])				as [max_used_grant_kb]
,max(qs.[total_ideal_grant_kb])			as [total_ideal_grant_kb]
,min(qs.[last_ideal_grant_kb])			as [min_last_ideal_grant_kb]
,max(qs.[last_ideal_grant_kb])			as [max_last_ideal_grant_kb]
,min(qs.[min_ideal_grant_kb])				as [min_ideal_grant_kb]
,max(qs.[max_ideal_grant_kb])				as [max_ideal_grant_kb]
,max(qs.[total_reserved_threads])			as [total_reserved_threads]
,min(qs.[last_reserved_threads])			as [min_last_reserved_threads]
,max(qs.[last_reserved_threads])			as [max_last_reserved_threads]
,min(qs.[min_reserved_threads])			as [min_reserved_threads]
,max(qs.[max_reserved_threads])			as [max_reserved_threads]
,max(qs.[total_used_threads])				as [total_used_threads]
,min(qs.[last_used_threads])				as [min_last_used_threads]
,max(qs.[last_used_threads])				as [max_last_used_threads]
,min(qs.[min_used_threads])				as [min_used_threads]
,max(qs.[max_used_threads])				as [max_used_threads]
from tbl_res_rec_g as t
inner join sys.dm_exec_query_stats as qs with(readuncommitted) on t.[plan_handle]=qs.[plan_handle] 
and t.[sql_handle]=qs.[sql_handle] 
and t.[start_time]=cast(qs.[last_execution_time] as date)
group by qs.[plan_handle]
,qs.[sql_handle]
--,qs.[last_execution_time]
)
select t.[session_id] --Сессия
,t.[blocking_session_id] --Сессия, которая явно блокирует сессию [session_id]
,t.[request_id] --Идентификатор запроса. Уникален в контексте сеанса
,t.[start_time] --Метка времени поступления запроса
,DateDiff(second, t.[start_time], GetDate()) as [date_diffSec] --Сколько в сек прошло времени от момента поступления запроса
,t.[status] --Состояние запроса
,t.[status_session] --Состояние сессии
,t.[command] --Тип выполняемой в данный момент команды
, COALESCE(
CAST(NULLIF(t.[total_elapsed_time] / 1000, 0) as BIGINT)
,CASE WHEN (t.[status_session] <> 'running' and isnull(t.[status], '')  <> 'running') 
THEN  DATEDIFF(ss,0,getdate() - nullif(t.[last_request_end_time], '1900-01-01T00:00:00.000'))
END
) as [total_time, sec] --Время всей работы запроса в сек
, CAST(NULLIF((CAST(t.[total_elapsed_time] as BIGINT) - CAST(t.[wait_time] AS BIGINT)) / 1000, 0 ) as bigint) as [work_time, sec] --Время работы запроса в сек без учета времени ожиданий
, CASE WHEN (t.[status_session] <> 'running' AND ISNULL(t.[status],'') <> 'running') 
THEN  DATEDIFF(ss,0,getdate() - nullif(t.[last_request_end_time], '1900-01-01T00:00:00.000'))
END as [sleep_time, sec] --Время сна в сек
, NULLIF( CAST((t.[logical_reads] + t.[writes]) * 8 / 1024 as numeric(38,2)), 0) as [IO, MB] --операций чтения и записи в МБ
, CASE  t.transaction_isolation_level
WHEN 0 THEN 'Unspecified'
WHEN 1 THEN 'ReadUncommited'
WHEN 2 THEN 'ReadCommited'
WHEN 3 THEN 'Repetable'
WHEN 4 THEN 'Serializable'
WHEN 5 THEN 'Snapshot'
END as [transaction_isolation_level_desc] --уровень изоляции транзакции (расшифровка)
,t.[percent_complete] --Процент завершения работы для следующих команд
,t.[DBName] --БД
,t.[object] --Объект
, SUBSTRING(
t.[TSQL]
, t.[statement_start_offset]/2+1
,	(
CASE WHEN ((t.[statement_start_offset]<0) OR (t.[statement_end_offset]<0))
THEN DATALENGTH (t.[TSQL])
ELSE t.[statement_end_offset]
END
- t.[statement_start_offset]
)/2 +1
) as [CURRENT_REQUEST] --Текущий выполняемый запрос в пакете
,t.[TSQL] --Запрос всего пакета
,t.[QueryPlan] --План всего пакета
,t.[wait_type] --Если запрос в настоящий момент блокирован, в столбце содержится тип ожидания (sys.dm_os_wait_stats)
,t.[login_time] --Время подключения сеанса
,t.[host_name] --Имя клиентской рабочей станции, указанное в сеансе. Для внутреннего сеанса это значение равно NULL
,t.[program_name] --Имя клиентской программы, которая инициировала сеанс. Для внутреннего сеанса это значение равно NULL
,cast(t.[wait_time]/1000 as decimal(18,3)) as [wait_timeSec] --Если запрос в настоящий момент блокирован, в столбце содержится продолжительность текущего ожидания (в секундах)
,t.[wait_time] --Если запрос в настоящий момент блокирован, в столбце содержится продолжительность текущего ожидания (в миллисекундах)
,t.[last_wait_type] --Если запрос был блокирован ранее, в столбце содержится тип последнего ожидания
,t.[wait_resource] --Если запрос в настоящий момент блокирован, в столбце указан ресурс, освобождения которого ожидает запрос
,t.[open_transaction_count] --Число транзакций, открытых для данного запроса
,t.[open_resultset_count] --Число результирующих наборов, открытых для данного запроса
,t.[transaction_id] --Идентификатор транзакции, в которой выполняется запрос
,t.[context_info] --Значение CONTEXT_INFO сеанса
,cast(t.[estimated_completion_time]/1000 as decimal(18,3)) as [estimated_completion_timeSec] --Только для внутреннего использования. Не допускает значение NULL
,t.[estimated_completion_time] --Только для внутреннего использования. Не допускает значение NULL
,cast(t.[cpu_time]/1000 as decimal(18,3)) as [cpu_timeSec] --Время ЦП (в секундах), затраченное на выполнение запроса
,t.[cpu_time] --Время ЦП (в миллисекундах), затраченное на выполнение запроса
,cast(t.[total_elapsed_time]/1000 as decimal(18,3)) as [total_elapsed_timeSec] --Общее время, истекшее с момента поступления запроса (в секундах)
,t.[total_elapsed_time] --Общее время, истекшее с момента поступления запроса (в миллисекундах)
,t.[scheduler_id] --Идентификатор планировщика, который планирует данный запрос
,t.[task_address] --Адрес блока памяти, выделенного для задачи, связанной с этим запросом
,t.[reads] --Число операций чтения, выполненных данным запросом
,t.[writes] --Число операций записи, выполненных данным запросом
,t.[logical_reads] --Число логических операций чтения, выполненных данным запросом
,t.[text_size] --Установка параметра TEXTSIZE для данного запроса
,t.[language] --Установка языка для данного запроса
,t.[date_format] --Установка параметра DATEFORMAT для данного запроса
,t.[date_first] --Установка параметра DATEFIRST для данного запроса
,t.[quoted_identifier] --1 = Параметр QUOTED_IDENTIFIER для запроса включен (ON). В противном случае — 0
,t.[arithabort] --1 = Параметр ARITHABORT для запроса включен (ON). В противном случае — 0
,t.[ansi_null_dflt_on] --1 = Параметр ANSI_NULL_DFLT_ON для запроса включен (ON). В противном случае — 0
,t.[ansi_defaults] --1 = Параметр ANSI_DEFAULTS для запроса включен (ON). В противном случае — 0
,t.[ansi_warnings] --1 = Параметр ANSI_WARNINGS для запроса включен (ON). В противном случае — 0
,t.[ansi_padding] --1 = Параметр ANSI_PADDING для запроса включен (ON)
,t.[ansi_nulls] --1 = Параметр ANSI_NULLS для запроса включен (ON). В противном случае — 0
,t.[concat_null_yields_null] --1 = Параметр CONCAT_NULL_YIELDS_NULL для запроса включен (ON). В противном случае — 0
,t.[transaction_isolation_level] --Уровень изоляции, с которым создана транзакция для данного запроса
,cast(t.[lock_timeout]/1000 as decimal(18,3)) as [lock_timeoutSec] --Время ожидания блокировки для данного запроса (в секундах)
,t.[lock_timeout] --Время ожидания блокировки для данного запроса (в миллисекундах)
,t.[deadlock_priority] --Значение параметра DEADLOCK_PRIORITY для данного запроса
,t.[row_count] --Число строк, возвращенных клиенту по данному запросу
,t.[prev_error] --Последняя ошибка, происшедшая при выполнении запроса
,t.[nest_level] --Текущий уровень вложенности кода, выполняемого для данного запроса
,t.[granted_query_memory] --Число страниц, выделенных для выполнения поступившего запроса (1 страница-это примерно 8 КБ)
,t.[executing_managed_code] --Указывает, выполняет ли данный запрос в настоящее время код объекта среды CLR (например, процедуры, типа или триггера).
--Этот флаг установлен в течение всего времени, когда объект среды CLR находится в стеке, даже когда из среды вызывается код Transact-SQL
,t.[group_id]	--Идентификатор группы рабочей нагрузки, которой принадлежит этот запрос
,t.[query_hash] --Двоичное хэш-значение рассчитывается для запроса и используется для идентификации запросов с аналогичной логикой.
--Можно использовать хэш запроса для определения использования статистических ресурсов для запросов, которые отличаются только своими литеральными значениями
,t.[query_plan_hash] --Двоичное хэш-значение рассчитывается для плана выполнения запроса и используется для идентификации аналогичных планов выполнения запросов.
--Можно использовать хэш плана запроса для нахождения совокупной стоимости запросов со схожими планами выполнения
,t.[most_recent_session_id] --Представляет собой идентификатор сеанса самого последнего запроса, связанного с данным соединением
,t.[connect_time] --Отметка времени установления соединения
,t.[net_transport] --Содержит описание физического транспортного протокола, используемого данным соединением
,t.[protocol_type] --Указывает тип протокола передачи полезных данных
,t.[protocol_version] --Версия протокола доступа к данным, связанного с данным соединением
,t.[endpoint_id] --Идентификатор, описывающий тип соединения. Этот идентификатор endpoint_id может использоваться для запросов к представлению sys.endpoints
,t.[encrypt_option] --Логическое значение, указывающее, разрешено ли шифрование для данного соединения
,t.[auth_scheme] --Указывает схему проверки подлинности (SQL Server или Windows), используемую с данным соединением
,t.[node_affinity] --Идентифицирует узел памяти, которому соответствует данное соединение
,t.[num_reads] --Число пакетов, принятых посредством данного соединения
,t.[num_writes] --Число пакетов, переданных посредством данного соединения
,t.[last_read] --Отметка времени о последнем полученном пакете данных
,t.[last_write] --Отметка времени о последнем отправленном пакете данных
,t.[net_packet_size] --Размер сетевого пакета, используемый для передачи данных
,t.[client_net_address] --Сетевой адрес удаленного клиента
,t.[client_tcp_port] --Номер порта на клиентском компьютере, который используется при осуществлении соединения
,t.[local_net_address] --IP-адрес сервера, с которым установлено данное соединение. Доступен только для соединений, которые в качестве транспорта данных используют протокол TCP
,t.[local_tcp_port] --TCP-порт сервера, если соединение использует протокол TCP
,t.[parent_connection_id] --Идентифицирует первичное соединение, используемое в сеансе MARS
,t.[most_recent_sql_handle] --Дескриптор последнего запроса SQL, выполненного с помощью данного соединения. Постоянно проводится синхронизация между столбцом most_recent_sql_handle и столбцом most_recent_session_id
,t.[host_process_id] --Идентификатор процесса клиентской программы, которая инициировала сеанс. Для внутреннего сеанса это значение равно NULL
,t.[client_version] --Версия TDS-протокола интерфейса, который используется клиентом для подключения к серверу. Для внутреннего сеанса это значение равно NULL
,t.[client_interface_name] --Имя библиотеки или драйвер, используемый клиентом для обмена данными с сервером. Для внутреннего сеанса это значение равно NULL
,t.[security_id] --Идентификатор безопасности Microsoft Windows, связанный с именем входа
,t.[login_name] --SQL Server Имя входа, под которой выполняется текущий сеанс.
--Чтобы узнать первоначальное имя входа, с помощью которого был создан сеанс, см. параметр original_login_name.
--Может быть SQL Server проверка подлинности имени входа или имени пользователя домена, прошедшего проверку подлинности Windows
,t.[nt_domain] --Домен Windows для клиента, если во время сеанса применяется проверка подлинности Windows или доверительное соединение.
--Для внутренних сеансов и пользователей, не принадлежащих к домену, это значение равно NULL
,t.[nt_user_name] --Имя пользователя Windows для клиента, если во время сеанса используется проверка подлинности Windows или доверительное соединение.
--Для внутренних сеансов и пользователей, не принадлежащих к домену, это значение равно NULL
,t.[memory_usage] --Количество 8-килобайтовых страниц памяти, используемых данным сеансом
,t.[total_scheduled_time] --Общее время, назначенное данному сеансу (включая его вложенные запросы) для исполнения, в миллисекундах
,t.[last_request_start_time] --Время, когда начался последний запрос данного сеанса. Это может быть запрос, выполняющийся в данный момент
,t.[last_request_end_time] --Время завершения последнего запроса в рамках данного сеанса
,t.[is_user_process] --0, если сеанс является системным. В противном случае значение равно 1
,t.[original_security_id] --Microsoft Идентификатор безопасности Windows, связанный с параметром original_login_name
,t.[original_login_name] --SQL Server Имя входа, которую использует клиент создал данный сеанс.
--Это может быть имя входа SQL Server, прошедшее проверку подлинности, имя пользователя домена Windows, 
--прошедшее проверку подлинности, или пользователь автономной базы данных.
--Обратите внимание, что после первоначального соединения для сеанса может быть выполнено много неявных или явных переключений контекста.
--Например если EXECUTE AS используется
,t.[last_successful_logon] --Время последнего успешного входа в систему для имени original_login_name до запуска текущего сеанса
,t.[last_unsuccessful_logon] --Время последнего неуспешного входа в систему для имени original_login_name до запуска текущего сеанса
,t.[unsuccessful_logons] --Число неуспешных попыток входа в систему для имени original_login_name между временем last_successful_logon и временем login_time
,t.[authenticating_database_id] --Идентификатор базы данных, выполняющей проверку подлинности участника.
--Для имен входа это значение будет равно 0.
--Для пользователей автономной базы данных это значение будет содержать идентификатор автономной базы данных
,t.[sql_handle] --Хэш-карта текста SQL-запроса
,t.[statement_start_offset] --Количество символов в выполняемом в настоящий момент пакете или хранимой процедуре, в которой запущена текущая инструкция.
--Может применяться вместе с функциями динамического управления sql_handle, statement_end_offset и sys.dm_exec_sql_text
--для извлечения исполняемой в настоящий момент инструкции по запросу
,t.[statement_end_offset] --Количество символов в выполняемом в настоящий момент пакете или хранимой процедуре, в которой завершилась текущая инструкция.
--Может применяться вместе с функциями динамического управления sql_handle, statement_end_offset и sys.dm_exec_sql_text
--для извлечения исполняемой в настоящий момент инструкции по запросу
,t.[plan_handle] --Хэш-карта плана выполнения SQL
,t.[database_id] --Идентификатор базы данных, к которой выполняется запрос
,t.[user_id] --Идентификатор пользователя, отправившего данный запрос
,t.[connection_id] --Идентификатор соединения, по которому поступил запрос
,t.[is_blocking_other_session] --1-сессия явно блокирует другие сессии, 0-сессия явно не блокирует другие сессии
,coalesce(t.[dop], mg.[dop]) as [dop] --Степень параллелизма запроса
,mg.[request_time] --Дата и время обращения запроса за предоставлением памяти
,mg.[grant_time] --Дата и время, когда запросу была предоставлена память. Возвращает значение NULL, если память еще не была предоставлена
,mg.[requested_memory_kb] --Общий объем запрошенной памяти в килобайтах
,mg.[granted_memory_kb] --Общий объем фактически предоставленной памяти в килобайтах.
--Может быть значение NULL, если память еще не была предоставлена.
--Обычно это значение должно быть одинаковым с requested_memory_kb.
--Для создания индекса сервер может разрешить дополнительное предоставление по требованию памяти,
--объем которой выходит за рамки изначально предоставленной памяти
,mg.[required_memory_kb] --Минимальный объем памяти в килобайтах (КБ), необходимый для выполнения данного запроса.
--Значение requested_memory_kb равно этому объему или больше его
,mg.[used_memory_kb] --Используемый в данный момент объем физической памяти (в килобайтах)
,mg.[max_used_memory_kb] --Максимальный объем используемой до данного момента физической памяти в килобайтах
,mg.[query_cost] --Ожидаемая стоимость запроса
,mg.[timeout_sec] --Время ожидания данного запроса в секундах до отказа от обращения за предоставлением памяти
,mg.[resource_semaphore_id] --Неуникальный идентификатор семафора ресурса, которого ожидает данный запрос
,mg.[queue_id] --Идентификатор ожидающей очереди, в которой данный запрос ожидает предоставления памяти.
--Значение NULL, если память уже предоставлена
,mg.[wait_order] --Последовательный порядок ожидающих запросов в указанной очереди queue_id.
--Это значение может изменяться для заданного запроса, если другие запросы отказываются от предоставления памяти или получают ее.
--Значение NULL, если память уже предоставлена
,mg.[is_next_candidate] --Является следующим кандидатом на предоставление памяти (1 = да, 0 = нет, NULL = память уже предоставлена)
,mg.[wait_time_ms] --Время ожидания в миллисекундах. Значение NULL, если память уже предоставлена
,mg.[pool_id] --Идентификатор пула ресурсов, к которому принадлежит данная группа рабочей нагрузки
,mg.[is_small] --Значение 1 означает, что для данной операции предоставления памяти используется малый семафор ресурса.
--Значение 0 означает использование обычного семафора
,mg.[ideal_memory_kb] --Объем, в килобайтах (КБ), предоставленной памяти, необходимый для размещения всех данных в физической памяти.
--Основывается на оценке количества элементов
,mg.[reserved_worker_count] --Число рабочих процессов, зарезервированной с помощью параллельных запросов, а также число основных рабочих процессов, используемых всеми запросами
,mg.[used_worker_count] --Число рабочих процессов, используемых параллельных запросов
,mg.[max_used_worker_count] --???
,mg.[reserved_node_bitmap] --???
,pl.[bucketid] --Идентификатор сегмента хэша, в который кэшируется запись.
--Значение указывает диапазон от 0 до значения размера хэш-таблицы для типа кэша.
--Для кэшей SQL Plans и Object Plans размер хэш-таблицы может достигать 10007 на 32-разрядных версиях систем и 40009 — на 64-разрядных.
--Для кэша Bound Trees размер хэш-таблицы может достигать 1009 на 32-разрядных версиях систем и 4001 на 64-разрядных.
--Для кэша расширенных хранимых процедур размер хэш-таблицы может достигать 127 на 32-разрядных и 64-разрядных версиях систем
,pl.[refcounts] --Число объектов кэша, ссылающихся на данный объект кэша.
--Значение refcounts для записи должно быть не меньше 1, чтобы размещаться в кэше
,pl.[usecounts] --Количество повторений поиска объекта кэша.
--Остается без увеличения, если параметризованные запросы обнаруживают план в кэше.
--Может быть увеличен несколько раз при использовании инструкции showplan
,pl.[size_in_bytes] --Число байтов, занимаемых объектом кэша
,pl.[memory_object_address] --Адрес памяти кэшированной записи.
--Это значение можно использовать с представлением sys.dm_os_memory_objects,
--чтобы проанализировать распределение памяти кэшированного плана, 
--и с представлением sys.dm_os_memory_cache_entries для определения затрат на кэширование записи
,pl.[cacheobjtype] --Тип объекта в кэше. Значение может быть одним из следующих
,pl.[objtype] --Тип объекта. Значение может быть одним из следующих
,pl.[parent_plan_handle] --Родительский план
--данные из sys.dm_exec_query_stats брались за сутки, в которых была пара (запрос, план)
,qs.[creation_time] --Время компиляции плана
,qs.[execution_count] --Количество выполнений плана с момента последней компиляции
,qs.[total_worker_time] --Общее время ЦП, затраченное на выполнение плана с момента компиляции, в микросекундах (но с точностью до миллисекунды)
,qs.[min_last_worker_time] --Минимальное время ЦП, затраченное на последнее выполнение плана, в микросекундах (но с точностью до миллисекунды)
,qs.[max_last_worker_time] --Максимальное время ЦП, затраченное на последнее выполнение плана, в микросекундах (но с точностью до миллисекунды)
,qs.[min_worker_time] --Минимальное время ЦП, когда-либо затраченное на выполнение плана, в микросекундах (но с точностью до миллисекунды)
,qs.[max_worker_time] --Максимальное время ЦП, когда-либо затраченное на выполнение плана, в микросекундах (но с точностью до миллисекунды)
,qs.[total_physical_reads] --Общее количество операций физического считывания при выполнении плана с момента его компиляции.
--Значение всегда равно 0 при запросе оптимизированной для памяти таблицы
,qs.[min_last_physical_reads] --Минимальное количество операций физического считывания за время последнего выполнения плана.
--Значение всегда равно 0 при запросе оптимизированной для памяти таблицы
,qs.[max_last_physical_reads] --Максимальное количество операций физического считывания за время последнего выполнения плана.
--Значение всегда равно 0 при запросе оптимизированной для памяти таблицы
,qs.[min_physical_reads] --Минимальное количество операций физического считывания за одно выполнение плана.
--Значение всегда равно 0 при запросе оптимизированной для памяти таблицы
,qs.[max_physical_reads] --Максимальное количество операций физического считывания за одно выполнение плана.
--Значение всегда равно 0 при запросе оптимизированной для памяти таблицы
,qs.[total_logical_writes] --Общее количество операций логической записи при выполнении плана с момента его компиляции.
--Значение всегда равно 0 при запросе оптимизированной для памяти таблицы
,qs.[min_last_logical_writes] --Минимальное количество страниц в буферном пуле, загрязненных во время последнего выполнения плана.
--Если страница уже является «грязной» (т. е. измененной), операции записи не учитываются.
--Значение всегда равно 0 при запросе оптимизированной для памяти таблицы
,qs.[max_last_logical_writes] --Максимальное количество страниц в буферном пуле, загрязненных во время последнего выполнения плана.
--Если страница уже является «грязной» (т. е. измененной), операции записи не учитываются.
--Значение всегда равно 0 при запросе оптимизированной для памяти таблицы
,qs.[min_logical_writes] --Минимальное количество операций логической записи за одно выполнение плана.
--Значение всегда равно 0 при запросе оптимизированной для памяти таблицы
,qs.[max_logical_writes] --Максимальное количество операций логической записи за одно выполнение плана.
--Значение всегда равно 0 при запросе оптимизированной для памяти таблицы
,qs.[total_logical_reads] --Общее количество операций логического считывания при выполнении плана с момента его компиляции.
--Значение всегда равно 0 при запросе оптимизированной для памяти таблицы
,qs.[min_last_logical_reads] --Минимальное количество операций логического считывания за время последнего выполнения плана.
--Значение всегда равно 0 при запросе оптимизированной для памяти таблицы
,qs.[max_last_logical_reads] --Максимальное количество операций логического считывания за время последнего выполнения плана.
--Значение всегда равно 0 при запросе оптимизированной для памяти таблицы
,qs.[min_logical_reads]	   --Минимальное количество операций логического считывания за одно выполнение плана.
--Значение всегда равно 0 при запросе оптимизированной для памяти таблицы
,qs.[max_logical_reads]	--Максимальное количество операций логического считывания за одно выполнение плана.
--Значение всегда равно 0 при запросе оптимизированной для памяти таблицы
,qs.[total_clr_time]	--Время, в микросекундах (но с точностью до миллисекунды),
--внутри Microsoft .NET Framework общеязыковая среда выполнения (CLR) объекты при выполнении плана с момента его компиляции.
--Объекты среды CLR могут быть хранимыми процедурами, функциями, триггерами, типами и статистическими выражениями
,qs.[min_last_clr_time] --Минимальное время, в микросекундах (но с точностью до миллисекунды),
--затраченное внутри .NET Framework объекты среды CLR во время последнего выполнения плана.
--Объекты среды CLR могут быть хранимыми процедурами, функциями, триггерами, типами и статистическими выражениями
,qs.[max_last_clr_time] --Максимальное время, в микросекундах (но с точностью до миллисекунды),
--затраченное внутри .NET Framework объекты среды CLR во время последнего выполнения плана.
--Объекты среды CLR могут быть хранимыми процедурами, функциями, триггерами, типами и статистическими выражениями
,qs.[min_clr_time] --Минимальное время, когда-либо затраченное на выполнение плана внутри объектов .NET Framework среды CLR,
--в микросекундах (но с точностью до миллисекунды).
--Объекты среды CLR могут быть хранимыми процедурами, функциями, триггерами, типами и статистическими выражениями
,qs.[max_clr_time] --Максимальное время, когда-либо затраченное на выполнение плана внутри среды CLR .NET Framework,
--в микросекундах (но с точностью до миллисекунды).
--Объекты среды CLR могут быть хранимыми процедурами, функциями, триггерами, типами и статистическими выражениями
--,qs.[total_elapsed_time] --Общее время, затраченное на выполнение плана, в микросекундах (но с точностью до миллисекунды)
,qs.[min_last_elapsed_time] --Минимальное время, затраченное на последнее выполнение плана, в микросекундах (но с точностью до миллисекунды)
,qs.[max_last_elapsed_time] --Максимальное время, затраченное на последнее выполнение плана, в микросекундах (но с точностью до миллисекунды)
,qs.[min_elapsed_time] --Минимальное время, когда-либо затраченное на выполнение плана, в микросекундах (но с точностью до миллисекунды)
,qs.[max_elapsed_time] --Максимальное время, когда-либо затраченное на выполнение плана, в микросекундах (но с точностью до миллисекунды)
,qs.[total_rows] --Общее число строк, возвращаемых запросом. Не может иметь значение null.
--Значение всегда равно 0, если скомпилированная в собственном коде хранимая процедура запрашивает оптимизированную для памяти таблицу
,qs.[min_last_rows] --Минимальное число строк, возвращенных последним выполнением запроса. Не может иметь значение null.
--Значение всегда равно 0, если скомпилированная в собственном коде хранимая процедура запрашивает оптимизированную для памяти таблицу
,qs.[max_last_rows] --Максимальное число строк, возвращенных последним выполнением запроса. Не может иметь значение null.
--Значение всегда равно 0, если скомпилированная в собственном коде хранимая процедура запрашивает оптимизированную для памяти таблицу
,qs.[min_rows] --Минимальное количество строк, когда-либо возвращенных по запросу во время выполнения один
--Значение всегда равно 0, если скомпилированная в собственном коде хранимая процедура запрашивает оптимизированную для памяти таблицу
,qs.[max_rows] --Максимальное число строк, когда-либо возвращенных по запросу во время выполнения один
--Значение всегда равно 0, если скомпилированная в собственном коде хранимая процедура запрашивает оптимизированную для памяти таблицу
,qs.[total_dop] --Общую сумму по степени параллелизма плана используется с момента его компиляции.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[min_last_dop] --Минимальная степень параллелизма, если время последнего выполнения плана.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[max_last_dop] --Максимальная степень параллелизма, если время последнего выполнения плана.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[min_dop] --Минимальная степень параллелизма этот план когда-либо используется во время одного выполнения.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[max_dop] --Максимальная степень параллелизма этот план когда-либо используется во время одного выполнения.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[total_grant_kb] --Общий объем зарезервированной памяти в КБ предоставить этот план, полученных с момента его компиляции.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[min_last_grant_kb] --Минимальный объем зарезервированной памяти предоставляет в КБ, когда время последнего выполнения плана.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[max_last_grant_kb] --Максимальный объем зарезервированной памяти предоставляет в КБ, когда время последнего выполнения плана.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[min_grant_kb] --Минимальный объем зарезервированной памяти в КБ предоставить никогда не получено в ходе одного выполнения плана.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[max_grant_kb] --Максимальный объем зарезервированной памяти в КБ предоставить никогда не получено в ходе одного выполнения плана.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[total_used_grant_kb] --Общий объем зарезервированной памяти в КБ предоставить этот план, используемый с момента его компиляции.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[min_last_used_grant_kb] --Минимальная сумма предоставления используемой памяти в КБ, если время последнего выполнения плана.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[max_last_used_grant_kb] --Максимальная сумма предоставления используемой памяти в КБ, если время последнего выполнения плана.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[min_used_grant_kb] --Минимальный объем используемой памяти в КБ предоставить никогда не используется при выполнении одного плана.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[max_used_grant_kb] --Максимальный объем используемой памяти в КБ предоставить никогда не используется при выполнении одного плана.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[total_ideal_grant_kb] --Общий объем идеальный память в КБ, оценка плана с момента его компиляции.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[min_last_ideal_grant_kb] --Минимальный объем памяти, идеальным предоставляет в КБ, когда время последнего выполнения плана.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[max_last_ideal_grant_kb] --Максимальный объем памяти, идеальным предоставляет в КБ, когда время последнего выполнения плана.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[min_ideal_grant_kb] --Минимальный объем памяти идеальный предоставления в этот план когда-либо оценка во время выполнения один КБ.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[max_ideal_grant_kb] --Максимальный объем памяти идеальный предоставления в этот план когда-либо оценка во время выполнения один КБ.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[total_reserved_threads] --Общая сумма по зарезервированным параллельного потоков этот план когда-либо использовавшегося с момента его компиляции.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[min_last_reserved_threads] --Минимальное число зарезервированных параллельных потоков, когда время последнего выполнения плана.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[max_last_reserved_threads] --Максимальное число зарезервированных параллельных потоков, когда время последнего выполнения плана.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[min_reserved_threads] --Минимальное число зарезервированных параллельного потоков, когда-либо использовать при выполнении одного плана.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[max_reserved_threads] --Максимальное число зарезервированных параллельного потоков никогда не используется при выполнении одного плана.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[total_used_threads] --Общая сумма используется параллельных потоков этот план когда-либо использовавшегося с момента его компиляции.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[min_last_used_threads] --Минимальное число используемых параллельных потоков, когда время последнего выполнения плана.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[max_last_used_threads] --Максимальное число используемых параллельных потоков, когда время последнего выполнения плана.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[min_used_threads] --Минимальное число используемых параллельных потоков, при выполнении одного плана использовали.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
,qs.[max_used_threads] --Максимальное число используемых параллельных потоков, при выполнении одного плана использовали.
--Он всегда будет равно 0 для запроса к таблице, оптимизированной для памяти
from tbl_res_rec as t
left outer join sys.dm_exec_query_memory_grants as mg on t.[plan_handle]=mg.[plan_handle] and t.[sql_handle]=mg.[sql_handle]
left outer join sys.dm_exec_cached_plans as pl on t.[plan_handle]=pl.[plan_handle]
left outer join tbl_rec_stat_g as qs on t.[plan_handle]=qs.[plan_handle] and t.[sql_handle]=qs.[sql_handle] --and qs.[last_execution_time]=cast(t.[start_time] as date);

Di heman demê de ez ji we re bi bîr bînim ku li gorî statîstîkên berhevkirî hûn dikarin pirsên herî dijwar bistînin:
code

/*
creation_time - Время, когда запрос был скомпилирован. Поскольку при старте сервера кэш пустой, данное время всегда больше либо равно моменту запуска сервиса. Если время, указанное в этом столбце позже, чем предполагаемое (первое использование процедуры), это говорит о том, что запрос по тем или иным причинам был рекомпилирован.
last_execution_time - Момент фактического последнего выполнения запроса.
execution_count - Сколько раз запрос был выполнен с момента компиляции
Количество выполнений позволяет найти ошибки в алгоритмах - часто в наиболее выполняемых запросах оказываются те, которые находятся внутри каких-либо циклов однако могут быть выполнены перед самим циклом один раз. Например, получение каких-либо параметров из базы данных, не меняющихся внутри цикла.
CPU - Суммарное время использования процессора в миллисекундах. Если запрос обрабатывается параллельно, то это время может превысить общее время выполнения запроса, поскольку суммируется время использования запроса каждым ядром. Во время использования процессора включается только фактическая нагрузка на ядра, в нее не входят ожидания каких-либо ресурсов.
Очевидно, что данный показатель позволяет выявлять запросы, наиболее сильно загружающие процессор.
AvgCPUTime - Средняя загрузка процессора на один запрос. 
TotDuration - Общее время выполнения запроса, в миллисекундах.
Данный параметр может быть использован для поиска тех запросов, которые, независимо от причины выполняются "наиболее долго". Если общее время выполнения запроса существенно ниже времени CPU (с поправкой на параллелизм) - это говорит о том, что при выполнения запроса были ожидания каких-либо ресурсов. В большинстве случаев это связано с дисковой активностью или блокировками, но также это может быть сетевой интерфейс или другой ресурс. 
Полный список типов ожиданий можно посмотреть в описании представления sys.dm_os_wait_stats.
AvgDur - Среднее время выполнения запроса в миллисекундах.
Reads - Общее количество чтений.
Это пожалуй лучший агрегатный показатель, позволяющий выявить наиболее нагружающие сервер запросы.
Логическое чтение - это разовое обращение к странице данных, физические чтения не учитываются.
В рамках выполнения одного запроса, могут происходить неоднократные обращения к одной и той же странице.
Чем больше обращений к страницам, тем больше требуется дисковых чтений, памяти и, если речь идет о повторных обращениях, большее время требуется удерживать страницы в памяти.
Writes - Общее количество изменений страниц данных.
Характеризует то, как запрос "нагружает" дисковую систему операциями записи.
Следует помнить, что этот показатель может быть больше 0 не только у тех запросов, которые явно меняют данные, но также и у тех, которые сохраняют промежуточные данные в tempdb.
AggIO - Общее количество логических операций ввода-вывода (суммарно)
Как правило, количество логических чтений на порядки превышает количество операций записи, поэтому этот показатель сам по себе для анализа применим в редких случаях.
AvgIO - Среднее количество логических дисковых операций на одно выполнение запроса.
Значение данного показателя можно анализировать из следующих соображений:
Одна страница данных - это 8192 байта. Можно получить среднее количество байт данных, "обрабатываемых" данным запросом. Если этот объем превышает реальное количество данных, которые обрабатывает запрос (суммарный объем данных в используемых в запросе таблицах), это говорит о том, что был выбран заведомо плохой план выполнения и требуется заняться оптимизацией данного запроса.
Я встречал случай, когда один запрос делал количество обращений, эквивалентных объему в 5Тб, при этом общий объем данных в это БД был 300Гб, а объем данных в таблицах, задействованных в запросе не превышал 10Гб.
В общем можно описать одну причину такого поведения сервера - вместо использования индекса сервер предпочитает сканировать таблицу или наоборот.
Если объем логических чтений в разы превосходит общие объем данных, то это вызвано повторным обращениям к одним и тем же страницам данных. Помимо того, что в одном запросе таблица может быть использована несколько раз, к одним и тем же страницам сервер обращается например в случаях, когда используется индекс и по результатам поиска по нему, найденные некоторые строки данных лежат на одной и той же странице. Конечно, в таком случае предпочтительным могло бы быть сканирование таблицы - в этом случае сервер обращался бы к каждой странице данных только один раз. Однако этому часто мешают... попытки оптимизации запросов, когда разработчик явно указывает, какой индекс или тип соединения должен быть использован.
Обратный случай - вместо использования индекса было выбрано сканирование таблицы. Как правило, это связано с тем, что статистика устарела и требуется её обновление. Однако и в этом случае причиной неудачно выбранного плана вполне могут оказаться подсказки оптимизатору запросов.
query_text - Текст самого запроса
database_name - Имя базы данных, в находится объект, содержащий запрос. NULL для системных процедур
object_name - Имя объекта (процедуры или функции), содержащего запрос.
*/
with s as (
select  creation_time,
last_execution_time,
execution_count,
total_worker_time/1000 as CPU,
convert(money, (total_worker_time))/(execution_count*1000)as [AvgCPUTime],
qs.total_elapsed_time/1000 as TotDuration,
convert(money, (qs.total_elapsed_time))/(execution_count*1000)as [AvgDur],
total_logical_reads as [Reads],
total_logical_writes as [Writes],
total_logical_reads+total_logical_writes as [AggIO],
convert(money, (total_logical_reads+total_logical_writes)/(execution_count + 0.0))as [AvgIO],
[sql_handle],
plan_handle,
statement_start_offset,
statement_end_offset
from sys.dm_exec_query_stats as qs with(readuncommitted)
where convert(money, (qs.total_elapsed_time))/(execution_count*1000)>=100 --выполнялся запрос не менее 100 мс
)
select
s.creation_time,
s.last_execution_time,
s.execution_count,
s.CPU,
s.[AvgCPUTime],
s.TotDuration,
s.[AvgDur],
s.[Reads],
s.[Writes],
s.[AggIO],
s.[AvgIO],
--st.text as query_text,
case 
when sql_handle IS NULL then ' '
else(substring(st.text,(s.statement_start_offset+2)/2,(
case
when s.statement_end_offset =-1 then len(convert(nvarchar(MAX),st.text))*2      
else s.statement_end_offset    
end - s.statement_start_offset)/2  ))
end as query_text,
db_name(st.dbid) as database_name,
object_schema_name(st.objectid, st.dbid)+'.'+object_name(st.objectid, st.dbid) as [object_name],
sp.[query_plan],
s.[sql_handle],
s.plan_handle
from s
cross apply sys.dm_exec_sql_text(s.[sql_handle]) as st
cross apply sys.dm_exec_query_plan(s.[plan_handle]) as sp

Hûn dikarin ji bo MySQL jî binivîsin. Ji bo vê yekê hûn hewce ne ku saz bikin mysql-connector-net û paşê kodê bi vî rengî binivîse:
Koda ji bo daxwazên li bendê

#Задаем переменные для подключение к MySQL и само подключение
[string]$sMySQLUserName = 'UserName'
[string]$sMySQLPW = 'UserPassword'
[string]$sMySQLDB = 'db'
[string]$sMySQLHost = 'IP-address'
[void][System.Reflection.Assembly]::LoadWithPartialName("MySql.Data");
[string]$sConnectionString = "server="+$sMySQLHost+";port=3306;uid=" + $sMySQLUserName + ";pwd="+"'" + $sMySQLPW +"'"+ ";database="+$sMySQLDB;
#Open a Database connection
$oConnection = New-Object MySql.Data.MySqlClient.MySqlConnection($sConnectionString)
$Error.Clear()
try
{
$oConnection.Open()
}
catch
{
write-warning ("Could not open a connection to Database $sMySQLDB on Host $sMySQLHost. Error: "+$Error[0].ToString())
}
#The first query
# Get an instance of all objects need for a SELECT query. The Command object
$oMYSQLCommand = New-Object MySql.Data.MySqlClient.MySqlCommand;
# DataAdapter Object
$oMYSQLDataAdapter = New-Object MySql.Data.MySqlClient.MySqlDataAdapter;
# And the DataSet Object
$oMYSQLDataSet = New-Object System.Data.DataSet;
# Assign the established MySQL connection
$oMYSQLCommand.Connection=$oConnection;
# Define a SELECT query
$oMYSQLCommand.CommandText='query';
$oMYSQLDataAdapter.SelectCommand=$oMYSQLCommand;
# Execute the query
$count=$oMYSQLDataAdapter.Fill($oMYSQLDataSet, "data");
$result = $oMYSQLDataSet.Tables[0].Rows[0]["Count"];
write-host $result;

Di encama

Vê gotarê li Zabbix li mînakek hejmarên performansê (tiştên daneyê) nihêrî. Ev nêzîkatî dihêle ku rêvebiran di demek rast an piştî demek taybetî de di derheqê pirsgirêkên cûda de agahdar bibin. Bi vî rengî, ev nêzîkatî dihêle ku em di pêşerojê de rûdana pirsgirêkek krîtîk kêm bikin û xebata DBMS û serverê rawestînin, ku di encamê de hilberînê ji rawestandina pêvajoyên xebatê diparêze.
Gotara berê: Karê rûtîn bi databasa pergala agahdariyê 24×7 di MS SQL Server de

Çavkaniyên

» Zabbix 3.4
» Performance counters
» Navenda Performansê ya ji bo Azure SQL Database û SQL Server Database Engine
» SQL Lifestyle
» SQLSkills
» TechNet Microsoft
» Analîzkirina karanîna bîranînê
» Analîza Performansê
» Belgekirina SQL
» Têbînî li ser Windows

Source: www.habr.com

Add a comment