{"id":19870,"date":"2022-10-18T15:10:24","date_gmt":"2022-10-18T13:10:24","guid":{"rendered":"https:\/\/www.dbi-services.com\/blog\/?p=19870"},"modified":"2022-10-20T15:15:57","modified_gmt":"2022-10-20T13:15:57","slug":"oracle-database-row-archiving","status":"publish","type":"post","link":"https:\/\/www.dbi-services.com\/blog\/oracle-database-row-archiving\/","title":{"rendered":"Oracle Database Row Archiving"},"content":{"rendered":"\n<p>In a recent customer project, I was suffering to delete millions of rows from a LOG table.<\/p>\n\n\n\n<p>Removing 3 months of data took more than 30 minutes with the best optimization possible.<\/p>\n\n\n\n<p>After a while, I remembered that a very nice oracle feature existing since Oracle 12cR1 enables us to archive rows automatically.<\/p>\n\n\n\n<p>Let&#8217;s me explain you how it works:<\/p>\n\n\n\n<p>I have a big table with 10 millions of rows:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>SQL&gt; create table bigtable\nsegment creation immediate\nnologging\nas\nwith generator as (\n        select\n                rownum id\n        from dual\n        connect by\n                level &lt;= 10000000\n)\nselect\n        rownum                          id,\n        mod(rownum-1,3)                 val1,\n        mod(rownum-1,10)                val2,\n        lpad('x',100,'x')               padding\nfrom\n        generator       v1\norder by\n        dbms_random.value\n 21  ;\n\nTable created.\n\nSQL&gt; exec dbms_stats.gather_table_stats('SYS','BIGTABLE');\n\nPL\/SQL procedure successfully completed.\n\nSQL&gt; desc bigtable\n Name                                      Null?    Type\n ----------------------------------------- -------- ----------------------------\n ID                                                 NUMBER\n VAL1                                               NUMBER\n VAL2                                               NUMBER\n PADDING                                            VARCHAR2(100)\n\nSQL&gt; select count(*) from bigtable;\n\n  COUNT(*)\n----------\n  10000000\n\nSQL&gt;\n<\/code><\/pre>\n\n\n\n<p>Let&#8217;s see the data dispersion related to VAL2 column:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>SQL&gt; select count(*),val2 from bigtable group by val2;\n\n  COUNT(*)       VAL2\n---------- ----------\n   1000000          6\n   1000000          1\n   1000000          7\n   1000000          8\n   1000000          2\n   1000000          4\n   1000000          5\n   1000000          9\n   1000000          3\n   1000000          0\n\n10 rows selected.\n\nSQL&gt;\n<\/code><\/pre>\n\n\n\n<p>Let&#8217;s deleting rows related to VAL2 value = 8 :<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>SQL&gt; set timing on\nSQL&gt; delete from bigtable where val2=8;\nSQL &gt; commit;\n\n1000000 rows deleted.\n\nElapsed: 00:00:02.97\nSQL&gt; explain plan for delete from bigtable where val2=8;\n\nExplained.\n\nElapsed: 00:00:00.00\nSQL&gt; select * from table(dbms_xplan.display);\n\nPLAN_TABLE_OUTPUT\n--------------------------------------------------------------------------------\nPlan hash value: 1385633249\n\n-------------------------------------------------------------------------------\n| Id  | Operation          | Name     | Rows  | Bytes | Cost (%CPU)| Time     |\n-------------------------------------------------------------------------------\n|   0 | DELETE STATEMENT   |          |  1000K|  2929K| 44506   (1)| 00:00:02 |\n|   1 |  DELETE            | BIGTABLE |       |       |            |          |\n|*  2 |   TABLE ACCESS FULL| BIGTABLE |  1000K|  2929K| 44506   (1)| 00:00:02 |\n-------------------------------------------------------------------------------\n\nPredicate Information (identified by operation id):\n\nPLAN_TABLE_OUTPUT\n--------------------------------------------------------------------------------\n---------------------------------------------------\n\n   2 - filter(\"VAL2\"=8)\n\n14 rows selected.\n\nElapsed: 00:00:00.02\nSQL&gt;\n<\/code><\/pre>\n\n\n\n<p>The rows have been removed and the oracle optimizer does a Full Scan to access the data because there is no Index on the VAL2 column. The DELETE sql statement took about 3 sec to execute.<\/p>\n\n\n\n<p>For any reason If you want to restore this &#8220;deleting&#8221; rows, only &#8220;flashback&#8221; or &#8220;restore&#8221; from a backup will help you.<\/p>\n\n\n\n<p>Now let&#8217;s enabling ROW ARCHIVAL on the table BIGTABLE:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>SQL&gt; alter table bigtable row archival;\n\nTable altered.\n\nElapsed: 00:00:00.05\nSQL&gt;\n<\/code><\/pre>\n\n\n\n<p>A new hidden column called <em>ora_archive_state<\/em> is created indicating whether a row is archived or not. The column is displayed only via the SELECT command, not in the DESC command.<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>SQL&gt; desc bigtable\n Name                                      Null?    Type\n ----------------------------------------- -------- ----------------------------\n ID                                                 NUMBER\n VAL1                                               NUMBER\n VAL2                                               NUMBER\n PADDING                                            VARCHAR2(100)\n\nSQL&gt; select ID,VAL1,VAL2,PADDING,ora_archive_state from bigtable where rownum = 1;\n\nID       VAL1       VAL2  PADDING       ORA_ARCHIVE_STATE\n--------------------------------------------------------------------------------\n4091832  2          1     xxxxxxxxxxx   0\n\n\nElapsed: 00:00:00.00\nSQL&gt;\n<\/code><\/pre>\n\n\n\n<p> The value 0 in the <em>ora_archive_state <\/em>means the row is not archived, thus visible via the SELECT.<\/p>\n\n\n\n<p>Let&#8217;s confirm all rows are active (not archived):<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>SQL&gt; select count(*) from bigtable;\n\n  COUNT(*)\n----------\n  10000000\n<\/code><\/pre>\n\n\n\n<p>Now let&#8217;s suppose we want to archive all rows having value VAL2=6.<\/p>\n\n\n\n<p>Lets&#8217;s modify the value of <em>ora_archive_state<\/em>:<\/p>\n\n\n\n<p><\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>SQL&gt; update bigtable set ora_archive_state=dbms_ilm.archivestatename(1) where val2=6;\n\n1000000 rows updated.\n\nElapsed: 00:00:37.94\nSQL&gt; commit;\n\nCommit complete.\n\nElapsed: 00:00:01.28\nSQL&gt;\n<\/code><\/pre>\n\n\n\n<p>Let&#8217;s count the number of rows active now:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>SQL&gt; select count(*) from bigtable;\n\n  COUNT(*)\n----------\n   8000000\n\nElapsed: 00:00:02.17\nSQL&gt;\n<\/code><\/pre>\n\n\n\n<p>The rows archived are no more visible, they have been deleted &#8220;logically&#8221; (or archived):<\/p>\n\n\n\n<p>If we want to view all rows archived or not, set the archival visibility to ALL for the session:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>SQL&gt; alter session set row archival visibility = all;\n\nSession altered.\n\nElapsed: 00:00:00.00\n\nSQL&gt; select count(*) from bigtable;\n\n  COUNT(*)\n----------\n  90000000\n\nSQL&gt; select count(*),val2,ora_archive_state from bigtable group by val2, ora_archive_state;\n\n  COUNT(*)       VAL2         ORA_ARCHIVE_STATE\n--------------------------------------------------------------------------------\n1000000          1           0\n1000000          4           0\n1000000          6           1\n1000000          3           0\n1000000          5           0\n1000000          9           0\n1000000          7           0\n1000000          2           0\n1000000          0           0\n\n9 rows selected.\n<\/code><\/pre>\n\n\n\n<p>To see only rows unarchived, set the archival visibility to ACTIVE:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>SQL&gt; alter session set row archival visibility = active;\n\nSession altered.\n\nElapsed: 00:00:00.00\nSQL&gt; select count(*),val2,ora_archive_state from bigtable group by val2, ora_archive_state;\n\n  COUNT(*)       VAL2 O\n---------- ---------- -\n   1000000          1 0\n   1000000          7 0\n   1000000          2 0\n   1000000          4 0\n   1000000          5 0\n   1000000          9 0\n   1000000          3 0\n   1000000          0 0\n\n8 rows selected.\n\n<\/code><\/pre>\n\n\n\n<h2 class=\"wp-block-heading\">CONCLUSION<\/h2>\n\n\n\n<p>Oracle Database Row Archiving enables you to archive and delete &#8220;logically&#8221; the rows.<\/p>\n\n\n\n<p>Generally, it can be used to archive rows in big table.<\/p>\n\n\n\n<p>The implementation of this feature is very easy and can help you when you have to deal archiving\/deleting rows in big table.<\/p>\n\n\n\n<p><\/p>\n","protected":false},"excerpt":{"rendered":"<p>In a recent customer project, I was suffering to delete millions of rows from a LOG table. Removing 3 months of data took more than 30 minutes with the best optimization possible. After a while, I remembered that a very nice oracle feature existing since Oracle 12cR1 enables us to archive rows automatically. Let&#8217;s me [&hellip;]<\/p>\n","protected":false},"author":27,"featured_media":0,"comment_status":"open","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"_acf_changed":false,"footnotes":""},"categories":[229,198,368],"tags":[1171,2203],"type_dbi":[],"class_list":["post-19870","post","type-post","status-publish","format-standard","hentry","category-database-administration-monitoring","category-database-management","category-development-performance","tag-oracle-19c","tag-oracle-database"],"acf":[],"yoast_head":"<!-- This site is optimized with the Yoast SEO Premium plugin v27.2 (Yoast SEO v27.4) - https:\/\/yoast.com\/product\/yoast-seo-premium-wordpress\/ -->\n<title>Oracle Database Row Archiving - dbi Blog<\/title>\n<meta name=\"description\" content=\"oracle\" \/>\n<meta name=\"robots\" content=\"index, follow, max-snippet:-1, max-image-preview:large, max-video-preview:-1\" \/>\n<link rel=\"canonical\" href=\"https:\/\/www.dbi-services.com\/blog\/oracle-database-row-archiving\/\" \/>\n<meta property=\"og:locale\" content=\"en_US\" \/>\n<meta property=\"og:type\" content=\"article\" \/>\n<meta property=\"og:title\" content=\"Oracle Database Row Archiving\" \/>\n<meta property=\"og:description\" content=\"oracle\" \/>\n<meta property=\"og:url\" content=\"https:\/\/www.dbi-services.com\/blog\/oracle-database-row-archiving\/\" \/>\n<meta property=\"og:site_name\" content=\"dbi Blog\" \/>\n<meta property=\"article:published_time\" content=\"2022-10-18T13:10:24+00:00\" \/>\n<meta property=\"article:modified_time\" content=\"2022-10-20T13:15:57+00:00\" \/>\n<meta name=\"author\" content=\"Oracle Team\" \/>\n<meta name=\"twitter:card\" content=\"summary_large_image\" \/>\n<meta name=\"twitter:label1\" content=\"Written by\" \/>\n\t<meta name=\"twitter:data1\" content=\"Oracle Team\" \/>\n\t<meta name=\"twitter:label2\" content=\"Est. reading time\" \/>\n\t<meta name=\"twitter:data2\" content=\"4 minutes\" \/>\n<script type=\"application\/ld+json\" class=\"yoast-schema-graph\">{\"@context\":\"https:\\\/\\\/schema.org\",\"@graph\":[{\"@type\":\"Article\",\"@id\":\"https:\\\/\\\/www.dbi-services.com\\\/blog\\\/oracle-database-row-archiving\\\/#article\",\"isPartOf\":{\"@id\":\"https:\\\/\\\/www.dbi-services.com\\\/blog\\\/oracle-database-row-archiving\\\/\"},\"author\":{\"name\":\"Oracle Team\",\"@id\":\"https:\\\/\\\/www.dbi-services.com\\\/blog\\\/#\\\/schema\\\/person\\\/66ab87129f2d357f09971bc7936a77ee\"},\"headline\":\"Oracle Database Row Archiving\",\"datePublished\":\"2022-10-18T13:10:24+00:00\",\"dateModified\":\"2022-10-20T13:15:57+00:00\",\"mainEntityOfPage\":{\"@id\":\"https:\\\/\\\/www.dbi-services.com\\\/blog\\\/oracle-database-row-archiving\\\/\"},\"wordCount\":338,\"commentCount\":0,\"keywords\":[\"Oracle 19c\",\"Oracle Database\"],\"articleSection\":[\"Database Administration &amp; Monitoring\",\"Database management\",\"Development &amp; Performance\"],\"inLanguage\":\"en-US\",\"potentialAction\":[{\"@type\":\"CommentAction\",\"name\":\"Comment\",\"target\":[\"https:\\\/\\\/www.dbi-services.com\\\/blog\\\/oracle-database-row-archiving\\\/#respond\"]}]},{\"@type\":\"WebPage\",\"@id\":\"https:\\\/\\\/www.dbi-services.com\\\/blog\\\/oracle-database-row-archiving\\\/\",\"url\":\"https:\\\/\\\/www.dbi-services.com\\\/blog\\\/oracle-database-row-archiving\\\/\",\"name\":\"Oracle Database Row Archiving - dbi Blog\",\"isPartOf\":{\"@id\":\"https:\\\/\\\/www.dbi-services.com\\\/blog\\\/#website\"},\"datePublished\":\"2022-10-18T13:10:24+00:00\",\"dateModified\":\"2022-10-20T13:15:57+00:00\",\"author\":{\"@id\":\"https:\\\/\\\/www.dbi-services.com\\\/blog\\\/#\\\/schema\\\/person\\\/66ab87129f2d357f09971bc7936a77ee\"},\"description\":\"oracle\",\"breadcrumb\":{\"@id\":\"https:\\\/\\\/www.dbi-services.com\\\/blog\\\/oracle-database-row-archiving\\\/#breadcrumb\"},\"inLanguage\":\"en-US\",\"potentialAction\":[{\"@type\":\"ReadAction\",\"target\":[\"https:\\\/\\\/www.dbi-services.com\\\/blog\\\/oracle-database-row-archiving\\\/\"]}]},{\"@type\":\"BreadcrumbList\",\"@id\":\"https:\\\/\\\/www.dbi-services.com\\\/blog\\\/oracle-database-row-archiving\\\/#breadcrumb\",\"itemListElement\":[{\"@type\":\"ListItem\",\"position\":1,\"name\":\"Accueil\",\"item\":\"https:\\\/\\\/www.dbi-services.com\\\/blog\\\/\"},{\"@type\":\"ListItem\",\"position\":2,\"name\":\"Oracle Database Row Archiving\"}]},{\"@type\":\"WebSite\",\"@id\":\"https:\\\/\\\/www.dbi-services.com\\\/blog\\\/#website\",\"url\":\"https:\\\/\\\/www.dbi-services.com\\\/blog\\\/\",\"name\":\"dbi Blog\",\"description\":\"\",\"potentialAction\":[{\"@type\":\"SearchAction\",\"target\":{\"@type\":\"EntryPoint\",\"urlTemplate\":\"https:\\\/\\\/www.dbi-services.com\\\/blog\\\/?s={search_term_string}\"},\"query-input\":{\"@type\":\"PropertyValueSpecification\",\"valueRequired\":true,\"valueName\":\"search_term_string\"}}],\"inLanguage\":\"en-US\"},{\"@type\":\"Person\",\"@id\":\"https:\\\/\\\/www.dbi-services.com\\\/blog\\\/#\\\/schema\\\/person\\\/66ab87129f2d357f09971bc7936a77ee\",\"name\":\"Oracle Team\",\"image\":{\"@type\":\"ImageObject\",\"inLanguage\":\"en-US\",\"@id\":\"https:\\\/\\\/secure.gravatar.com\\\/avatar\\\/f711f7cd2c9b09bf2627133755b569fb5be0694810cfd33033bdd095fedba86d?s=96&d=mm&r=g\",\"url\":\"https:\\\/\\\/secure.gravatar.com\\\/avatar\\\/f711f7cd2c9b09bf2627133755b569fb5be0694810cfd33033bdd095fedba86d?s=96&d=mm&r=g\",\"contentUrl\":\"https:\\\/\\\/secure.gravatar.com\\\/avatar\\\/f711f7cd2c9b09bf2627133755b569fb5be0694810cfd33033bdd095fedba86d?s=96&d=mm&r=g\",\"caption\":\"Oracle Team\"},\"url\":\"https:\\\/\\\/www.dbi-services.com\\\/blog\\\/author\\\/oracle-team\\\/\"}]}<\/script>\n<!-- \/ Yoast SEO Premium plugin. -->","yoast_head_json":{"title":"Oracle Database Row Archiving - dbi Blog","description":"oracle","robots":{"index":"index","follow":"follow","max-snippet":"max-snippet:-1","max-image-preview":"max-image-preview:large","max-video-preview":"max-video-preview:-1"},"canonical":"https:\/\/www.dbi-services.com\/blog\/oracle-database-row-archiving\/","og_locale":"en_US","og_type":"article","og_title":"Oracle Database Row Archiving","og_description":"oracle","og_url":"https:\/\/www.dbi-services.com\/blog\/oracle-database-row-archiving\/","og_site_name":"dbi Blog","article_published_time":"2022-10-18T13:10:24+00:00","article_modified_time":"2022-10-20T13:15:57+00:00","author":"Oracle Team","twitter_card":"summary_large_image","twitter_misc":{"Written by":"Oracle Team","Est. reading time":"4 minutes"},"schema":{"@context":"https:\/\/schema.org","@graph":[{"@type":"Article","@id":"https:\/\/www.dbi-services.com\/blog\/oracle-database-row-archiving\/#article","isPartOf":{"@id":"https:\/\/www.dbi-services.com\/blog\/oracle-database-row-archiving\/"},"author":{"name":"Oracle Team","@id":"https:\/\/www.dbi-services.com\/blog\/#\/schema\/person\/66ab87129f2d357f09971bc7936a77ee"},"headline":"Oracle Database Row Archiving","datePublished":"2022-10-18T13:10:24+00:00","dateModified":"2022-10-20T13:15:57+00:00","mainEntityOfPage":{"@id":"https:\/\/www.dbi-services.com\/blog\/oracle-database-row-archiving\/"},"wordCount":338,"commentCount":0,"keywords":["Oracle 19c","Oracle Database"],"articleSection":["Database Administration &amp; Monitoring","Database management","Development &amp; Performance"],"inLanguage":"en-US","potentialAction":[{"@type":"CommentAction","name":"Comment","target":["https:\/\/www.dbi-services.com\/blog\/oracle-database-row-archiving\/#respond"]}]},{"@type":"WebPage","@id":"https:\/\/www.dbi-services.com\/blog\/oracle-database-row-archiving\/","url":"https:\/\/www.dbi-services.com\/blog\/oracle-database-row-archiving\/","name":"Oracle Database Row Archiving - dbi Blog","isPartOf":{"@id":"https:\/\/www.dbi-services.com\/blog\/#website"},"datePublished":"2022-10-18T13:10:24+00:00","dateModified":"2022-10-20T13:15:57+00:00","author":{"@id":"https:\/\/www.dbi-services.com\/blog\/#\/schema\/person\/66ab87129f2d357f09971bc7936a77ee"},"description":"oracle","breadcrumb":{"@id":"https:\/\/www.dbi-services.com\/blog\/oracle-database-row-archiving\/#breadcrumb"},"inLanguage":"en-US","potentialAction":[{"@type":"ReadAction","target":["https:\/\/www.dbi-services.com\/blog\/oracle-database-row-archiving\/"]}]},{"@type":"BreadcrumbList","@id":"https:\/\/www.dbi-services.com\/blog\/oracle-database-row-archiving\/#breadcrumb","itemListElement":[{"@type":"ListItem","position":1,"name":"Accueil","item":"https:\/\/www.dbi-services.com\/blog\/"},{"@type":"ListItem","position":2,"name":"Oracle Database Row Archiving"}]},{"@type":"WebSite","@id":"https:\/\/www.dbi-services.com\/blog\/#website","url":"https:\/\/www.dbi-services.com\/blog\/","name":"dbi Blog","description":"","potentialAction":[{"@type":"SearchAction","target":{"@type":"EntryPoint","urlTemplate":"https:\/\/www.dbi-services.com\/blog\/?s={search_term_string}"},"query-input":{"@type":"PropertyValueSpecification","valueRequired":true,"valueName":"search_term_string"}}],"inLanguage":"en-US"},{"@type":"Person","@id":"https:\/\/www.dbi-services.com\/blog\/#\/schema\/person\/66ab87129f2d357f09971bc7936a77ee","name":"Oracle Team","image":{"@type":"ImageObject","inLanguage":"en-US","@id":"https:\/\/secure.gravatar.com\/avatar\/f711f7cd2c9b09bf2627133755b569fb5be0694810cfd33033bdd095fedba86d?s=96&d=mm&r=g","url":"https:\/\/secure.gravatar.com\/avatar\/f711f7cd2c9b09bf2627133755b569fb5be0694810cfd33033bdd095fedba86d?s=96&d=mm&r=g","contentUrl":"https:\/\/secure.gravatar.com\/avatar\/f711f7cd2c9b09bf2627133755b569fb5be0694810cfd33033bdd095fedba86d?s=96&d=mm&r=g","caption":"Oracle Team"},"url":"https:\/\/www.dbi-services.com\/blog\/author\/oracle-team\/"}]}},"_links":{"self":[{"href":"https:\/\/www.dbi-services.com\/blog\/wp-json\/wp\/v2\/posts\/19870","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.dbi-services.com\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.dbi-services.com\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.dbi-services.com\/blog\/wp-json\/wp\/v2\/users\/27"}],"replies":[{"embeddable":true,"href":"https:\/\/www.dbi-services.com\/blog\/wp-json\/wp\/v2\/comments?post=19870"}],"version-history":[{"count":6,"href":"https:\/\/www.dbi-services.com\/blog\/wp-json\/wp\/v2\/posts\/19870\/revisions"}],"predecessor-version":[{"id":19877,"href":"https:\/\/www.dbi-services.com\/blog\/wp-json\/wp\/v2\/posts\/19870\/revisions\/19877"}],"wp:attachment":[{"href":"https:\/\/www.dbi-services.com\/blog\/wp-json\/wp\/v2\/media?parent=19870"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.dbi-services.com\/blog\/wp-json\/wp\/v2\/categories?post=19870"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.dbi-services.com\/blog\/wp-json\/wp\/v2\/tags?post=19870"},{"taxonomy":"type","embeddable":true,"href":"https:\/\/www.dbi-services.com\/blog\/wp-json\/wp\/v2\/type_dbi?post=19870"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}