Então, começamos a explorar o uso da captura de dados alterados em um de nossos bancos de dados de produção. Gostaríamos de saber a data e hora de cada alteração. Lendo passo a passo e tutoriais , etc., parece que a abordagem padrão é usar o LSN para se relacionar com a cdc.lsn_time_mapping
tabela do sistema. Essa abordagem funciona, mas não é muito direta nem eficiente quando falamos de centenas de milhares de alterações por dia.
Em um ambiente de teste, fiz o seguinte ajuste nas tabelas de controle de alterações. Emiti uma ALTER TABLE
instrução para adicionar uma coluna ao final chamado [__ChangeDateTime]
e tornei seu valor padrão GetDate()
. A abordagem parece funcionar, o controle de alterações ainda funciona normalmente, as datas e horas estão sendo capturadas. Mas mexer nas tabelas do sistema me deixa um pouco nervoso.
Se este não é um campo do sistema que a Microsoft adicionou desde o início , eles devem ter seus motivos. Como eles optaram pela abordagem LSN para cdc.lsn_time_mapping, estou me preparando para problemas ao criar meu próprio hack dessa maneira?
ATUALIZAR:
Descoberto durante o teste que GetDate() às vezes não é preciso o suficiente para nossas necessidades - várias alterações compartilhando o mesmo tempo. Recomende o uso de sysdatetime() e datetime2 para mover o valor para o nanossegundo. Opção para 2008+ apenas obviamente.
Lembre-se de que o CDC usa um agente de leitura de log para preencher a tabela de alterações. Por que isso é importante? Por esse mecanismo, as linhas aparecem nas tabelas de alteração de forma assíncrona com as alterações feitas nas tabelas base.
Na verdade, existem 3 pontos de tempo diferentes que podem ser registrados, em ordem cronológica inversa:
cdc.lsn_time_mapping
).Portanto, a primeira coisa é ter claro o que você deseja gravar. Normalmente, nos importaríamos com o número 2 ou com o número 3.
Se o mecanismo de mapeamento LSN (nº 2) não estiver funcionando bem o suficiente para você, a única alternativa compatível é adicionar uma coluna à tabela base e preenchê-la você mesmo (nº 3).
No que diz respeito à alteração das tabelas internas, por uma questão de política, acho melhor evitar hackear com as internas quando houver alternativas suportadas. A última coisa que você deseja é um importante sistema de produção caindo, precisando ligar para o suporte ao produto e ter o serviço negado por causa de algo assim. Não importa os problemas de potencialmente quebrar coisas (atualizações) ou ser quebrado porque foi inesperado (desligue o CDC e ligue-o novamente, conforme mencionado na outra resposta).
Um exemplo prático:
A única ressalva que eu daria é que essas tabelas são descartadas automaticamente quando o CDC é desabilitado. A coluna não é recriada automaticamente quando você a reativa
Inspirado na resposta de Gareth, aqui está uma versão mais curta. Isso não usa, o
DECLARE
que é ótimo se você precisar criar umVIEW
(DECLARE
não é permitido entrarVIEW
)Com base nas respostas anteriores, criei este script que examinará todas as tabelas CDC e exibirá o nome da tabela e a última atualização: