我想将一个或多个模型提交到数据库,并在每次测试后回滚它们。纯sqlalchemy
实现(在底部)以我期望的方式工作。但是,flask-sqlalchemy
实现无法在每次测试后回滚已提交的模型。
如何将flask-sqlalchemy
的作用域会话绑定到引擎的连接?
通用flask
app:
from flask import Flask
from flask_sqlalchemy import SQLAlchemy
app = Flask(__name__)
app.config['SQLALCHEMY_DATABASE_URI'] = 'sqlite://'
db = SQLAlchemy(app)
class A(db.Model):
id = db.Column(db.Integer, primary_key=True)
flask-sqlalchemy
testcase(不回滚):
from app import *
from unittest import TestCase
class Test(TestCase):
def setUp(self):
self.connection = db.engine.connect()
self.transaction = self.connection.begin()
options = dict(bind=self.connection, binds={})
self.session = db.create_scoped_session(options=options)
db.session = self.session
self.addCleanup(self.cleanup)
def cleanup(self):
self.transaction.rollback()
self.connection.close()
self.session.remove()
@classmethod
def setUpClass(cls):
db.create_all()
@classmethod
def tearDownClass(cls):
pass
def test_1(self):
a = A()
db.session.add(a)
db.session.commit()
assert len(db.session.query(A).all()) == 1
def test_2(self):
assert len(db.session.query(A).all()) == 0 # len is 1
sqlalchemy
testcase(有效):
from sqlalchemy import *
from sqlalchemy.orm import *
from sqlalchemy.ext.declarative import declarative_base
from unittest import TestCase
Base = declarative_base()
class A(Base):
__tablename__ = 'test'
id = Column(Integer, primary_key=True)
class Test(TestCase):
def setUp(self):
self.connection = e.connect()
self.transaction = self.connection.begin()
# Begin scoped session
factory = sessionmaker(bind=self.connection)
self.session = scoped_session(factory)
self.addCleanup(self.cleanup)
def cleanup(self):
self.session.close()
self.transaction.rollback()
self.connection.close()
@classmethod
def setUpClass(cls):
global e
e = create_engine("sqlite://")
Base.metadata.create_all(e)
@classmethod
def tearDownClass(cls):
pass
def test_1(self):
a = A()
self.session.add(a)
self.session.commit()
assert len(self.session.query(A).all()) == 1
def test_2(self):
assert len(self.session.query(A).all()) == 0
答案 0 :(得分:1)
我遇到了同样的问题,也许我的修复与你的一样。
这是我的setUp和tearDown:
import unittest
from my_app import db
class Test(unittest.TestCase):
def setUp(self):
self.connection = db.engine.connect()
self.trans = self.connection.begin()
db.session.configure(bind=self.connection, binds={})
def tearDown(self):
self.trans.rollback()
self.connection.close()
db.session.remove()
对我来说实际上是在添加:
binds={}
我还没有真正调查过为什么会修复它,但它确实适用于我。如果有人知道为什么空的dict绑定可以修复问题,我很乐意听到。