在python sqlite3模块中提交行为和原子性

时间:2012-11-30 10:04:52

标签: python sqlite commit atomic

如果我想创建一个表并在另一个表中插入一个新条目,可以这样做 在sqlite模块中成为原子?

请参阅http://docs.python.org/2/library/sqlite3.html上的文档:

  

默认情况下,sqlite3模块在a之前隐式打开事务   数据修改语言(DML)声明(即   INSERT / UPDATE / DELETE / REPLACE),并隐式提交事务   在非DML,非查询语句之前(即除了之外的任何其他语句)   选择或上述)。

     

因此,如果您在事务中并发出类似CREATE的命令   TABLE ...,VACUUM,PRAGMA,sqlite3模块将隐式提交   在执行该命令之前。这样做有两个原因。   首先是其中一些命令不起作用   交易。另一个原因是sqlite3需要跟踪   事务状态(如果事务处于活动状态)。

我不确定这第二段是否适用于自动启动 交易或手动和自动交易。

Sqlite docs http://www.sqlite.org/lang_transaction.html告诉我们手动交易 在显式COMMIT之前不会提交:

  

可以使用BEGIN命令手动启动事务。这样   事务通常持续到下一个COMMIT或ROLLBACK   命令。

假设我们有这样的事情:

con = sqlite3.connect(fdb) 
cur = con.cursor()

sql = 'begin transaciton'
cur.execute(sql)    

sql = 'CREATE TABLE some-table ...
cur.execute(sql)

# *** is there an implicit commit at this point ?! ***

sql = 'INSERT INTO  another-table ...
cur.execute(sql)

con.commit()

这会是原子的,还是python sqlite会在create table语句之后进行提交? 有没有办法使它成为原子?

2 个答案:

答案 0 :(得分:6)

你不能原子地这样做。每当执行COMMIT语句时,Python SQLite库都会隐式发出CREATE TABLE ..,因为SQLite在事务处于活动状态时不支持执行CREATE TABLE ..语句。 / p>

您可以通过在python解释器和sqlite3命令行工具中打开数据库来测试它。一旦发出CREATE TABLE ..语句,就可以在.schema命令行工具中运行sqlite3命令,并查看该语句的结果。

请注意,这意味着您在 CREATE TABLE ..语句之前在事务中所做的任何事情也将被提交。要以另一种方式查看,CREATE TABLE ..语句首先提交,然后启动完全事务。

答案 1 :(得分:3)

Python SQLite3库即使在不需要的情况下也会插入自动提交。

要使整个事务成为原子,请使用任何其他Python SQLite包装器,例如APSW