Dela via


Felsöka frågeprestanda i Azure Database for MySQL – flexibel server

GÄLLER FÖR: Azure Database for MySQL – Azure Database for MySQL – enskild server – flexibel server

Viktigt!

Azure Database for MySQL – enskild server är på väg att dras tillbaka. Vi rekommenderar starkt att du uppgraderar till en flexibel Azure Database for MySQL-server. Mer information om hur du migrerar till en flexibel Azure Database for MySQL-server finns i Vad händer med Azure Database for MySQL – enskild server?

Frågeprestanda kan påverkas av flera faktorer, så det är först viktigt att titta på omfattningen av de symptom som du upplever i din flexibla Azure Database for MySQL-serverinstans. Är till exempel frågeprestandan långsam för:

  • Alla frågor som körs på Azure Database for MySQL– flexibel serverinstans?
  • En specifik uppsättning frågor?
  • En specifik fråga?

Tänk också på att eventuella ändringar av strukturen eller underliggande data i tabellerna som du frågar efter kan påverka prestandan.

Aktivera loggningsfunktioner

Innan du analyserar enskilda frågor måste du definiera frågemått. Med den här informationen kan du implementera loggningsfunktioner på databasservern för att spåra frågor som överskrider ett tröskelvärde som du anger baserat på programmets behov.

Azure Database for MySQL – flexibel server, vi rekommenderar att du använder funktionen för långsam frågelogg för att identifiera frågor som tar längre tid än N sekunder att köra. När du har identifierat frågorna från loggen för långsamma frågor kan du använda MySQL-diagnostik för att felsöka dessa frågor.

Innan du kan börja spåra tidskrävande frågor behöver du aktivera parametern slow_query_log med hjälp av Azure-portalen eller Azure CLI. Med den här parametern aktiverad bör du också konfigurera värdet för parametern long_query_time för att ange hur många sekunder som frågor kan köra innan de identifieras som "långsamma" frågor. Standardvärdet för parametern är 10 sekunder, men du kan justera värdet för att uppfylla behoven i programmets serviceavtal.

Azure Database for MySQL – flexibel server – långsamt frågelogggränssnitt.

Loggen för långsamma frågor är ett bra verktyg för att spåra tidskrävande frågor, men det finns vissa scenarier där det kanske inte är effektivt. Till exempel loggen för långsamma frågor:

  • Påverkar prestanda negativt om antalet frågor är mycket högt eller om frågeuttrycket är mycket stort. Justera värdet för parametern i enlighet med detta long_query_time .
  • Kanske inte är till hjälp om du också har aktiverat parametern log_queries_not_using_index , som anger att loggfrågor förväntas hämta alla rader. Frågor som utför en fullständig indexgenomsökning drar nytta av ett index, men de loggas eftersom indexet inte begränsar antalet rader som returneras.

Hämtar information från loggarna

Loggar är tillgängliga i upp till sju dagar från det att de har skapats. Du kan lista och ladda ned långsamma frågeloggar via Azure-portalen eller Azure CLI. I Azure-portalen navigerar du till servern under Övervakning, väljer Serverloggar och väljer sedan nedåtpilen bredvid en post för att ladda ned loggarna som är associerade med datum och tid som du undersöker.

Azure Database for MySQL – flexibel server som hämtar data från loggarna.

Om dina långsamma frågeloggar dessutom är integrerade med Azure Monitor-loggar via diagnostikloggar kan du köra frågor i ett redigeringsprogram för att analysera dem ytterligare:

AzureDiagnostics
| where Resource == '<your server name>'
| where Category == 'MySqlSlowLogs'
| project TimeGenerated, Resource , event_class_s, start_time_t , query_time_d, sql_text_s
| where query_time_d > 10

Kommentar

Fler exempel för att komma igång med att diagnostisera långsamma frågeloggar via diagnostikloggar finns i Analysera loggar i Azure Monitor-loggar.

Följande ögonblicksbild visar ett exempel på en långsam fråga.

# Time: 2021-11-13T10:07:52.610719Z
# User@Host: root[root] @  [172.30.209.6]  Id: 735026
# Query_time: 25.314811  Lock_time: 0.000000 Rows_sent: 126  Rows_examined: 443308
use employees;
SET timestamp=1596448847;
select * from titles where DATE(from_date) > DATE('1994-04-05') AND title like '%senior%';;

Observera att frågan kördes på 26 sekunder, undersökte över 443 000 rader och returnerade 126 rader med resultat.

