Vamos falar desse wait event que por algumas vezes aparece no nosso dia a dia e não é difícil de se resolver, o “enq: TM Contention”.
Normalmente você vai se deparar com ele durante operações DML em tabelas que possuam uma relação entre si, e suas respectivas FKs não estejam indexadas.
Para encontrar quais são as tabelas, basta executar o select abaixo:
SELECT l.sid, s.blocking_session blocker, s.event, l.type, l.lmode, l.request, o.object_name, o.object_type FROM v$lock l, dba_objects o, v$session s WHERE upper(s.username) = upper('&User') AND l.id1 = o.object_id (+) AND l.sid = s.sid ORDER BY sid, type;
A execução do select acima vai lhe retornar alguma coisa similar a imagem abaixo:
Agora é só avaliar a estrutura das tabelas envolvidas para identificar a FK em questão (que não esteja indexada), feito isso crie um índice e o problema não deve voltar a ocorrer.
Caso você queira fazer um levantamento mais abrangente pode executar o select abaixo, para investigar todos os objetos de um determinado usuário:
SELECT * FROM ( SELECT c.table_name, cc.column_name, cc.position column_position FROM user_constraints c, user_cons_columns cc WHERE c.constraint_name = cc.constraint_name AND c.constraint_type = 'R' MINUS SELECT i.table_name, ic.column_name, ic.column_position FROM user_indexes i, user_ind_columns ic WHERE i.index_name = ic.index_name ) ORDER BY table_name, column_position;
Caso haja alguma tabela nesta situação que falamos, o resultado vai ser algo similar a imagem abaixo:
Forte abraço e até a próxima!