Uma publicação aqui no DBA.StackExchange ( Quais são as práticas recomendadas para os gatilhos manterem um número de revisão nos registros? ) Gerou uma pergunta interessante (pelo menos, interessante para mim) sobre o desempenho no MySQL.
O contexto é que queremos inserir um registro em uma tabela para cada linha que é atualizada. Antes da atualização da linha, queremos armazenar um valor anterior e incrementar uma das colunas (uma coluna "versão").
Se fizermos isso dentro de um gatilho, funcionará bem. Para o MySQL, os gatilhos são linha por linha , por isso seria uma solução fácil. Selecione os dados atualmente na tabela, insira-os na tabela de log e atualize a coluna "versão" nos novos dados.
No entanto, é possível mover essa lógica para um procedimento armazenado. Se você fizer isso, estará executando a inserção e incrementando a coluna "version" na tabela. A coisa toda seria definida com base.
Então, quando se trata de executar essa inserção, seria mais eficiente usar a abordagem de procedimento armazenado baseado em conjunto ou uma abordagem baseada em gatilho?
Esta pergunta é para o MySQL (já que possui gatilhos linha a linha), embora possa se aplicar a outros DBMSs de linha a linha.
fonte
Respostas:
Por uma questão de simplicidade, os gatilhos são o caminho a seguir para implementar qualquer tipo de rastreamento de alterações no banco de dados. No entanto, você precisa estar ciente do que acontece quando você usa gatilhos.
De acordo com a Programação de procedimentos armazenados do MySQL , a página 256, sob o cabeçalho "Trigger Overhead", diz o seguinte:
Uma explicação expandida da sobrecarga do acionador é fornecida nas páginas 529-531. O ponto de conclusão dessa seção afirma o seguinte:
Não mencionado no livro é outro fator ao usar gatilhos: Quando se trata de auditoria de log, lembre-se de onde você faz o log de dados. Digo isso porque, se você optar por fazer logon em uma tabela MyISAM, cada INSERT em uma tabela MyISAM produz um bloqueio de tabela completo durante o INSERT. Isso pode se tornar um gargalo sério em um ambiente de alto tráfego e alta transação. Além disso, se o gatilho estiver em uma tabela do InnoDB e você registrar alterações no MyISAM de dentro do gatilho, isso desativará secretamente a conformidade com ACID (ou seja, reduza as transações de bloco ao comportamento de confirmação automática), que não podem ser revertidas.
Ao usar gatilhos em tabelas do InnoDB e alterações de log
Dessa maneira, os logs de auditoria podem se beneficiar do COMMIT / ROLLBACK, como as tabelas principais.
Em relação ao uso de procedimentos armazenados, você teria que chamar minuciosamente o procedimento armazenado em todos os pontos do DML na tabela que está sendo rastreada. Pode-se facilmente perder as alterações de registro em face de dezenas de milhares de linhas de código de aplicativo. Colocar esse código em um gatilho elimina a localização de todas essas instruções DML.
EMBARGO
Dependendo da complexidade do gatilho, ele ainda pode ser um gargalo. Se você deseja reduzir gargalos no log de auditoria, há algo que você pode fazer. No entanto, isso exigirá uma pequena alteração na infraestrutura.
Usando hardware comum, crie mais dois servidores de banco de dados
Isso servirá para reduzir a E / S de gravação no banco de dados principal (MD) devido ao log de auditoria. Aqui está como você pode fazer isso:
Etapa 01) Ative o log binário no banco de dados principal.
Etapa 02) Usando um servidor barato, configure o MySQL (mesma versão que o MD) com o log binário ativado. Este será o DM. Replicação de instalação do MD para o DM.
Etapa 03) Usando um segundo servidor barato, configure o MySQL (mesma versão do MD) com o log binário desativado. Configure cada tabela de auditoria para usar --replicate-do-table . Isso será AU. Replicação de instalação do DM para o AU.
Etapa 04) mysqldump as estruturas da tabela do MD e carregue-a no DM e AU.
Etapa 05) Converta todas as tabelas de auditoria no MD para usar o mecanismo de armazenamento BLACKHOLE
Etapa 06) Converta todas as tabelas no DM e AU para usar o mecanismo de armazenamento BLACKHOLE
Etapa 07) Converta todas as tabelas de auditoria na AU para usar o mecanismo de armazenamento MyISAM
Quando terminar
O que isso faz é armazenar informações de auditoria em um servidor de banco de dados separado e também reduzir qualquer degradação de E / S de gravação que o MD normalmente teria.
fonte
Aqui está uma abordagem para executar esta atualização em massa.
Para este exemplo
Para criar table_A_Keys2Update, faça o seguinte:
Depois de preencher table_A_Keys2Update com os IDs cujo número de revisão precisa ser incrementado, execute o seguinte UPDATE JOIN para aumentar o número de revisão de todas as linhas cujo ID está em table_A e table_A_Keys2Update:
Essa consulta de uma linha pode substituir um gatilho e um procedimento armazenado.
Opcionalmente, você pode colocar essa consulta em um procedimento armazenado e chamá-lo, se desejar.
fonte