2012-08-10 65 views
2

如果使用事务并且sql操作失败,我知道它会回滚所有更改,但会在finally语句后暂停所有代码,还是会继续运行其他代码?在android中的事务失败后究竟发生了什么?

像下面的代码看起来是否正确或应该使用catch语句?是否有可能为测试目的而模拟错误?

public static boolean updateSuccessful = false; 

updateToVersion2(); 
//Does anything after here still run on error? 

if(!updateSuccessful) { 
    deleteAndRecreateDatabase(); 
} 


public void updateToDbVersion2() { 
    this.myDataBase.beginTransaction(); 
    try { 
     this.myDataBase.execSQL("UPDATE myRecords SET column = 'newValue1' WHERE _id = 1"); 
     this.myDataBase.execSQL("UPDATE myRecords SET column = 'newValue2' WHERE _id = 2"); 
     this.myDataBase.setTransactionSuccessful(); 
     // This is not reached on update error, right? 
     updateSuccessful = true; 
    } finally { 
     this.myDataBase.endTransaction(); 
    } 
} 

回答

0

一个transacti各地本身就是整体行为。无论是成功的还是失败的,这意味着您要么以数据库的形式获取所有数据,要么您什么都没有(当然是在这个交易中)。 如果事务在某个时候失败了,它应该先到达“catch”部分,然后再到“finally”。

正如user827992指出的那样,捕捉异常是很有趣的。那里可能会有一些额外的(也许是有价值的)信息。

+0

因此没有什么特别的事情发生。它会像其他任何错误一样失败,但是如果使用事务,它将不会对数据库进行部分更改。 – Jack 2012-08-12 21:53:16

+0

是的,但仍然推荐使用它们。请注意,数据库中的每个操作都会打开一个单独的事务。这个过程大部分时间都在进行。如果你在同一事务之外提交了20个更改到你的数据库,那么处理时间将乘以20.如果你在同一个事务中包含所有这些更改,那么它只需要几毫秒。 – 2012-08-13 10:34:36

+0

感谢您的信息。我认为这比实际更复杂。 – Jack 2012-08-15 01:33:57

1

你应该抓住例外!为什么你放弃它会使代码闻起来不好...

如果在execSQLsetTransactionSuccessful之间确实发生了异常并且最终落入您要结束事务的finally部分,该怎么办?

的代码可能是这样的:

public void updateToDbVersion2() { 
    boolean fubar = false; 
    this.myDataBase.beginTransaction(); 
    try { 
     this.myDataBase.execSQL("UPDATE myRecords SET column = 'newValue1' WHERE _id = 1"); 
     this.myDataBase.execSQL("UPDATE myRecords SET column = 'newValue2' WHERE _id = 2"); 
     this.myDataBase.setTransactionSuccessful(); 
     // This is not reached on update error, right? 
     updateSuccessful = true; 
    } catch(Exception ex){ 
     fubar = true; 
     // Do whatever is needed to be done such as logcat FOR debugging ONLY! 
    } finally { 
     if (!fubar){ 
      // No exceptions occurred, OK to end transaction 
      this.myDataBase.endTransaction(); 
     } 
    } 
} 

注意在finally子句条件检查如何确保预防潜在的混乱的结果,并确保数据的完整性。

+1

这是必要的吗?我的理解是,最终将永远运行,如果endTransaction在没有setTransactionSuccessful的情况下到达,它将回滚事务 – Jack 2012-08-12 22:08:01