我正在努力使用 SQLAlchemy 为 Postgresql 数据库自动创建表。
在我的模块中,我定义了一个
base.py
:
from sqlalchemy import MetaData
from sqlalchemy.orm import DeclarativeBase, Session
class Base(DeclarativeBase):
# Ensure all models use the public schema by default
metadata = MetaData(schema='public')
__abstract__ = True
def __eq__(self, other):
return True
def to_dict(self) -> dict:
"""Converts the fields (columns) of a class to a dictionary without the '_sa_instance_state' key."""
return {field.name: getattr(self, field.name) for field in self.__table__.c}
@classmethod
def get_count(cls, session: Session) -> int:
"""Get the count of rows in the table."""
return session.query(cls).count()
然后我在我的
models.py
中定义了一个表
from sqlalchemy import Column, DateTime, Integer, Float, ForeignKey
from sqlalchemy.orm import relationship
from .base import Base
class SensorData(Base):
__tablename__ = 'sensor_data'
trip_id = Column(Integer, primary_key=True)
timestamp = Column(DateTime, primary_key=True)
acceleration_x = Column(Float)
# Other fields...
和我的
database.py
中的数据库对象:
from sqlalchemy import create_engine, MetaData
from .models import SensorData # Models imported after Base
from .base import Base
class Database:
def __init__(self):
from sqlalchemy.engine.url import URL
url_object = URL.create(
drivername="postgresql+psycopg2",
username="username",
password="password",
host="localhost",
port=5432,
database="database"
)
self.engine = create_engine(url_object, echo=True)
self.metadata = MetaData(schema='public')
# Explicitly bind metadata and engine to the Base class
Base.metadata = self.metadata
Base.metadata.bind = self.engine
Base.metadata.create_all(self.engine) # Table creation
在代码的其他部分,我想创建数据库对象,并创建表(如果它们尚不存在)(在公共模式中)
db = Database()
所有代码执行都没有错误,但是没有创建任何表。数据库用户还应该有足够的权限。根据我的阅读,导入类的顺序很重要,但我不确定如何确保使用当前的代码设置正确导入所有内容?
在创建表之前,您需要初始化基类的所有子类声明
如果你有下一个结构
project
└── __init__.py
└── models.py
└── database.py
您可以在
__init__.py
中执行下一步
from .models import *
from .database import Database
db = Database()