{"id":3238,"date":"2013-09-18T04:59:35","date_gmt":"2013-09-18T09:59:35","guid":{"rendered":"http:\/\/appcrawler.com\/wordpress\/?p=3238"},"modified":"2013-09-18T04:59:35","modified_gmt":"2013-09-18T09:59:35","slug":"finding-rows-that-were-locked-after-the-fact","status":"publish","type":"post","link":"http:\/\/appcrawler.com\/wordpress\/2013\/09\/18\/finding-rows-that-were-locked-after-the-fact\/","title":{"rendered":"Finding rows that were locked, after the fact"},"content":{"rendered":"<p>In the Oracle database, if you have purchased the tuning pack, you have full access to the DBA_HIST_% views.  AWR, or Automated Workload Repository, is normally accessed via grid control or another tool.<\/p>\n<p>However, the raw data in the DBA_HIST views is absolutely invaluable.  This post will show how you can find which rows were locked and blocking another user.<\/p>\n<p>To do this, we use the DBA_HIST_ACTIVE_SESS_HISTORY view.  This view reflects historical samples taken every ten seconds of the live data in the GV$ACTIVE_SESSION_HISTORY view, which itself reflects samples taken every second.<\/p>\n<p>For us to find the rows, we must query for sessions waiting on the &#8220;enq: TX &#8211; row lock contention&#8221; event during our window of interest.  We also want to group by SQL_ID, so we can see which statements were being executed that were most impacted.<\/p>\n<p>Starting at about 21:06, ten minutes into the test, we had huge row locks on the following SQL statement\u2026<\/p>\n<pre lang=\"sql\">\r\nUPDATE dcs_inventory SET inventory_lock = :1  WHERE catalog_ref_id = :2\r\n<\/pre>\n<p>We reverse engineered the row(s) on which it was waiting (this is where the Oracle database really shines with this kind instrumentation), and found the following\u2026<\/p>\n<pre lang=\"sql\">\r\nSQL> select inventory_lock from atg_core_prod.dcs_inventory where rowid = dbms_rowid.rowid_create(1, 116307, 1024, 1109549, 44);\r\n\r\nINVENTORY_LOCK\r\n--------------------\r\ninventoryManager\r\n\r\nSQL> select inventory_lock from atg_core_prod.dcs_inventory where rowid = dbms_rowid.rowid_create(1, 116307, 1024, 1109512, 56);\r\n\r\nINVENTORY_LOCK\r\n--------------------\r\ninventoryManager\r\n\r\nSQL> select catalog_ref_id from atg_core_prod.dcs_inventory where rowid = dbms_rowid.rowid_create(1, 116307, 1024, 1109512, 56);\r\n\r\nCATALOG_REF_ID\r\n----------------------------------------\r\n3413362\r\n\r\nSQL> select display_name from atg_cata_prod.dcs_sku where sku_id = '3413362';\r\n\r\nDISPLAY_NAME\r\n--------------------------------------------------------------------------------\r\nCAMOUFLAGE FIVE PANEL HAT\r\n\r\nSQL>\r\n<\/pre>\n<p>You can also find the rowid for a given row, and search for it in DBA_HIST_ACTIVE_SESS_HISTORY with something like below<\/p>\n<pre lang=\"plsql\">\r\ndeclare\r\n  l_rowid_type number;\r\n  l_object_number number;\r\n  l_relative_fno number;\r\n  l_block_number number;\r\n  l_row_number number;\r\n  l_ts_type_in number;\r\nbegin\r\n  for r in (select order_id,rowid from atg_core_prod.dcspp_order where order_id in ('EXP536424935','EXP536461512','EXP536439773')) loop\r\n    dbms_rowid.rowid_info(r.rowid,l_rowid_type,l_object_number,l_relative_fno,l_block_number,l_ts_type_in);\r\n    dbms_output.put_line(r.order_id);\r\n    dbms_output.put_line(l_rowid_type);\r\n    dbms_output.put_line(l_object_number);\r\n    dbms_output.put_line(l_relative_fno);\r\n    dbms_output.put_line(l_block_number);\r\n    dbms_output.put_line(l_ts_type_in);\r\n  end loop;\r\nend;\r\n\/\r\n<\/pre>\n<p>Keep in mind this is mostly effective with UPDATE&#8217;s and assumes that the rows aren&#8217;t migrated as they are in a table shrink.  However, it can be invaluable.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>In the Oracle database, if you have purchased the tuning pack, you have full access to the DBA_HIST_% views. AWR, or Automated Workload Repository, is normally accessed via grid control or another tool. However, the raw data in the DBA_HIST&hellip;<\/p>\n<p class=\"more-link-p\"><a class=\"more-link\" href=\"http:\/\/appcrawler.com\/wordpress\/2013\/09\/18\/finding-rows-that-were-locked-after-the-fact\/\">Read more &rarr;<\/a><\/p>\n","protected":false},"author":2,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"_mi_skip_tracking":false,"footnotes":""},"categories":[19,22],"tags":[],"_links":{"self":[{"href":"http:\/\/appcrawler.com\/wordpress\/wp-json\/wp\/v2\/posts\/3238"}],"collection":[{"href":"http:\/\/appcrawler.com\/wordpress\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"http:\/\/appcrawler.com\/wordpress\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"http:\/\/appcrawler.com\/wordpress\/wp-json\/wp\/v2\/users\/2"}],"replies":[{"embeddable":true,"href":"http:\/\/appcrawler.com\/wordpress\/wp-json\/wp\/v2\/comments?post=3238"}],"version-history":[{"count":12,"href":"http:\/\/appcrawler.com\/wordpress\/wp-json\/wp\/v2\/posts\/3238\/revisions"}],"predecessor-version":[{"id":3310,"href":"http:\/\/appcrawler.com\/wordpress\/wp-json\/wp\/v2\/posts\/3238\/revisions\/3310"}],"wp:attachment":[{"href":"http:\/\/appcrawler.com\/wordpress\/wp-json\/wp\/v2\/media?parent=3238"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"http:\/\/appcrawler.com\/wordpress\/wp-json\/wp\/v2\/categories?post=3238"},{"taxonomy":"post_tag","embeddable":true,"href":"http:\/\/appcrawler.com\/wordpress\/wp-json\/wp\/v2\/tags?post=3238"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}