ORA-00054: ressource occupée et acquisition avec NOWAIT spécifié ou expiration du délai

Pourquoi est-ce que je reçois cette erreur de firebase database lorsque je mets à jour une table?

ERREUR à la ligne 1: ORA-00054: ressource occupée et acquisition avec NOWAIT spécifié ou expiration du délai

Votre table est déjà verrouillée par une requête. Comme vous avez exécuté “select for update” et que vous n’avez pas encore validé / annulé et que vous avez à nouveau activé la requête de sélection. Effectuez un commit / rollback avant d’exécuter votre requête.

D’ici ORA-00054: ressource occupée et acquiert avec NOWAIT spécifié

Vous pouvez également rechercher le SQL, le nom d’utilisateur, la machine, les informations de port et accéder au processus réel qui contient la connexion.

SELECT O.OBJECT_NAME, S.SID, S.SERIAL#, P.SPID, S.PROGRAM,S.USERNAME, S.MACHINE,S.PORT , S.LOGON_TIME,SQ.SQL_FULLTEXT FROM V$LOCKED_OBJECT L, DBA_OBJECTS O, V$SESSION S, V$PROCESS P, V$SQL SQ WHERE L.OBJECT_ID = O.OBJECT_ID AND L.SESSION_ID = S.SID AND S.PADDR = P.ADDR AND S.SQL_ADDRESS = SQ.ADDRESS; 

Veuillez tuer la session Oracle

Utilisez la requête ci-dessous pour vérifier les informations de session actives

 SELECT O.OBJECT_NAME, S.SID, S.SERIAL#, P.SPID, S.PROGRAM, SQ.SQL_FULLTEXT, S.LOGON_TIME FROM V$LOCKED_OBJECT L, DBA_OBJECTS O, V$SESSION S, V$PROCESS P, V$SQL SQ WHERE L.OBJECT_ID = O.OBJECT_ID AND L.SESSION_ID = S.SID AND S.PADDR = P.ADDR AND S.SQL_ADDRESS = SQ.ADDRESS; 

tuer comme

 alter system kill session 'SID,SERIAL#'; 

