DBF: ROLLBACK (built-in feature)

DBF: ROLLBACK (built-in feature)

Postby nageswaragunupudi » Sat Sep 10, 2022 4:32 am

It is less known, but ROLLBACK feature is already built into our DBFCDX and DBFNTX RDDs. I have not tested with other RDDs.
This feature exists in the RDDs for many years.

Simple Syntax:
Code: Select all  Expand view

dbInfo( DBI_ROLLBACK )
 


This rolls back any modifications (including DBDELETE() and DBRECALL()) made to the current record in the current work area.

Just like any RDBMS, RollBack does not work after COMMIT.

FWH was using this feature in TDataBase class for many years. Please see METHOD RollBack().

Limitations of DBF ROLLBACK feature:
1) Rollback works only if the record pointer is not changed. Any SKIP() operation implicitly commits the transaction.
So, we can not use this RollBack with more than one record in the same work area.
While programming we need to remember this carefully.

2) RollBack does not work with DBAPPEND(). In real time applications, we need to use some work arounds.

We already know the functions:
dbCommit() // works on current work area and
dbCommitAll() // command COMMIT.

From the next version FWH provides two new functions:
dbRollBack() and
dbRollBackAll()

Source code of these functions:
Code: Select all  Expand view

function DBROLLBACK()

   if DbRecordInfo( DBRI_UPDATED )
      DbInfo( DBI_ROLLBACK )
   endif

return nil

//----------------------------------------------------------------------------//

function DBROLLBACKALL()

   local n, cAlias

   for n := 1 to 255
      if !Empty( cAlias := ALIAS( n ) ) .and. ( cAlias )->( RDDNAME() ) $ "DBFCDX,DBFNTX"
         ( cAlias )->( dbRollBack() )
      endif
   next

return nil
 


Here is a test program:
Code: Select all  Expand view
#include "fivewin.ch"

REQUEST DBFCDX

function Main()

   local cCust, cStat
   local cFirst, cName

   USE CUSTOMER NEW SHARED ALIAS ( cCust := cGetNewAlias( "CUST" ) ) VIA "DBFCDX"
   USE STATES   NEW SHARED ALIAS ( cStat := cGetNewAlias( "STAT" ) ) VIA "DBFCDX"

   // save values
   cFirst      := ( cCust )->FIRST
   cName       := ( cStat )->NAME

   // Start testing

   TRY
      if ( cCust )->( RLOCK() ) .and. ( cStat )->( RLOCK() )

         ? "Original Values:", ( cCust )->FIRST, ( cStat )->NAME
         ( cCust )->FIRST  := NTOCDOW( hb_RandomInt( 1, 7 ) )
         ( cStat )->NAME   := NTOCMONTH( hb_RandomInt( 1, 12 ) )
         ? "Modified Values:", ( cCust )->FIRST, ( cStat )->NAME

         if Alert( "CHOOSE", { "COMMIT", "ROLLBACK" }, "OPTION" ) == 1
            COMMIT
            UNLOCK ALL
         else
            dbRollBackAll()
            UNLOCK ALL
         endif
      else
         UNLOCK ALL
      endif

   CATCH
      dbRollBackAll()
      UNLOCK ALL
   END

   ? "Final Values:", ( cCust )->FIRST, ( cStat )->NAME

   // Restore Values

   if ( cCust )->( RLOCK() ) .and. ( cStat )->( RLOCK() )
      ( cCust )->FIRST  := cFirst
      ( cStat )->NAME   := cName
      COMMIT
      UNLOCK ALL
   endif

   CLOSE DATA

return nil
 


Caution:
We should not modify more than one record in the same workarea.
If we want to modify more than one record in the same dbf, we need to open the same dbf in different workareas

This is not difficult. I successfully used transaction tracking with DBFs.
Regards

G. N. Rao.
Hyderabad, India
User avatar
nageswaragunupudi
 
Posts: 10259
Joined: Sun Nov 19, 2006 5:22 am
Location: India

Re: DBF: ROLLBACK (built-in feature)

Postby Antonio Linares » Sat Sep 10, 2022 7:35 am

Dear Rao,

many thanks!
regards, saludos

Antonio Linares
www.fivetechsoft.com
User avatar
Antonio Linares
Site Admin
 
Posts: 41332
Joined: Thu Oct 06, 2005 5:47 pm
Location: Spain


Return to FiveWin for Harbour/xHarbour

Who is online

Users browsing this forum: Google [Bot] and 15 guests