MySQL için Microsoft'un “SQL Server Profilcisi” gibi bir araç var mı? [kapalı]


43

MySQL üzerinde geliştirirken, bir profil oluşturucuyu ateşlemeyi gerçekten çok özlüyorum. Ben bulmak SQLyog Query Analyzer için yeterince iyi bir yedek ama bir araç bulamadık SQL profilcisine gibi çalışır.

Microsoft'un SQL Profilerini görmemiş olan MySQL halkı için , işte ekran görüntüsü

profiler sql

Önceki işimde, SQL Profiler'ı zıplayan ve hatta yığın izleri veren bir aracımız vardı.

altiris profiler

Bahsettiğim aletler gibi MySQL ile çalışan herhangi bir araç bilen var mı?

(FYI, Altiris Profiler'ın MySQL ile çalışmasını sağlayabilirim, ancak Windows'un daha fazla çalıştırılmasını da içerecektir.

Yanıtlar:


17

MySQL hiçbir zaman Query Profiling ile gelmedi. Şimdi MySQL, Oracle tarafından büyükbaba tarafından kabul edildiğine göre, durumun böyle devam edeceğini biliyorum.

Ancak, tüm umutlar kaybolmaz.

2007'den beri Percona, bir Geliştirici ve DBA'nın Sorgu Profilleri dahil olmak üzere istediği her şey için kesinlikle harika araçlar buldu.

Olarak bilinen araçların Percona ilk seti, MAATKIT , MySQL ciddi bir kullanıcı için bir bölge oluşturdu. Gibi birçok şey özellikleri :

  • Sorgu Profil Oluşturma
  • Çoğaltma kalp atışı
  • Çoğaltma Slave Yönetimi
  • Tablo Sağlama Toplamı ve Senkronizasyon

Percona son zamanlarda MAATKIT'i bugün Percona Araç Takımı olarak bilinen daha güncel bir araç seti haline getirdi . Bu araçlar, ciddi MySQL kullanıcılarının etkinlik alanlarını genişleterek MAATKIT’in kaldığı yerden kaldı:

  • Yabancı Anahtar Hata Kontrolü
  • Çevrimiçi Şema Değiştirme
  • Görsel Açıklama Planları
  • ve dahası ...

Orijinal soruya geri dönersek, sorgu profilleme için araçlar

İşte bu araçlardan birini kullanarak gelebilecek zengin bilginin bir örneği:

Bir müşterinin, her 20 dakikada bir en kötü 20 sorguyu rapor etmesi için mk-query-digest uygulaması yapmasına yardımcı oldum. Bu YouTube videosundan bir fikrim var . Müşteri herhangi bir kötü sorgunun çıktısını memcached'e hareket ettirir ve böylece sorgunun veri tabanına zarar verme sıklığını azaltır.

İşte mk-query-digest'i çağırmak için yaptığım betiği (sadece işlem listesini incelemek)

#!/bin/sh

RUNFILE=/tmp/QueriesAreBeingDigested.txt
if [ -f ${RUNFILE} ] ; then exit ; fi

MKDQ=/usr/local/sbin/mk-query-digest
RUNTIME=${1}
COPIES_TO_KEEP=${2}
DBVIP=${3}

WHICH=/usr/bin/which
DATE=`${WHICH} date`
ECHO=`${WHICH} echo`
HEAD=`${WHICH} head`
TAIL=`${WHICH} tail`
AWK=`${WHICH} awk`
SED=`${WHICH} sed`
CAT=`${WHICH} cat`
WC=`${WHICH} wc`
RM=`${WHICH} rm | ${TAIL} -1 | ${AWK} '{print $1}'`
LS=`${WHICH} ls | ${TAIL} -1 | ${AWK} '{print $1}'`

HAS_THE_DBVIP=`/sbin/ip addr show | grep "scope global secondary" | grep -c "${DBVIP}"`
if [ ${HAS_THE_DBVIP} -eq 1 ] ; then exit ; fi

DT=`${DATE} +"%Y%m%d_%H%M%S"`
UNIQUETAG=`${ECHO} ${SSH_CLIENT}_${SSH_CONNECTION}_${DT} | ${SED} 's/\./ /g' | ${SED} 's/ //g'`

cd /root/QueryDigest
OUTFILE=QP_${DT}.txt
HOSTADDR=${DBVIP}
${MKDQ} --processlist h=${HOSTADDR},u=queryprofiler,p=queryprofiler --run-time=${RUNTIME} > ${OUTFILE}

#
# Rotate out Old Copies
#

QPFILES=QPFiles.txt
QPFILES2ZAP=QPFiles2Zap.txt
${LS} QP_[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]_[0-9][0-9][0-9][0-9][0-9][0-9].txt > ${QPFILES}

LINECOUNT=`${WC} -l < ${QPFILES}`
if [ ${LINECOUNT} -gt ${COPIES_TO_KEEP} ]
then
        (( DIFF = LINECOUNT - COPIES_TO_KEEP ))
        ${HEAD} -${DIFF} < ${QPFILES} > ${QPFILES2ZAP}
        for QPFILETOZAP in `${CAT} ${QPFILES2ZAP}`
        do
                ${RM} ${QPFILETOZAP}
        done
fi

rm -f ${QPFILES2ZAP}
rm -f ${QPFILES}
rm -f ${RUNFILE}

Mk-query-digest kullanarak mysql'e bağlanmak için yaptığım kullanıcı

GRANT PROCESS ON *.* TO 'queryprofiler'@'%' IDENTIFIED BY 'queryprofiler';

En son 144 kopyayı tutan 48 saniyede bir (10 saniyeden az) her 20 dakikada bir koştuğum crontab.

*/20 * * * * /root/QueryDigest/ExecQueryDigest.sh 1190s 144 10.1.1.8

İnanılmaz kısım: mk-query-digest'in çıktısı

İşte 1190 saniye boyunca 2011-12-28 11:20:00 koşturan bir profil (20 dakika daha az 10 saniye)

Son 22 satır

# Rank Query ID           Response time    Calls   R/Call     Item
# ==== ================== ================ ======= ========== ====
#    1 0x5E994008E9543B29    40.3255 11.2%     101   0.399263 SELECT schedule_occurrence schedule_eventschedule schedule_event schedule_eventtype schedule_event schedule_eventtype schedule_occurrence.start
#    2 0x392F6DA628C7FEBD    33.9181  9.4%      17   1.995184 SELECT mt_entry mt_objecttag
#    3 0x6C6318E56E149036    26.4695  7.3%     102   0.259505 SELECT schedule_occurrence schedule_eventschedule schedule_event schedule_eventtype schedule_event schedule_eventtype schedule_occurrence.start
#    4 0x00F66961DAE6FFB2    25.5472  7.1%      55   0.464495 SELECT mt_entry mt_placement mt_category
#    5 0x99E13015BFF1E75E    22.3618  6.2%     199   0.112371 SELECT mt_entry mt_objecttag
#    6 0x84DD09F0FC444677    22.3516  6.2%      39   0.573118 SELECT mt_entry
#    7 0x440EBDBCEDB88725    21.1817  5.9%      36   0.588380 SELECT mt_entry
#    8 0x8D258C584B858811    17.2402  4.8%      37   0.465951 SELECT mt_entry mt_placement mt_category
#    9 0x4E2CB0F4CAFD1400    16.9768  4.7%      40   0.424419 SELECT mt_entry mt_placement mt_category
#   10 0x377E0D0898266FDD    16.6979  4.6%     150   0.111319 SELECT polls_pollquestion mt_category
#   11 0x3B9686D98BB8E054    16.2089  4.5%      32   0.506529 SELECT mt_entry mt_objecttag mt_tag
#   12 0x97F670B604A85608    15.6158  4.3%      34   0.459287 SELECT mt_entry mt_placement mt_category
#   13 0x3F5557DA231225EB    14.4309  4.0%      36   0.400859 SELECT mt_entry mt_placement mt_category
#   14 0x191D660A10738896    13.1220  3.6%      31   0.423290 SELECT mt_entry mt_placement mt_category
#   15 0xF88F7421DD88036D    12.1261  3.4%      61   0.198788 SELECT mt_entry mt_blog mt_objecttag mt_tag mt_author
#   16 0xA909BF76E7051792    10.3971  2.9%      53   0.196172 SELECT mt_entry mt_objecttag mt_tag
#   17 0x3D42D07A335ED983     9.1424  2.5%      20   0.457121 SELECT mt_entry mt_placement mt_category
#   18 0x59F43B57DD43F2BD     9.0533  2.5%      21   0.431111 SELECT mt_entry mt_placement mt_category
#   19 0x7961BD4C76277EB7     8.5564  2.4%      47   0.182052 INSERT UNION UPDATE UNION mt_session
#   20 0x173EB4903F3B6DAC     8.5394  2.4%      22   0.388153 SELECT mt_entry mt_placement mt_category

Bunun, Sorgu Tepki Süresi'ne göre en kötü 20 sorguyu içeren listenin, sorgunun arandığı Zaman sayısına bölündüğüne dikkat edin.

Query ID # 1'e bakarsak, 0x5E994008E9543B29yani Query ID'yi çıktı dosyasında buluruz ve işte o belirli sorgu için rapor:

# Query 1: 0.09 QPS, 0.03x concurrency, ID 0x5E994008E9543B29 at byte 0 __
# This item is included in the report because it matches --limit.
#              pct   total     min     max     avg     95%  stddev  median
# Count          4     101
# Exec time      7     40s   303ms      1s   399ms   992ms   198ms   293ms
# Lock time      0       0       0       0       0       0       0       0
# Users                  1      mt
# Hosts                101 10.64.95.73:33750 (1), 10.64.95.73:34452 (1), 10.64.95.73:38440 (1)... 97 more
# Databases              1     mt1
# Time range 1325089201 to 1325090385
# bytes          0 273.60k   2.71k   2.71k   2.71k   2.62k       0   2.62k
# id             4 765.11M   7.57M   7.58M   7.58M   7.29M    0.12   7.29M
# Query_time distribution
#   1us
#  10us
# 100us
#   1ms
#  10ms
# 100ms  ################################################################
#    1s  ######
#  10s+
# Tables
#    SHOW TABLE STATUS FROM `mt1` LIKE 'schedule_occurrence'\G
#    SHOW CREATE TABLE `mt1`.`schedule_occurrence`\G
#    SHOW TABLE STATUS FROM `mt1` LIKE 'schedule_eventschedule'\G
#    SHOW CREATE TABLE `mt1`.`schedule_eventschedule`\G
#    SHOW TABLE STATUS FROM `mt1` LIKE 'schedule_event'\G
#    SHOW CREATE TABLE `mt1`.`schedule_event`\G
#    SHOW TABLE STATUS FROM `mt1` LIKE 'schedule_eventtype'\G
#    SHOW CREATE TABLE `mt1`.`schedule_eventtype`\G
#    SHOW TABLE STATUS FROM `schedule_occurrence` LIKE 'start'\G
#    SHOW CREATE TABLE `schedule_occurrence`.`start`\G
# EXPLAIN
SELECT `schedule_occurrence`.`id`, `schedule_occurrence`.`schedule_id`, `schedule_occurrence`.`event_id`, `schedule_occurrence`.`start`, `schedule_occurrence`.`end`, `schedule_occurrence`.`cancelled`, `schedule_occurrence`.`original_start`, `schedule_occurrence`.`original_end`, `schedule_occurrence`.`all_day`, `schedule_occurrence`.`ongoing`, `schedule_occurrence`.`featured`, `schedule_eventschedule`.`id`, `schedule_eventschedule`.`event_id`, `schedule_eventschedule`.`start`, `schedule_eventschedule`.`end`, `schedule_eventschedule`.`all_day`, `schedule_eventschedule`.`ongoing`, `schedule_eventschedule`.`min_date_calculated`, `schedule_eventschedule`.`max_date_calculated`, `schedule_eventschedule`.`rule`, `schedule_eventschedule`.`end_recurring_period`, `schedule_eventschedule`.`textual_description`, `schedule_event`.`id`, `schedule_event`.`title`, `schedule_event`.`slug`, `schedule_event`.`description`, `schedule_event`.`host_id`, `schedule_event`.`cost`, `schedule_event`.`age_restrictions`, `schedule_event`.`more_info`, `schedule_event`.`photo_id`, `schedule_event`.`contact_email`, `schedule_event`.`event_type_id`, `schedule_event`.`featured`, `schedule_event`.`staff_pick`, `schedule_event`.`futuremost`, `schedule_event`.`creator_id`, `schedule_event`.`created_on`, `schedule_event`.`allow_comments`, `schedule_event`.`mt_entry`, `schedule_eventtype`.`id`, `schedule_eventtype`.`parent_id`, `schedule_eventtype`.`name`, `schedule_eventtype`.`slug`, `schedule_eventtype`.`lft`, `schedule_eventtype`.`rght`, `schedule_eventtype`.`tree_id`, `schedule_eventtype`.`level`, T5.`id`, T5.`title`, T5.`slug`, T5.`description`, T5.`host_id`, T5.`cost`, T5.`age_restrictions`, T5.`more_info`, T5.`photo_id`, T5.`contact_email`, T5.`event_type_id`, T5.`featured`, T5.`staff_pick`, T5.`futuremost`, T5.`creator_id`, T5.`created_on`, T5.`allow_comments`, T5.`mt_entry`, T6.`id`, T6.`parent_id`, T6.`name`, T6.`slug`, T6.`lft`, T6.`rght`, T6.`tree_id`, T6.`level` FROM `schedule_occurrence` INNER JOIN `schedule_eventschedule` ON (`schedule_occurrence`.`schedule_id` = `schedule_eventschedule`.`id`) INNER JOIN `schedule_event` ON (`schedule_eventschedule`.`event_id` = `schedule_event`.`id`) INNER JOIN `schedule_eventtype` ON (`schedule_event`.`event_type_id` = `schedule_eventtype`.`id`) INNER JOIN `schedule_event` T5 ON (`schedule_occurrence`.`event_id` = T5.`id`) INNER JOIN `schedule_eventtype` T6 ON (T5.`event_type_id` = T6.`id`) WHERE (EXTRACT(MONTH FROM `schedule_occurrence`.`start`) = 8 AND EXTRACT(DAY FROM `schedule_occurrence`.`start`) = 6 AND `schedule_occurrence`.`start` BETWEEN '2011-01-01 00:00:00' and '2011-12-31 23:59:59.99') ORDER BY `schedule_occurrence`.`ongoing` ASC, `schedule_occurrence`.`all_day` DESC, `schedule_occurrence`.`start` ASC\G

Histogram metne dayalı olmasına rağmen, bazen 1 saniyeden uzun süre ve çoğu zaman 0.01 ile 0.1 saniye arasında çalışan sorgunun genel performansının doğru bir resmini verir. Buradan, sorguya yeniden bakılarak, sorgu sonuçlarını memcached içine yerleştirerek, eksik veya kapsayan dizinleri ekleyerek vb.

SONUÇ

IMHO Percona, profilleme araçlarını Windows GUI'ye yerleştirirse, kolayca Microsoft'un SQL Server Profilcisi'ne rakip olur.

Savunma dinleniyor


IMHO JetProfiler, Percona Tools'un grafiksel olarak birleştirildiği gibi görünüyor. Her birinin birbiri üzerine nüansları var. Linux kullanıcıları ve komut satırı kullanıcıları Percona Tools veya MAATKIT'ten memnun kalacaklardır. JetProfiler, DB derinlemesine sahip olmanızın yanı sıra emrinizde bir MONyog'un Windows grafik avantajını ortadan kaldırır.
RolandoMySQLDBA 22


5

Hayır, böyle bir araç yok.


Kabul. Çoğu MySQL geliştiricisinin / yöneticisinin Microsoft SQL Server ile hiç bu kadar zaman geçirmediğini ve MS yığınının geliştirme için ne kadar inanılmaz olduğunu anlamadıklarını öğrendim. Gördüğüm her MySQL sorgu aracı sorgulamaya dayanıyor, ancak SQL Server gerçek zamanlı olarak veritabanıyla olan her şeyi izlemenize izin veriyor. SQL Server Profiler'in detaylarına yaklaşacak hiçbir şey yok çünkü MySQL bunu desteklemiyor.
parleer

4

GUI MySQL araçlarıyla birleştirilmiş MySQL Sorgu Profilcisi , muhtemelen SQL Server Profilcisi aracına ulaşabileceğiniz kadar yakındır.


2
Ah, orada GUI yok ...
Sam Saffron

Daha da kötüsü, hala trafik geçmişini göstermiyor. Vay canına, Microsoft bu konudaki çoraplarını Oracle'dan alıyor!

4

Bulduğum en iyi çözümler, yavaş sorgu günlüğünün bir kombinasyonunu kullanmak (Profiler'e göre daha kötüdür) ve sadece 3306 numaralı bağlantı noktasında Wireshark'ı çalıştırmak ( Profiler'e kıyasla gerçekten berbat ve kazandı. Bağlantıları şifreliyorsanız çalışmayın).

Ayrıca, sys.dm_exec_sessions ve sys.dm_exec_requests (bir miktar sys.dm_exec_sql_text eklenmiş) ile azaltılmış bir kombinasyonuna benzeyen SHOW FULL PROCESSLIST de var.





Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.