Eu estava executando alguns testes simples em um editor e assinante na mesma instância:
- Eu inseri 50.000 linhas em um artigo publicado e os dados foram enviados corretamente para o assinante.
- Excluí inadvertidamente o 49.985º registro do assinante (mas não percebi na época)
- Excluí 50.000 linhas do artigo publicado
Enquanto observava o tamanho da tabela de assinantes, notei que a contagem de linhas caía quase para zero e depois voltava para 50.000. As exclusões começariam a ser executadas novamente, a contagem de linhas cairia e, em seguida, voltaria para 50.000. Isso continuou acontecendo repetidamente.
Executei um rastreamento padrão e vi todas as exclusões funcionando normalmente. Depois que estava quase completo, esta declaração apareceu:
IF @@TRANCOUNT > 0 ROLLBACK
Então eu modifiquei o rastreamento para incluir mensagens de erro e vi isso:
The row was not found at the Subscriber when applying the replicated command.
Portanto, parece que quando o agente de distribuição está executando todas as exclusões uma a uma, o processo ainda está incluído em uma transação (o DELETE original era uma linha). Se houver um erro, ele executa um ROLLBACK e começa novamente.
Minhas perguntas:
- Existe uma maneira padrão de sair do loop?
- Seria aceitável recriar a linha ausente para que o processo pudesse ser concluído?
- O que você faz se isso acontecer na produção? Acho que não é bem uma pergunta. Mas isso parece que um erro simples pode ter algumas complicações bastante sérias, a menos que a replicação seja monitorada com muito cuidado.
O erro é causado pelo código no procedimento armazenado de exclusão personalizado para cada artigo:
Se nenhuma linha for excluída, um procedimento especial será chamado e a transação será revertida.
Para evitar isso, criei um script pós-instantâneo que altera todos os procedimentos armazenados de replicação de exclusão/atualização e registra o erro em uma tabela.