Skip to Main Content

Breadcrumb

Question and Answer

Chris Saxon

Thanks for the question, Mahendra.

Asked: December 25, 2005 - 11:45 pm UTC

Last updated: October 09, 2015 - 12:57 am UTC

Version: 9201

Viewed 1000+ times

You Asked

Dear Tom,

Flashback protects us against accidental lose of data like Drop Table, Truncate Table and Delete. We need to have either Time or SCN to flashback to a given point of time.

My question is does Oracle provide us the detail about the SCN/time of the event when any / some of above operation took place like truncate table / drop table ? I mean does Oracle maintains SCN/time with actual SQL text anywhere, which can be useful to Oracle DBA/Developer when such event took place?

Thanks in advanse

Thanks & Regards,
Mahendra


and Tom said...

flashback TABLE does not protect against truncate at all!!!


For drop table, the recycle bin (user_recyclebin) has everything you need.
For truncate - you cannot "untruncate" a table.

There is flashback transaction history and flashback row history that can be used to find out "when" a bad DML statement was issued.

Rating

  (22 ratings)

Is this answer out of date? If it is, please let us know via a Comment

Comments

Thanks

Mahendra, December 26, 2005 - 10:48 pm UTC


Flash Back

Karthick, December 27, 2005 - 3:27 am UTC

</code> https://blogs.oracle.com/oraclemagazine/post/on-finding-order-and-setting-packages-against-procedures <code>

This publishing in oracle magazine is good.

I have few questions.

1. Can I retrieve lost data in a single select? That is without using enable_at_time and then disable. Ie joining some data dictionary table and specifying the time I want.

2. 900 sec is the default time that oracle has set for UNDO_RETENTION what will the time that you will suggest.

3. What is the main reason behind introducing flash back? To get lost data is a general answer. But what sort of loss (oracle should have made a detail analysis about this).


Tom Kyte
December 27, 2005 - 9:50 am UTC

that is using the 9iR1 method - in 9ir2 and above it became much easier. Consider this tiny example:

scott@ORA10GR2> variable n number
scott@ORA10GR2> exec select dbms_flashback.get_system_change_number into :n from dual;

PL/SQL procedure successfully completed.

I'll be using SCN, but you may also use a date/timestamp -- see sql reference for details

scott@ORA10GR2>
scott@ORA10GR2> update emp set sal = sal * 1.5;

14 rows updated.

scott@ORA10GR2> commit;

Commit complete.

make a change and commit it


scott@ORA10GR2>
scott@ORA10GR2> select a.ename, a.sal new_sal, b.sal old_sal
2 from emp a, emp as of scn :n b
3 where a.empno = b.empno
4 /

ENAME NEW_SAL OLD_SAL
---------- ---------------- ----------------
SMITH 1800 1200
ALLEN 3600 2400
WARD 2813 1875
JONES 6694 4463
MARTIN 2813 1875
BLAKE 6413 4275
CLARK 5513 3675
SCOTT 6750 4500
KING 11250 7500
TURNER 3375 2250
ADAMS 2475 1650
JAMES 2138 1425
FORD 6750 4500
MILLER 2925 1950

14 rows selected.

Join the data with itself from before the modification.... no dbms_flashback.enable/disable anymore


scott@ORA10GR2>
scott@ORA10GR2> update emp
2 set sal = ( select sal
3 from emp as of scn :n b
4 where b.empno = emp.empno )
5 /

14 rows updated.

scott@ORA10GR2> commit;

Commit complete.

flashback in modifications - no restriction on that anymore..

scott@ORA10GR2>
scott@ORA10GR2> select ename, sal from emp;

ENAME SAL
---------- ----------------
SMITH 1200
ALLEN 2400
WARD 1875
JONES 4463
MARTIN 1875
BLAKE 4275
CLARK 3675
SCOTT 4500
KING 7500
TURNER 2250
ADAMS 1650
JAMES 1425
FORD 4500
MILLER 1950

14 rows selected.



2) a little longer than your longest running query at the very least, OR whatever you want to have for "whoops recovery" purposes above and beyond that value

