SQLAlchemy为定义数据库表提供了一个非常干净的界面:
engine = create_engine('sqlite:///:memory:')
metadata = MetaData()
user = Table('user', metadata,
Column('user_id', Integer, primary_key = True),
Column('user_name', String(16), nullable = False),
Column('email_address', String(60), key='email'),
Column('password', String(20), nullable = False)
)
user_prefs = Table('user_prefs', metadata,
Column('pref_id', Integer, primary_key=True),
Column('user_id', Integer, ForeignKey("user.user_id"), nullable=False),
Column('pref_name', String(40), nullable=False),
Column('pref_value', String(100))
)
一旦定义了这些表,就可以很容易地使用metadata.create_all(engine)
函数创建这些表。当您想要创建不会干扰生产中使用的现有表的表时,这对于测试尤其有用。
我目前正在开发的项目在很大程度上依赖于postgres中的用户定义函数。是否有一种干净的方法来使用SQLAlchemy定义这些函数,以便metadata.create_all(engine)
正确地创建函数以及相应的表?
答案 0 :(得分:6)
我今天一直在做类似的事情。到目前为止,我发现最好的方法是使用sqlalchemy sbt run
事件监听器。对于常规函数,您可以将事件绑定到元数据,但是对于特定于表的函数,您可以绑定到表。例如:
before_create
如果要在创建表之前创建函数,可以只用表替换元数据。
每次拨打import sqlalchemy
from sqlalchemy.schema import DDL
sqlalchemy.event.listen(
metadata,
'before_create',
DDL('CREATE OR REPLACE FUNCTION myfunc() ...')
)
时,此DDL似乎都会运行,因此使用metadata.create_all
非常重要。如果您想要更多地控制何时创建函数,您可能更适合使用alembic或类似的迁移。
这里的sqlalchemy文档中描述了DDL的一些用法:http://docs.sqlalchemy.org/en/latest/core/ddl.html#custom-ddl