(Par exemple, alter system kill session '13,36543' 😉

Référence http://abeytom.blogspot.com/2012/08/finding-and-fixing-ora-00054-resource.html

Il y a un travail très facile pour résoudre ce problème.

Si vous exécutez une trace 10046 sur votre session (google ça … trop à expliquer). Vous verrez qu’avant toute opération DDL, Oracle effectue les opérations suivantes:

LOCK TABLE ‘TABLE_NAME’ AUCUNE ATTENTE

Donc, si une autre session a une transaction ouverte, vous obtenez une erreur. Donc, le correctif est … roulement de tambour s’il vous plaît. Émettez votre propre verrou avant le DDL et laissez de côté «NO WAIT».

Note spéciale:

Si vous divisez ou déposez des partitions, Oracle verrouille simplement la partition. – Vous pouvez donc simplement verrouiller la sous-partition de partition.

Donc … Les étapes suivantes corrigent le problème.

  1. TABLEAU DE VERROUILLAGE ‘TABLE NAME’; – vous allez “attendre” (les développeurs appellent cela la suspension). jusqu’à la session avec la transaction ouverte, valide. Ceci est une queue. il peut donc y avoir plusieurs sessions devant vous. mais vous ne ferez PAS d’erreur.
  2. Exécutez DDL. Votre DDL exécutera alors un verrou avec NO WAIT. Cependant, votre session a acquis le verrou. Donc tu es bon.
  3. DDL auto-commits. Cela libère les serrures.

Les instructions DML vont “attendre” ou, comme les développeurs l’appellent “se bloquer”, la table est verrouillée.

Je l’utilise dans le code qui s’exécute à partir d’un travail pour supprimer des partitions. Ça fonctionne bien. C’est dans une firebase database qui s’insère constamment à raison de plusieurs centaines d’insertions / seconde. Pas d’erreurs

si vous vous demandez Faire cela en 11g. Je l’ai déjà fait en 10g auparavant.

Cette erreur se produit lorsque la ressource est occupée. Vérifiez si vous avez des contraintes référentielles dans la requête. Ou même les tables que vous avez mentionnées dans la requête peuvent être occupées. Ils peuvent être engagés dans un autre travail qui sera définitivement répertorié dans les résultats de requête suivants:

 SELECT * FROM V$SESSION WHERE STATUS = 'ACTIVE' 

Trouvez le SID,

 SELECT * FROM V$OPEN_CURSOR WHERE SID = --the id 

Cela se produit lorsqu’une session autre que celle utilisée pour modifier une table contient un verrou probablement à cause d’un DML (update / delete / insert). Si vous développez un nouveau système, il est probable que vous ou un membre de votre équipe publiez la déclaration de mise à jour et que vous puissiez tuer la session sans trop de conséquences. Ou vous pouvez vous engager à partir de cette session une fois que vous savez qui a ouvert la session.

Si vous avez access à un système d’administration SQL, utilisez-le pour rechercher la session incriminée. Et peut-être le tuer.

Vous pouvez utiliser v $ session et v $ lock et d’autres mais je vous suggère de rechercher comment trouver cette session et comment la tuer.

Dans un système de production, cela dépend vraiment. Pour oracle 10g et plus, vous pouvez exécuter

 LOCK TABLE mytable in exclusive mode; alter table mytable modify mycolumn varchar2(5); 

Dans une session séparée, mais les éléments suivants sont prêts au cas où cela prendrait trop de temps.

 alter system kill session '.... 

Cela dépend du système que vous avez, les anciens systèmes sont plus susceptibles de ne pas s’engager à chaque fois. C’est un problème car il peut y avoir des serrures de longue date. Ainsi, votre verrou empêchera tout nouveau verrou et attendra un verrou que celui qui sait quand sera libéré. C’est pourquoi vous avez l’autre déclaration prête. Ou vous pouvez rechercher des scripts PLSQL qui font des choses similaires automatiquement.

Dans la version 11g, il y a une nouvelle variable d’environnement qui définit un temps d’attente. Je pense que cela fait probablement quelque chose de similaire à ce que j’ai décrit. Rappelez-vous que les problèmes de locking ne disparaissent pas.

 ALTER SYSTEM SET ddl_lock_timeout=20; alter table mytable modify mycolumn varchar2(5); 

Enfin, il vaut peut-être mieux attendre que peu d’utilisateurs du système effectuent ce type de maintenance.

Votre problème ressemble à un mélange d’opérations DML et DDL. Voir cette URL qui explique ce problème:

http://www.orafaq.com/forum/t/54714/2/

Il suffit de vérifier le processus en tenant la session et de le tuer. C’est normal.

Ci-dessous SQL trouvera votre processus

 SELECT s.inst_id, s.sid, s.serial#, p.spid, s.username, s.program FROM gv$session s JOIN gv$process p ON p.addr = s.paddr AND p.inst_id = s.inst_id; 

Alors tuez le

 ALTER SYSTEM KILL SESSION 'sid,serial#' 

OU

un exemple que j’ai trouvé en ligne semble avoir besoin de l’ID d’instance et modifier la session de suppression du système ‘130,620, @ 1’;

Dans mon cas, j’étais tout à fait sûr que c’était une de mes propres sessions qui bloquait. Par conséquent, il était prudent de procéder comme suit:

  • J’ai trouvé la session offensante avec:

    SELECT * FROM V$SESSION WHERE OSUSER='my_local_username';

    La session était inactive , mais le verrou était toujours en place. Notez que vous devrez peut-être utiliser une autre condition WHERE dans votre cas (par exemple, essayez les champs USERNAME ou MACHINE ).

  • Tue la session en utilisant l’ ID et le SERIAL# acquis ci-dessus:

    alter system kill session ', ';

J’ai réussi à bash cette erreur en créant simplement une table! Il n’y avait évidemment aucun problème de contention sur une table qui n’existait pas encore. L’instruction CREATE TABLE contenait une CONSTRAINT fk_name FOREIGN KEY référençant une table bien remplie. J’ai dû:

  • Supprimez la clause FOREIGN KEY de l’instruction CREATE TABLE
  • Créer un INDEX sur la colonne FK
  • Créez le FK

J’ai eu cette erreur lorsque j’ai eu 2 scripts que je courais. J’avais:

  • Une session SQL * Plus connectée directement à l’aide d’un compte utilisateur de schéma (compte n ° 1)
  • Une autre session SQL * Plus connectée en utilisant un compte d’utilisateur de schéma différent (compte n ° 2), mais se connectant via un lien de firebase database en tant que premier compte

J’ai lancé une chute de table, puis la création de la table sous le compte n ° 1. J’ai effectué une mise à jour de la table sur la session du compte n ° 2. N’a pas commis de modifications. Ré-exécuté le script de repository / création de table en tant que compte n ° 1. Erreur dans la commande drop table x .

Je l’ai résolu en lançant COMMIT; dans la session SQL * Plus du compte n ° 2.

Je suis également confronté au même problème. Rien de programmeur n’a à faire pour résoudre cette erreur. J’ai informé mon équipe Oracle DBA. Ils tuent la séance et travaillent comme un charme.

La solution donnée par le lien de Shashi est la meilleure … pas besoin de contacter dba ou quelqu’un d’autre

faire une sauvegarde

 create table xxxx_backup as select * from xxxx; 

supprimer toutes les lignes

 delete from xxxx; commit; 

insérez votre sauvegarde.

 insert into xxxx (select * from xxxx_backup); commit;