3) "whoops operations".

there is in 10g:

flashback query (get the data as of that prior point in time, correct an error)

flashback row history (see all of the versions of a given row between two points in time, pinpoint WHEN a bad transaction took place)

flashback transaction (get all of the SQL to undo a given bad transaction - sql is generated for you)

flashback table (put a table(s) back the way it was some time ago)

flashback undrop a table (undrop a table)

flashback database (put the database back the way it was some time ago)




A reader, December 27, 2005 - 12:41 pm UTC

Tom,
What files other than the database itself are required to do a flashback of the database? Do I need to provision extra space for these files?
Thanks


Tom Kyte
December 27, 2005 - 2:19 pm UTC

you need to have a flash recovery area, the database had to be operating in a mode that permits the flashback database to work

</code> http://docs.oracle.com/docs/cd/B19306_01/backup.102/b14191/osrecov.htm#sthref1593 <code>

Receving ORA-01466

Janardhan, December 28, 2005 - 11:10 am UTC

Hi Tom,
        You are doing a great job.I am learning so much stuff from your website. Here is my issue..
I am receiving ORA-01466 when I tested your example in my test database (9.2.0.6).My undo settings are

undo_management                      string      AUTO
undo_retention                       integer     10800
undo_suppress_errors                 boolean     FALSE
undo_tablespace                      string      UNDOTBS1

I have enough free space in undo tablespace.

***********************************************************

SQL> create table test1 (empid number,ename varchar2(20),esal number);

Table created.

SQL> insert into test1 values (&i,&n,&s);
Enter value for i: 1
Enter value for n: 'SMITH'
Enter value for s: 1000
old   1: insert into test1 values (&i,&n,&s)
new   1: insert into test1 values (1,'SMITH',1000)

1 row created.

SQL> /
Enter value for i: 2
Enter value for n: 'GEORGE'
Enter value for s: 2000
old   1: insert into test1 values (&i,&n,&s)
new   1: insert into test1 values (2,'GEORGE',2000)

1 row created.

SQL> /
Enter value for i: 3
Enter value for n: 'TIM'
Enter value for s: 3000
old   1: insert into test1 values (&i,&n,&s)
new   1: insert into test1 values (3,'TIM',3000)

1 row created.

SQL> /
Enter value for i: 4
Enter value for n: 'HANK'
Enter value for s: 4000
old   1: insert into test1 values (&i,&n,&s)
new   1: insert into test1 values (4,'HANK',4000)

1 row created.

SQL> commit;

Commit complete.

SQL> select * from test1;

     EMPID ENAME                      ESAL
---------- -------------------- ----------
         1 SMITH                      1000
         2 GEORGE                     2000
         3 TIM                        3000
         4 HANK                       4000

SQL> variable n number
SQL> exec select dbms_flashback.get_system_change_number into :n from dual;

PL/SQL procedure successfully completed.

SQL> print n

         N
----------
   7825696


SQL> update test1 set esal=esal*2;

4 rows updated.

SQL> commit;

Commit complete.

SQL> select * from test1;

     EMPID ENAME                      ESAL
---------- -------------------- ----------
         1 SMITH                      2000
         2 GEORGE                     4000
         3 TIM                        6000
         4 HANK                       8000

SQL> select a.ename,a.esal new_sal,b.esal old_sal from test1 a, test1 as of scn :n b
  2  where a.empid=b.empid;
select a.ename,a.esal new_sal,b.esal old_sal from test1 a, test1 as of scn :n b
                                                  *
ERROR at line 1:
ORA-01466: unable to read data - table definition has changed


 

Tom Kyte
December 28, 2005 - 11:48 am UTC

table is too "new" - wait a bit (like 5 minutes in 9i).

The table is just "too new"

(I used existing tables in the SCOTT schema)

Issue resolved

Janardhan, December 29, 2005 - 9:50 am UTC

Thanks for your reponse.Issue resolved.

save record @ form

Ishfaq Ahmed, January 24, 2006 - 1:16 am UTC

