Ao tentar truncar um tabela no banco de dados, me deparei com o erro ORA-00054.
Este erro significa que você está tentando manipular algum objeto (digo objeto e não arquivo, pois pode tratar-se de um índice) que já está sendo utilizado por outro recurso. Gerando lock no objeto. Neste caso, era realmente um índice que estava com o status UNUSABLE, impedindo o funcionamento do comando TRUNCATE na tabela específica.
Vamos ver uma maneira de resolver tal problema.
1) Tentativa de realizar o truncate na tabela FIN_OUT do owner PROD
SQL> TRUNCATE TABLE PROD.FIN_OUT
2 /
TRUNCATE TABLE PROD.FIN_OUT
*
ERROR at line 1:
ORA-00054: resource busy and acquire with NOWAIT specified
2) Verificando os status dos índices
SQL> select distinct status from dba_indexes;
STATUS
--------
UNUSABLE
N/A
VALID
SQL> select owner, index_name from dba_indexes where status = 'UNUSABLE';
OWNER INDEX_NAME
------------------------------ ------------------------------
PROD IDX_FIN
VALID: índice válido
N/A: Índice para partition table
UNUSABLE: índice inutilizável (causando nosso problema)
3) Verificando se o objeto está lockado por outra sessão através da view v$locked_object
SQL> select substr(o.object_name,1,25) objeto,
l.session_id session_id,
l.oracle_username ora_user,
l.os_user_name os_user
from dba_objects o, v$locked_object l
where l.object_id = o.object_id
order by 1,3,4;
OBJETO SESSION_ID ORA_USER OS_USER
------------------------- ---------- ------------------------------ ---------------------------
FIN_OUT 5244 PROD root
Perceba que a sessão 5244 está lockando o objeto.
4) Com um SELECT simples na v$session, descobrimos que a sessão está inativa
SQL> select sid, SERIAL#, USERNAME, status from v$session where sid = 5244;
SID SERIAL# USERNAME STATUS
---------- ---------- ------------------------------ --------
5244 49767 PROD INACTIVE
5) Realizei o kill nesta sessão, eliminando-a do banco de dados.
SQL> alter system kill session '5244, 49767' immediate;
System altered.
6) Apliquei o rebuild online no índice que estava inutilizável.
SQL> alter index BR_PROD.IDX_FIN rebuild online;
Index altered.
SQL> select distinct status from dba_indexes;
STATUS
--------
N/A
VALID
Após atuação, consegui truncar minha tabela sem nenhum problema
SQL> TRUNCATE TABLE PROD.FIN_OUT;
Table truncated.
Por hoje é só, até o próximo artigo.