如何使用SQLAlchemy创建新数据库?
使用SQLAlchemy时,可以这样创建一个引擎对象:
from sqlalchemy import create_engine
engine = create_engine("postgresql://localhost/mydb")
如果在调用create_engine
时指定的数据库(这里是mydb
)不存在,那么访问engine
就会失败。有没有办法让SQLAlchemy在指定的数据库不存在时自动创建一个新的数据库呢?
6 个回答
17
在创建数据库的时候,可以通过给 create_engine
函数设置 isolation_level='AUTOCOMMIT'
来避免手动管理事务。
import sqlalchemy
with sqlalchemy.create_engine(
'postgresql:///postgres',
isolation_level='AUTOCOMMIT'
).connect() as connection:
connection.execute('CREATE DATABASE my_database')
另外,如果你不确定数据库是否已经存在,可以通过抑制 sqlalchemy.exc.ProgrammingError
这个错误来忽略数据库创建时因为已存在而产生的错误。
import contextlib
import sqlalchemy.exc
with contextlib.suppress(sqlalchemy.exc.ProgrammingError):
# creating database as above
204
SQLAlchemy-Utils 是一个为 SQLAlchemy 提供自定义数据类型和各种实用功能的工具。你可以通过 pip 安装最新的官方版本:
pip install sqlalchemy-utils
这些 数据库助手 包含一个 create_database
函数:
from sqlalchemy import create_engine
from sqlalchemy_utils import database_exists, create_database
engine = create_engine("postgres://localhost/mydb")
if not database_exists(engine.url):
create_database(engine.url)
print(database_exists(engine.url))
130
在Postgres中,默认情况下通常会有三个数据库。如果你能以超级用户身份连接(比如使用postgres
这个角色),那么你可以连接到postgres
或template1
这两个数据库。默认的pg_hba.conf文件只允许名为postgres
的Unix用户使用postgres
角色,所以最简单的方法就是直接切换到这个用户。无论如何,像往常一样创建一个引擎,使用一个有权限创建数据库的用户:
>>> engine = sqlalchemy.create_engine("postgres://postgres@/postgres")
不过,你不能使用engine.execute()
,因为Postgres不允许在事务中创建数据库,而sqlalchemy总是试图在事务中运行查询。为了绕过这个限制,你需要从引擎中获取底层连接:
>>> conn = engine.connect()
但是这个连接仍然在一个事务中,所以你必须用commit
来结束这个打开的事务:
>>> conn.execute("commit")
然后你就可以使用正确的PostgreSQL命令来创建数据库了。
>>> conn.execute("create database test")
>>> conn.close()