here is the button "SAVE" code , it saves new value but not update old record
Plz. Help me in this regard

DECLARE
BEGIN
:STAT := :SYSTEM.FORM_STATUS;
IF :STAT = 'CHANGED' THEN
UPDATE PRODUCT_MASTER SET
DESCRIPTION = :DESCRIPTION,
PROFIT_RATIO = :PROFIT_PERCENT,
U_M = :UNIT_MEASURE,
QTY_ON_HAND = :QTY_ON_HAND,
REORDER_LVL = :RECORDER_LVL,
SELL_PRICE = :SELL_PRICE,
COST_PRICE = :COST_PRICE WHERE PRODUCT_NO = :PRODUCT_NO;
--COMMIT_FORM;
--MESSAGE('R E C O R D U P D A T E D');
commit;
else
:STAT :='New Entry';
if :STAT ='New Entry' then
insert into product_master values (:product_no,:DESCRIPTION,:PROFIT_PERCENT,:UNIT_MEASURE,:QTY_ON_HAND,:RECORDER_LVL,:SELL_PRICE,:COST_PRICE);
:system.message_level := 5;
--COMMIT_FORM;
MESSAGE('R E C O R D S A V E D');
end if;
:STAT := ' ';
GO_ITEM('PRODUCT_NO');
END IF;
END;

Flashback and Indexes

V, June 19, 2006 - 11:09 am UTC

When I drop a table I see both the table and index in the recyclebin:

SQL> select object_name,type from recyclebin;

OBJECT_NAME                    TYPE
------------------------------ -------------------------
BIN$FpUFLdu5Vr7gRAADupYrZw==$1 INDEX
BIN$FpUFLdu6Vr7gRAADupYrZw==$0 TABLE

SQL> flashback table t1 to before drop;

Flashback complete.

SQL> select index_name from user_indexes;

INDEX_NAME
------------------------------
BIN$FpUFLdu5Vr7gRAADupYrZw==$1

But when I look at user_indexes I see the new name not the original index name.  What do I have to do to get it back to the original, drop & recreate? 

Tom Kyte
June 19, 2006 - 6:36 pm UTC

You have to rename the index manually yourself - this is "by design", they made a decision to not rename back the subordinate objects.

The index is back, you just need to rename it.

Alexander the ok, December 18, 2006 - 10:55 am UTC

Hi Tom,

I'm a little confused about how to set up your file system for a database with flashback and where to place your files. According to this:

</code> http://download-east.oracle.com/docs/cd/B19306_01/server.102/b14220/backrec.htm#i1014670 <code>

You should place all those files in the flashback recovery area. If I do not do this, will I have problems, or is it just a suggestion? I'm asking because we have standard Oracle file systems we use so things are uniform so any dba can get around on someone's box. Stuffing all our database files in one location like the docs suggestion would be very different.

Tom Kyte
December 18, 2006 - 11:13 am UTC

do you want to use flash recovery? If so, you will set it up like that.

Alexander the ok, December 18, 2006 - 12:02 pm UTC

Well that's not entirely true though because I can enable flashback by setting 3 parameters and be off and running without all my files being where those instructions say.

Tom Kyte
December 18, 2006 - 2:52 pm UTC

flash recovery. not just "flashback".

flashback query - undo based
flashback transaction - undo based
flashback version query - undo based
flashback table - recycle bin metaphor (not undo, not redo)
flashback database - flash recovery

A reader, April 26, 2007 - 10:34 am UTC

What is your opinion on the use of the Flash Recovery Area on a RAID5 server to store daily database backups as the ONLY store of these backups?
We know this is a very bad idea, but are being told by our suppliers that because we being provided with RAID5, this is adequate protection. Are there any specific dangers in doing this (other than the obvious 'what if you lose your disks?') Documentation states that a limitation of Flashback Database is the inability to recover from media failures - anything else we can point them towards to stop them delivering this? We're being backed into a corner...EVERYTHING oracle related is on the same server as well as a domain controller and a SQL Server installation. Them trying to insist backups are held in the same place is a step too far as far as I'm concerned, but I could use some backup from 'professionals'!

