2009-10-15 12 views
7

क्या कोई तरीका है कि कोई परीक्षण कर सकता है कि ओरेकल में अपडेट के लिए एक पंक्ति लॉक हो गई है?आप कैसे जांचते हैं कि अद्यतन के लिए एक पंक्ति लॉक है या नहीं?

select * from SOME_TABLE where THE_ID = 1000 for update; 

किसी अन्य उपयोगकर्ता मैं अगर THE_ID = 1000 साथ पंक्ति लॉक किया गया है जाँच करना चाहते हैं के साथ:

उदाहरण के लिए, निम्न क्वेरी, एक उपयोगकर्ता द्वारा किया लगता है। अगर मैं एक अद्यतन या कुछ कोशिश करता हूं तो दूसरा उपयोगकर्ता अवरुद्ध हो जाता है और प्रतीक्षा करता रहता है (वह नहीं चाहता)।

मैं भी दूसरे उपयोगकर्ता के साथ निम्न क्वेरी चलाने की कोशिश की है:

select * from SOME_TABLE where THE_ID = 1000 for update NOWAIT; 

जब से मैं एक ही पंक्ति पर दो ताले नहीं लगा सकेंगे इस असफल हो जायेगी। और यह करता है। मुझे एक "ओआरए-00054: संसाधन व्यस्त है और NOWAIT निर्दिष्ट त्रुटि के साथ अधिग्रहण" मिलता है। क्या मैं हमेशा लॉक की उपस्थिति की जांच करने के लिए इस त्रुटि पर भरोसा कर सकता हूं, या क्या यह निर्धारित करने का एक सरल और साफ तरीका है कि कोई पंक्ति लॉक है या नहीं?

धन्यवाद!

+1

आपको चाहिए इस त्रुटि मिलती है "ORA-00054: व्यस्त संसाधन और प्रतीक्षा नहीं के साथ प्राप्त निर्दिष्ट" - आप सुनिश्चित करें कि आपके उपयोगकर्ता तालिका देख सकते हैं कर रहे हैं? – SeriousCallersOnly

+0

@ SeriousCallersOnly: धन्यवाद, मैं वास्तव में ": व्यस्त संसाधन और प्रतीक्षा नहीं निर्दिष्ट त्रुटि के साथ प्राप्त ORA-00054" हो रहा है। ओआरए -00 9 42 को मेरे ऐप की एक और परत से फेंक दिया गया था। उसके लिए माफ़ करना। मैं सवाल संपादित करूंगा। –

उत्तर

14

आप के लिए अद्यतन प्रतीक्षा नहीं के साथ एक प्रक्रिया लिख ​​सकते हैं और एक त्रुटि संदेश लौट जब पंक्ति लॉक किया गया है सकते हैं:

SQL> CREATE OR REPLACE PROCEDURE do_something(p_id NUMBER) IS 
    2  row_locked EXCEPTION; 
    3  PRAGMA EXCEPTION_INIT(row_locked, -54); 
    4 BEGIN 
    5  FOR cc IN (SELECT * 
    6     FROM some_table 
    7     WHERE ID = p_id FOR UPDATE NOWAIT) LOOP 
    8  -- proceed with what you want to do; 
    9  NULL; 
10  END LOOP; 
11 EXCEPTION 
12  WHEN row_locked THEN 
13  raise_application_error(-20001, 'this row is locked...'); 
14 END do_something; 
15/

Procedure created 

अब चलो दो सत्रों के साथ एक छोटा सा उदाहरण का निर्माण करते हैं:

session_1> select id from some_table where id = 1 for update; 

     ID 
---------- 
     1 

session_2> exec do_something(1); 

begin do_something(1); end; 

ORA-20001: this row is locked... 
ORA-06512: at "VNZ.DO_SOMETHING", line 11 
ORA-06512: at line 2 

session_1> commit; 

Commit complete 

session_2> exec do_something(1); 

PL/SQL procedure successfully completed 
+0

मैं पहले से ही SeriousCallersOnly का जवाब दिया जैसा कि मैंने वास्तव में ORA-00054 त्रुटि हो रहा है। धन्यवाद। लेकिन क्या मैं लॉक की जांच करने के लिए उस पर भरोसा कर सकता हूं? –

+0

@ डीपीबी: आप इस तंत्र पर भरोसा कर सकते हैं। मैं एक छोटे से दिखा कैसे प्रक्रिया दो सत्रों एक ही पंक्ति पर ताला लगा के साथ काम करेंगे उदाहरण गयी। –

1

यह न तो सरल है और न ही साफ है, लेकिन जानकारी V$LOCK और V$SESSION विचारों में उपलब्ध है।

हालांकि, अगर आप अपने सामान्य आवेदन कोड के भाग के रूप कुछ इस तरह का उपयोग करने की जरूरत महसूस, आप फिर से सोचने की जरूरत। एप्लिकेशन को इस बात की परवाह नहीं करनी चाहिए कि डेटाबेस लॉकिंग कैसे करता है। यदि आप डेडलॉक्स में भाग रहे हैं, तो आपको अपने प्रश्नों को पुन: व्यवस्थित करने की आवश्यकता है ताकि वे न हों।

संबंधित मुद्दे

 संबंधित मुद्दे