Mysql
 sql >> Base de Dados >  >> RDS >> Mysql

Por que uma consulta de inserção às vezes demora tanto para ser concluída?


Tenho notado o mesmo fenômeno em meus sistemas. As consultas que normalmente levam um milissegundo, de repente, levam de 1 a 2 segundos. Todos os meus casos são simples, instruções INSERT/UPDATE/REPLACE de tabela única --- não em nenhum SELECT. Nenhuma carga, travamento ou acúmulo de rosca é evidente.

Eu suspeitava que fosse devido à limpeza de páginas sujas, liberação de alterações no disco ou algum mutex oculto, mas ainda tenho que reduzi-lo.

Também descartado
  • Carga do servidor -- sem correlação com carga alta
  • Engine -- acontece com InnoDB/MyISAM/Memory
  • Cache de consulta MySQL -- acontece independentemente de estar ativado ou desativado
  • Rotações de registros -- sem correlação nos eventos

A única outra observação que tenho neste momento é derivada do fato de estar executando o mesmo banco de dados em várias máquinas. Eu tenho um aplicativo de leitura pesada, então estou usando um ambiente com replicação - a maior parte da carga está nos escravos. Percebi que mesmo havendo carga mínima no master, o fenômeno ocorre mais lá. Mesmo que eu não veja problemas de bloqueio, talvez seja o Innodb/Mysql tendo problemas com a simultaneidade (thread)? Lembre-se de que as atualizações no escravo serão de thread único.

MySQL Versão 5.1.48

Atualizar

Acho que tenho uma pista para o problema no meu caso. Em alguns dos meus servidores, notei esse fenômeno em mais do que nos outros. Vendo o que era diferente entre os diferentes servidores e ajustando as coisas, fui levado ao variável de sistema innodb do MySQL innodb_flush_log_at_trx_commit .

Achei o documento um pouco estranho de ler, mas innodb_flush_log_at_trx_commit pode assumir os valores de 1,2,0:
  • Para 1, o buffer de log é liberado para o arquivo de log para cada confirmação, e o arquivo de log é liberado para o disco para cada confirmação.
  • Para 2, o buffer de log é liberado para o arquivo de log a cada confirmação, e o arquivo de log é liberado para o disco aproximadamente a cada 1-2 segundos.
  • Para 0, o buffer de log é liberado para o arquivo de log a cada segundo, e o arquivo de log é liberado para o disco a cada segundo.

Efetivamente, na ordem (1,2,0), conforme relatado e documentado, você deve obter um desempenho crescente no comércio para aumentar o risco.

Dito isso, descobri que os servidores com innodb_flush_log_at_trx_commit=0 tiveram um desempenho pior (ou seja, com 10 a 100 vezes mais "atualizações longas") do que os servidores com innodb_flush_log_at_trx_commit=2 . Além disso, as coisas melhoraram imediatamente nas instâncias ruins quando mudei para 2 (observe que você pode alterá-lo rapidamente).

Então, minha pergunta é, qual é o seu definido? Observe que não estou culpando esse parâmetro, mas destacando que seu contexto está relacionado a esse problema.