We have yet to even see evidence that they're taking the backups off the server onto tape...project is to be delivered in a couple of weeks!! Nightmare.

cheers

Tom Kyte
April 26, 2007 - 1:28 pm UTC

... We know this is a very bad idea, ...

you have my vote as well.


raid5 is sort of pretty good at being available. funny thing about disk failures though isn't it.

when one disk goes in a lot (a manufacturing lot), the rest are soon to follow. disk failures are based on manufacturing defects (which happen in lots) and age of disk (which all disks in a lot are the same age...)

so, the probability of two or more disks failing near the same time in your raid 5 array - high.


what more than "what if you lose your disks" do you need? Something like "you will also be struck by lightening?" I wouldn't need that, losing the disks would be painful enough.


Thankyou!!!

A reader, April 27, 2007 - 3:16 am UTC

Thanks for that! I've been trying to get them to listen to me for weeks on this and other subjects. Perhaps they'll now listen to you!

Cheers
Liz

My above comments may be redundant!

A reader, April 27, 2007 - 8:25 am UTC

Thankyou again for your support on the above issue, but it may turn out to be a none-issue after all!
Further questioning of our supplier has revealed that they are installing 10g release 2 Standard Edition, and notes on the oracle discussion forum and documentation suggest that Flashback Database isn't an option with this installation (please correct me if I'm wrong).
It would seem that the supplier has decided upon this backup strategy as a theory based on documentation only, but haven't tested in practice. Looks like they've called their recovery area 'Flash_Recovery' for dumping backup files without actually implementing the Flash recovery features.
We've asked the question and the response so far is a stoney silence....

flashback table

Ken Mirvis, July 18, 2007 - 6:36 am UTC

Where does Oracle store flashback table information? And how to size that area?
I understand that the undo tablespace is used for all flashback purposes bar one: flashback database - flashback recovery area.

What considerations must be made for flashback table when sizing undo tablespace?
Tom Kyte
July 18, 2007 - 10:52 am UTC

there are:

o flashback query, undo based
o flashback versions query, undo based
o flashback table to point in time, undo based

o flashback table to before drop, recycle bin based (NOT undo)

o flashback database, flashrecovery based (NOT undo)


So, there is "bar two" - when you drop a table, we just 'hide' the extents and try not to reuse them until and unless we have to. You might be able to undrop a table 5 years after dropping it (if the tablespace it was in did not reuse that space over time). You might not be able to undrop a table 0.0001 seconds after dropping it (if you drop table t; create table t; - in the same tablespace and that tablespace was "full" when you dropped it - the subsequent create will overwrite the old table t)


The consideration for sizing undo:

take the maximum of:

a) the length of time your longest running query executes for
b) the length of time you would like to be able to flashback for

that is your undo retention period, now you need to understand how much undo you generate in a period of time - then - divide.

the undo advisor will help you (you can go to your running system and say "if I wanted to have 4 hours of undo retention - how big would my undo tablespace be given my current workload?")

v$undostat will help as well - it is what the advisor itself uses.

FBQ between a period

A reader, August 13, 2007 - 3:39 am UTC

Tom referring to the first post asked...
Can i know all the values of a column changed between a certian period.
Tom Kyte
August 15, 2007 - 10:50 am UTC

flashback row history, yes.

FBQ between a period

A reader, August 13, 2007 - 3:46 am UTC

Tom,
Can i know all the values of a column changed between a certian period using FBQ.
let's say.
I want to know all the values of a column X that have been changed between 1st March 2006 and 31st March 2006.

Tom Kyte
August 15, 2007 - 10:52 am UTC

versions query - yes

select ename, sal,
       versions_operation,
       versions_starttime,
       versions_endtime
 <b> from emp versions between timestamp to_timestamp('&START') and to_timestamp('&STOP')</b>
 where empno = 7788
 order by versions_startscn nulls first
/

OK

A reader, August 27, 2007 - 9:02 am UTC

