运行以下python脚本两次会抛出此错误:
peewee.ProgrammingError: relation "test_table" already exists
因为该表未在 .rollback()上删除。删除内部事务( with test_db.atomic())有效。为什么内部事务(根据documentation只是保存点)不会被回滚?
from datetime import datetime
from peewee import Model, DateTimeField
from playhouse.postgres_ext import PostgresqlExtDatabase
"""
CREATE ROLE test WITH LOGIN;
DROP DATABASE IF EXISTS test;
CREATE DATABASE test WITH OWNER test;
"""
CREDENTIALS = {
"database": "test",
"user": "test",
"password": None,
"host": "localhost",
"port": 5432,
"register_hstore": False,
}
test_db = PostgresqlExtDatabase(**CREDENTIALS)
test_db.connect()
test_db.set_autocommit(False)
test_db.begin() # start transaction
class TestTable(Model):
timestamp = DateTimeField(null=False, default=datetime(1970,1,1,0,0,0,))
class Meta:
db_table = "test_table"
database = test_db
with test_db.atomic():
TestTable.create_table()
TestTable.create()
test_db.rollback() # rollback transaction
print TestTable.get().timestamp
test_db.close()
版本
peewee==2.8.3
psycopg2==2.6.2
PostgreSQL 9.5.1 on x86_64-apple-darwin15.3.0, compiled by Apple LLVM version 7.0.2 (clang-700.1.81), 64-bit
答案 0 :(得分:0)
根据您使用的数据库,DDL(架构更改)可能会或可能不会回滚。
Postgresql和SQLite似乎都支持回滚DDL,但MySQL不支持。
但是,SQLite的Python驱动程序有一个错误,导致它在您发出DDL时发出COMMIT。第一个补丁是在2010年提交的:http://bugs.python.org/issue10740。
另请查看pysqlite2,它与标准库sqlite3基本相同: