Files

61 lines
1.9 KiB
Python
Raw Permalink Normal View History

2026-08-22 22:28:41 +08:00
"""
数据库连接与初始化模块。
职责:
- 建立 SQLite + SQLAlchemy 连接(引擎)
- 提供会话工厂 SessionLocal 与 FastAPI 依赖 get_db
- 提供数据库初始化函数 init_db()
"""
import os
from pathlib import Path
from dotenv import load_dotenv
from sqlalchemy import create_engine
from sqlalchemy.orm import declarative_base, sessionmaker
# 定位 backend 目录与项目根目录(与 backend 同级)
BACKEND_DIR = Path(__file__).resolve().parent
PROJECT_ROOT = BACKEND_DIR.parent
# 读取项目根目录下的 .env 配置文件(若存在)
load_dotenv(PROJECT_ROOT / ".env")
# 数据库地址:默认使用 backend 目录下的 SQLite 文件,可通过 .env 的 DATABASE_URL 覆盖(留空视为使用默认值)
DATABASE_URL = os.getenv("DATABASE_URL") or f"sqlite:///{(BACKEND_DIR / 'blog.db').as_posix()}"
# 创建 SQLAlchemy 引擎
# SQLite 需关闭 check_same_threadFastAPI 多线程处理请求时会跨线程复用会话
engine = create_engine(
DATABASE_URL,
connect_args={"check_same_thread": False} if DATABASE_URL.startswith("sqlite") else {},
)
# 会话工厂:每个请求创建独立会话,避免线程安全问题
SessionLocal = sessionmaker(autocommit=False, autoflush=False, bind=engine)
# 所有 ORM 模型的公共声明基类
Base = declarative_base()
def get_db():
"""FastAPI 依赖注入:提供数据库会话,请求结束后自动关闭。"""
db = SessionLocal()
try:
yield db
finally:
db.close()
def init_db() -> None:
"""初始化数据库:创建所有已注册 ORM 模型对应的数据表。"""
# 延迟导入模型,确保全部模型注册到 Base.metadata 后再建表
from . import models # noqa: F401
Base.metadata.create_all(bind=engine)
if __name__ == "__main__":
# 支持直接运行:python -m backend.database
init_db()
print(f"数据库初始化完成:{DATABASE_URL}")