Hello Tom,
Can Multiple tables be flashed back in a single stretch?
In documentation it is mentioned as "we can specify tables
in the flashback list".
I tried this but not working.
Could you please clarify this?

Tom Kyte
September 04, 2007 - 11:53 am UTC

scott%ORA10GR2> flashback table dept to scn &S;
old   1: flashback table dept to scn &S
new   1: flashback table dept to scn   27362402

Flashback complete.

Flashback multiple tables

Michel Cadot, September 04, 2007 - 12:07 pm UTC


Here's an example:
SQL> -- Create the tables and display their content --
SQL> 
SQL> create table t1 enable row movement
  2  as select level val from dual connect by level <=3
  3  /
Table created.
SQL> create table t2 enable row movement
  2  as select level val from dual connect by level <=3
  3  /
Table created.
SQL> exec dbms_lock.sleep(10);
PL/SQL procedure successfully completed.
SQL> select * from t1;
          VAL
-------------
            1
            2
            3

3 rows selected.

SQL> select * from t2;
          VAL
-------------
            1
            2
            3

3 rows selected.

SQL> col scn new_value scn
SQL> SELECT dbms_flashback.get_system_change_number scn FROM DUAL;
          SCN
-------------
4339478652078

1 row selected.

SQL> def scn
DEFINE SCN             = 4339478652078 (NUMBER)
SQL> 
SQL> -- Modify data --
SQL> 
SQL> delete t1 where mod(val,2)=0;
2 rows deleted.
SQL> commit;
Commit complete.
SQL> update t2 set val=val*val;
5 rows updated.
SQL> commit;
Commit complete.
SQL> select * from t1;
          VAL
-------------
            1
            3

2 rows selected.

SQL> select * from t2;
          VAL
-------------
            1
            4
            9

3 rows selected.

SQL> 
SQL> -- Flashback both tables at the same time --
SQL> 
SQL> flashback table t1,t2 to scn &scn;

Flashback complete.

SQL> select * from t1;
          VAL
-------------
            1
            2
            3

3 rows selected.

SQL> select * from t2;
          VAL
-------------
            1
            2
            3

3 rows selected.

Regards
Michel

What about tables protected with OLS Policies?

Bill S., June 11, 2008 - 2:43 pm UTC

Using 10gR2 on SuSe Linux.

The senior DBA and I were playing around with flashback, and set up a test box that we could import our production database schemas into. During the course of testing out table recovery, she noticed that if she dropped a table with an active OLS policy on it, the table did not show up in the recycle bin. However, if she dropped a table with no policies on it, that table would show up. To complete the exercise, we re-imported the original table and set the OLS policy back up on it. Then we dropped the policy from the table, and subsequently dropped the table itself. It showed up in the recycle bin just fine.
I can't find anything in the docs about it (checked the 10g Admin guide, the 10g OLS admin guide). Any ideas where I can look next? :-O

Thanks much, Tom. Always a pleasure.
Tom Kyte
June 11, 2008 - 8:46 pm UTC

that is by design. It is documented.

http://docs.oracle.com/docs/cd/B19306_01/backup.102/b14192/flashptr004.htm#sthref641

"Due to security concerns, tables which have Fine-Grained Auditing (FGA) and Virtual Private Database (VPD) policies defined over them are not protected by the recycle bin."

Aha! The doc I didn't look in has it!

Bill S., June 12, 2008 - 8:22 am UTC

Thanks much. I never thought to look in that one.

I figured as much but it is always nice to have the docs confirm it.

Table dropped with an index

Naresh Reddy, June 13, 2011 - 2:21 am UTC

Hi Tom,You are doing a lot for Oracle DBA'S.Now i have an issue arises i.e.
Example:I am having a table emp and i had created an index on empname.i had dropped the table without sense after realize that, i used flashback table and retrive the table,is that emp table contains the index on empname.
Tom Kyte
June 17, 2011 - 11:01 am UTC

the index would be undropped as well - but - the index name would be mangled.

ops$tkyte%ORA11GR2> create table emp as select * from scott.emp;

Table created.

ops$tkyte%ORA11GR2> create index emp_ename_idx on emp(ename);