Vanligtvis bör du fokusera på frågor med höga värden för Query_time och Rows_examined. Men om du märker frågor med hög Query_time men bara några få Rows_examined, indikerar detta ofta förekomsten av en resursflaskhals. I dessa fall bör du kontrollera om det finns någon I/O-begränsning eller CPU-användning.

Profilera en fråga

När du har identifierat en specifik fråga som körs långsamt kan du använda kommandot EXPLAIN och profilering för att samla in mer information.

Kontrollera frågeplanen genom att köra följande kommando:

EXPLAIN <QUERY>

Kommentar

Mer information om hur du använder EXPLAIN-instruktioner finns i Använda EXPLAIN för att profilera frågeprestanda i Azure Database for MySQL – flexibel server.

Förutom att skapa en EXPLAIN-plan för en fråga kan du använda kommandot SHOW PROFILE, som gör att du kan diagnostisera körningen av instruktioner som har körts under den aktuella sessionen.

Om du vill aktivera profilering och profilera en specifik fråga i en session kör du följande uppsättning kommandon:

SET profiling = 1;
<QUERY>;
SHOW PROFILES;
SHOW PROFILE FOR QUERY <X>;

Kommentar

Profilering av enskilda frågor är endast tillgängligt i en session och historiska instruktioner kan inte profileras.

Nu ska vi titta närmare på hur du använder dessa kommandon för att profilera en fråga. Först aktiverar du profilering för den aktuella sessionen och kör SET PROFILING = 1 kommandot:

mysql> SET PROFILING = 1;
Query OK, 0 rows affected, 1 warning (0.00 sec)

Kör sedan en suboptimal fråga som utför en fullständig tabellgenomsökning:

mysql> select * from sbtest8 where c like '%99098187165%';
+----+---------+-------------------------------------------------------------------------------------------------------------------------+-------------------------------------------------------------+
| id | k       | c                                                                                                                       | pad                                                         |
+----+---------+-------------------------------------------------------------------------------------------------------------------------+-------------------------------------------------------------+
| 10 | 5035785 | 81674956652-89815953173-84507133182-62502329576-99098187165-62672357237-37910808188-52047270287-89115790749-78840418590 | 91637025586-81807791530-84338237594-90990131533-07427691758 |
+----+---------+-------------------------------------------------------------------------------------------------------------------------+-------------------------------------------------------------+
1 row in set (27.60 sec)

Visa sedan en lista över alla tillgängliga frågeprofiler genom att SHOW PROFILES köra kommandot:

mysql> SHOW PROFILES;
+----------+-------------+----------------------------------------------------+
| Query_ID | Duration    | Query                                              |
+----------+-------------+----------------------------------------------------+
|        1 | 27.59450000 | select * from sbtest8 where c like '%99098187165%' |
+----------+-------------+----------------------------------------------------+
1 row in set, 1 warning (0.00 sec)

Kör slutligen kommandot för att visa profilen för fråga 1 SHOW PROFILE FOR QUERY 1 .

mysql> SHOW PROFILE FOR QUERY 1;
+----------------------+-----------+
| Status               | Duration  |
+----------------------+-----------+
| starting             |  0.000102 |
| checking permissions |  0.000028 |
| Opening tables       |  0.000033 |
| init                 |  0.000035 |
| System lock          |  0.000018 |
| optimizing           |  0.000017 |
| statistics           |  0.000025 |
| preparing            |  0.000019 |
| executing            |  0.000011 |
| Sending data         | 27.594038 |
| end                  |  0.000041 |
| query end            |  0.000014 |
| closing tables       |  0.000013 |
| freeing items        |  0.000088 |
| cleaning up          |  0.000020 |
+----------------------+-----------+
15 rows in set, 1 warning (0.00 sec)

Lista de mest använda frågorna på databasservern

När du felsöker frågeprestanda är det bra att förstå vilka frågor som oftast körs på din azure database for MySQL– flexibel serverinstans. Du kan använda den här informationen för att mäta om någon av de viktigaste frågorna tar längre tid än vanligt att köra. Dessutom kan en utvecklare eller DBA använda den här informationen för att identifiera om någon fråga har en plötslig ökning av antalet frågekörningar och varaktighet.

Kör följande fråga om du vill visa de 10 vanligaste frågorna mot din flexibla Azure Database for MySQL-serverinstans:

SELECT digest_text AS normalized_query,
 count_star AS all_occurrences,
 Concat(Round(sum_timer_wait / 1000000000000, 3), ' s') AS total_time,
 Concat(Round(min_timer_wait / 1000000000000, 3), ' s') AS min_time,
 Concat(Round(max_timer_wait / 1000000000000, 3), ' s') AS max_time,
 Concat(Round(avg_timer_wait / 1000000000000, 3), ' s') AS avg_time,
 Concat(Round(sum_lock_time / 1000000000000, 3), ' s') AS total_locktime,
 sum_rows_affected AS sum_rows_changed,
 sum_rows_sent AS sum_rows_selected,
 sum_rows_examined AS sum_rows_scanned,
 sum_created_tmp_tables,
 sum_select_scan,
 sum_no_index_used,
 sum_no_good_index_used
FROM performance_schema.events_statements_summary_by_digest
ORDER BY sum_timer_wait DESC LIMIT 10;

Kommentar

Använd den här frågan för att jämföra de vanligaste frågorna på databasservern och avgöra om de vanligaste frågorna har ändrats eller om några befintliga frågor i det ursprungliga riktmärket har ökat under körningstiden.

Lista de 10 dyraste frågorna efter total körningstid

Utdata från följande fråga innehåller information om de 10 vanligaste frågorna som körs mot databasservern och deras antal körningar på databasservern. Den innehåller också annan användbar information, till exempel svarstider för frågor, deras låstider, antalet temporära tabeller som skapats som en del av frågekörningen osv. Använd det här frågeutdata för att hålla reda på de viktigaste frågorna i databasen och ändringar i faktorer som svarstider, vilket kan tyda på en chans att finjustera frågan ytterligare för att undvika framtida risker.

SELECT REPLACE(event_name, 'statement/sql/', '') AS statement, 
 count_star AS all_occurrences , 
 Concat(Round(sum_timer_wait / 1000000000000, 2), ' s') AS total_latency, 
 Concat(Round(avg_timer_wait / 1000000000000, 2), ' s') AS avg_latency, 
 Concat(Round(sum_lock_time / 1000000000000, 2), ' s') AS total_lock_time  , 
 sum_rows_affected AS sum_rows_changed, 
 sum_rows_sent AS  sum_rows_selected, 
 sum_rows_examined AS  sum_rows_scanned, 
 sum_created_tmp_tables,  sum_created_tmp_disk_tables, 
 IF(sum_created_tmp_tables = 0, 0, Concat( Truncate(sum_created_tmp_disk_tables / 
 sum_created_tmp_tables * 100, 0))) AS 
 tmp_disk_tables_percent, 
 sum_select_scan, 
 sum_no_index_used, 
 sum_no_good_index_used 
FROM performance_schema.events_statements_summary_global_by_event_name 
WHERE event_name LIKE 'statement/sql/%' 
 AND count_star > 0 
ORDER BY sum_timer_wait DESC 
LIMIT 10;

Övervaka InnoDB-skräpinsamling

När InnoDB-skräpinsamling blockeras eller fördröjs kan databasen utveckla en betydande rensningsfördröjning som kan påverka lagringsanvändningen och frågeprestanda negativt.

HLL (InnoDB Rollback Segment History List Length) mäter antalet ändringsposter som lagras i ångra-loggen. Ett växande HLL-värde anger att InnoDB:s skräpinsamlingstrådar (rensningstrådar) inte håller jämna steg med skrivarbetsbelastningen eller att rensning blockeras av en tidskrävande fråga eller transaktion.

För långa fördröjningar i skräpinsamling kan få allvarliga, negativa konsekvenser:

  • InnoDB-systemtabellområdet expanderar, vilket påskyndar tillväxten av den underliggande lagringsvolymen. Ibland kan systemtabellområdet svälla med flera terabyte till följd av en blockerad rensning.
  • Borttagna poster tas inte bort i tid. Detta kan göra att InnoDB-tabellytor växer och förhindrar att motorn återanvänder lagringen som används av dessa poster.
  • Prestandan för alla frågor kan försämras och processoranvändningen kan öka på grund av tillväxten av InnoDB-lagringsstrukturer.

Därför är det viktigt att övervaka HLL-värden, mönster och trender.

Hitta HLL-värden

Du hittar HLL-värdet genom att köra kommandot show engine innodb status. Värdet visas i utdata under rubriken TRANSAKTIONER:

mysql> show engine innodb status\G 
*************************** 1. row *************************** 
 
(...) 
 
------------ 
TRANSACTIONS 
------------ 
Trx id counter 52685768 
Purge done for trx's n:o < 52680802 undo n:o < 0 state: running but idle 
History list length 2964300 
 
(...) 

Du kan också fastställa HLL-värdet genom att fråga tabellen information_schema.innodb_metrics:

mysql> select count from information_schema.innodb_metrics  
    -> where name = 'trx_rseg_history_len'; 
+---------+ 
|  count  | 
+---------+ 
| 2964300 | 
+---------+ 
1 row in set (0.00 sec)

Tolka HLL-värden

När du tolkar HLL-värden bör du överväga riktlinjerna som anges i följande tabell:

Värde Anteckningar
Mindre än ~10 000 Normalvärden som anger att skräpinsamlingen inte hamnar efter.
Mellan ~10 000 och ~1 000 000 Dessa värden anger en mindre fördröjning i skräpinsamlingen. Sådana värden kan vara acceptabla om de förblir stabila och inte ökar.
Större än ~1 000 000 Dessa värden bör undersökas och kan kräva korrigerande åtgärder

Hantera överdrivna HLL-värden

Om HLL visar stora toppar eller uppvisar ett mönster av periodisk tillväxt undersöker du frågorna och transaktionerna som körs på din flexibla Azure Database for MySQL-serverinstans omedelbart. Sedan kan du lösa eventuella arbetsbelastningsproblem som kan förhindra förloppet för skräpinsamlingsprocessen. Databasen förväntas inte vara fri från rensningsfördröjning, men du får inte låta fördröjningen växa okontrollerat.

Om du till exempel vill hämta transaktionsinformation från information_schema.innodb_trx tabellen kör du följande kommandon:

select * from information_schema.innodb_trx  
order by trx_started asc\G

Informationen i trx_started kolumnen hjälper dig att beräkna transaktionsåldern.

mysql> select * from information_schema.innodb_trx  
    -> order by trx_started asc\G 
*************************** 1. row *************************** 
                    trx_id: 8150550 
                 trx_state: RUNNING 
               trx_started: 2021-11-13 20:50:11 
     trx_requested_lock_id: NULL 
          trx_wait_started: NULL 
                trx_weight: 0 
       trx_mysql_thread_id: 19 
                 trx_query: select * from employees where DATE(hire_date) > DATE('1998-04-05') AND first_name like '%geo%';
(…) 

Information om aktuella databassessioner, inklusive den tid som spenderas i sessionens aktuella tillstånd, finns information_schema.processlist i tabellen. Följande utdata visar till exempel en session som aktivt har kört en fråga under de senaste 1462 sekunderna:

mysql> select user, host, db, command, time, info  
    -> from information_schema.processlist  
    -> order by time desc\G 
*************************** 1. row *************************** 
   user: test 
   host: 172.31.19.159:38004 
     db: employees 
command: Query 
   time: 1462 
   info: select * from employees where DATE(hire_date) > DATE('1998-04-05') AND first_name like '%geo%';
 
(...) 

Rekommendationer

  • Kontrollera att databasen har tillräckligt med resurser allokerade för att köra dina frågor. Ibland kan du behöva skala upp instansstorleken för att få fler CPU-kärnor och ytterligare minne för din arbetsbelastning.

  • Undvik stora eller långvariga transaktioner genom att dela upp dem i mindre transaktioner.

  • Konfigurera innodb_purge_threads enligt din arbetsbelastning för att förbättra effektiviteten för bakgrundsrensningsåtgärder.

    Kommentar

    Testa eventuella ändringar i den här servervariabeln för varje miljö för att mäta ändringen av motorbeteendet.

  • Använd aviseringar på "Host CPU Percent", "Host Memory Percent" och "Total Connections" så att du får meddelanden om systemet överskrider något av de angivna tröskelvärdena.

  • Använd Query Performance Insights eller Azure-arbetsböcker för att identifiera eventuella problematiska eller långsamt körande frågor och sedan optimera dem.

  • För produktionsdatabasservrar samlar du in diagnostik med jämna mellanrum för att säkerställa att allt fungerar smidigt. Annars kan du felsöka och lösa eventuella problem som du identifierar.

Nästa steg

Om du vill hitta peer-svar på dina viktigaste frågor eller för att publicera eller besvara en fråga går du till Stack Overflow.