Index created.

ops$tkyte%ORA11GR2> 
ops$tkyte%ORA11GR2> select object_name, object_type from user_objects;

OBJECT_NAME                    OBJECT_TYPE
------------------------------ ------------
EMP_ENAME_IDX                  INDEX

EMP                            TABLE


ops$tkyte%ORA11GR2> select object_name, original_name, type from user_recyclebin;

no rows selected

ops$tkyte%ORA11GR2> drop table emp;

Table dropped.

ops$tkyte%ORA11GR2> select object_name, object_type from user_objects;

no rows selected

ops$tkyte%ORA11GR2> select object_name, original_name, type from user_recyclebin;

OBJECT_NAME                    ORIGINAL_NAME                    TYPE
------------------------------ -------------------------------- -------------------------
BIN$pet4jxIZCArgQAB/AQBrkA==$0 EMP_ENAME_IDX                    INDEX
BIN$pet4jxIaCArgQAB/AQBrkA==$0 EMP                              TABLE

ops$tkyte%ORA11GR2> flashback table emp to before drop;

Flashback complete.

ops$tkyte%ORA11GR2> select object_name, object_type from user_objects;

OBJECT_NAME                    OBJECT_TYPE
------------------------------ ------------
EMP                            TABLE

BIN$pet4jxIZCArgQAB/AQBrkA==$0 INDEX


ops$tkyte%ORA11GR2> select object_name, original_name, type from user_recyclebin;

no rows selected

<b>see the index is restored, but the name is mangled, it is up to you to rename the indexes back:</b>

ops$tkyte%ORA11GR2> alter index "BIN$pet4jxIZCArgQAB/AQBrkA==$0" rename to emp_ename_idx;

Index altered.

ops$tkyte%ORA11GR2> select object_name, object_type from user_objects;

OBJECT_NAME                    OBJECT_TYPE
------------------------------ ------------
EMP                            TABLE

EMP_ENAME_IDX                  INDEX


A reader, August 14, 2011 - 10:27 pm UTC

Hi - In production, we have 2 kinds of systems. One is an oltp database and accepts online data and undergoes batch processing at night. We have another which is loaded once during the batch cycle but otherwise used only for reporting purposes.

The first database is still in 10g and the second system is getting upgraded to 11g.

In case of data corruption in these 2 databases, what would you recommend as the best flashback strategy ?

Can you recommend a flashback strategy for the first database if that gets upgraded to 11g as well.
Tom Kyte
August 15, 2011 - 2:23 am UTC

what type of corruption are you trying to protect against?

physical - that is the job of media recovery - your backups and being in archivelog mode.

logical - a bug in your processing - that is the job of either flashback database OR flashback table OR tablespace point in time recovery. It depends on your total set of needs and requirements.

You'd need to be a lot more specific about your needs.

Alexander, October 08, 2015 - 6:22 pm UTC

Hi guys,

Recently my understanding of flashback has been called into question and I was hoping you could clarify a couple of things for me.

I understand that flashback database is the only flashback operations to use flashback logs. I'm having a discussion with an Oracle employee stating that if I want to guarantee being able to flashback a table to a point in time past where my undo retention/size can provide, to turn on flashback database and it will look into flashback logs. I disagree with this and think it will just give the "ORA-" telling you the undo blocks are gone.

I did notice that you can apparently create a restore point for a table and maybe he's thinking of that which is similar enough to a restore point for flashback database that he thinks it must also use flashback logs. Or I'm just wrong.

Thanks.
Chris Saxon
October 09, 2015 - 12:57 am UTC

From the documentation:

"Prerequisites for Flashback Table:

The undo data in the undo tablespace must extend far enough back in time to satisfy the flashback target time or SCN.

The point to which you can perform Flashback Table is determined by the undo retention period, which is the minimal time for which undo data is kept before being recycled, and tablespace characteristics. The undo data contains information about data blocks before they were changed. The flashback operation uses undo to re-create the original data."

Flashback logs wont be used for flashback *table*

Hope this helps.