解析 Python Web 开发中的数据库与 ORM 技术

解析 Python Web 开发中的数据库与 ORM 技术

目录

  1. 🗂 数据库基础
    • 关系型数据库 vs NoSQL 数据库
  2. ⚙️ SQLAlchemy
    • ORM vs 原生 SQL
    • SQLAlchemy 基础(Session、Model、Query 等)
    • 关联查询、懒加载与急加载
    • 事务处理和回滚
  3. 🛠 Django ORM
    • Django ORM 的查询优化
    • 自定义 Manager 和 QuerySet
    • 数据库迁移(Django Migrations)
  4. ⏩ 异步数据库操作
    • 使用 databases 库处理异步数据库连接
    • 使用 Tortoise-ORM 实现异步 ORM 操作

1. 🗂 数据库基础

数据库是存储和管理数据的关键技术,分为关系型数据库和 NoSQL 数据库。关系型数据库通过表格来存储数据,遵循严格的模式约束和 ACID 特性;NoSQL 数据库则更加灵活,通常用于处理大规模和非结构化数据。

关系型数据库 vs NoSQL 数据库

关系型数据库(如 MySQL、PostgreSQL、SQLite)基于关系模型来组织数据,通常由多个表格组成,表格通过外键相互关联。它们提供了强大的查询语言(SQL),支持事务操作、数据一致性和复杂的查询优化。

-- 创建用户表的 SQL 语句
CREATE TABLE users (
    id SERIAL PRIMARY KEY,
    username VARCHAR(50) NOT NULL,
    email VARCHAR(100) NOT NULL UNIQUE
);

关系型数据库最适合结构化的数据和复杂查询。其优点包括数据一致性、高度的 ACID 支持和丰富的查询功能。缺点在于需要事先定义模式,并且对水平扩展支持不如 NoSQL 数据库。

NoSQL 数据库(如 MongoDB、Redis、Cassandra)提供了非结构化或半结构化的数据存储,通常以键值对、文档或图形结构进行组织。这类数据库不强制使用固定的模式,因此在处理动态或大规模数据时表现更好。

{
    "username": "john_doe",
    "email": "john@example.com",
    "hobbies": ["reading", "hiking"]
}

NoSQL 数据库的优点包括灵活的模式、横向扩展能力和对海量数据的处理。然而,由于缺乏一致性保障和事务支持,它们在某些应用场景中并不适用。


2. ⚙️ SQLAlchemy

SQLAlchemy 是 Python 最流行的 ORM(对象关系映射)框架之一,它为开发者提供了在 Python 代码中操作数据库的强大工具,允许在关系型数据库和对象之间无缝转换。

ORM vs 原生 SQL

ORM(对象关系映射) 提供了一种将数据库表映射为 Python 类的方式,开发者可以通过操作类对象来对数据库进行查询、插入和更新操作,而无需编写 SQL 语句。ORM 简化了数据库操作,并且在处理复杂关联时,能更好地提升开发效率。

from sqlalchemy import Column, Integer, String
from sqlalchemy.ext.declarative import declarative_base

Base = declarative_base()

# 定义 ORM 模型
class User(Base):
    __tablename__ = 'users'
    id = Column(Integer, primary_key=True)
    username = Column(String(50), nullable=False)
    email = Column(String(100), nullable=False, unique=True)

相比之下,原生 SQL 具有更高的灵活性和性能优势,尤其在复杂查询和优化场景中,开发者可以手动编写高度优化的 SQL 语句。ORM 在封装操作的同时,也可能导致一些性能上的开销。

SQLAlchemy 基础(Session、Model、Query 等)

在 SQLAlchemy 中,所有的数据库操作都围绕着 Session 对象展开,它是与数据库的会话接口,负责提交事务、执行查询并管理对象的生命周期。

from sqlalchemy import create_engine
from sqlalchemy.orm import sessionmaker

# 创建数据库引擎
engine = create_engine('sqlite:///app.db')
Session = sessionmaker(bind=engine)

# 创建会话
session = Session()

# 查询数据库
users = session.query(User).all()
for user in users:
    print(user.username)

SQLAlchemy 的 Model 是数据库表的 Python 映射,开发者可以通过定义类属性来创建数据库列。Query 对象用于生成 SQL 查询,并且支持链式调用,构建复杂查询条件。

# 查询带有条件的用户
active_users = session.query(User).filter(User.active == True).all()

关联查询、懒加载与急加载

关联查询 用于从多个表中提取相关数据。SQLAlchemy 通过 relationship 提供了外键关联,使得开发者可以轻松处理一对多、多对多等关联查询。

from sqlalchemy.orm import relationship

class Post(Base):
    __tablename__ = 'posts'
    id = Column(Integer, primary_key=True)
    title = Column(String(100), nullable=False)
    user_id = Column(Integer, ForeignKey('users.id'))

    # 定义关联关系
    user = relationship("User", back_populates="posts")

SQLAlchemy 支持 懒加载急加载,懒加载只在访问关联对象时才加载相关数据,而急加载则通过 join 一次性加载全部相关数据。

# 懒加载
user = session.query(User).get(1)
# 访问 posts 属性时才会查询关联的 Post 表
print(user.posts)

# 急加载
user = session.query(User).options(joinedload(User.posts)).get(1)
print(user.posts)

事务处理和回滚

事务是数据库操作的基本单位,SQLAlchemy 支持自动事务处理。通过 commit 提交事务,rollback 则用于回滚未完成的操作,确保数据的一致性。

try:
    new_user = User(username='jane_doe', email='jane@example.com')
    session.add(new_user)
    session.commit()  # 提交事务
except Exception as e:
    session.rollback()  # 出错时回滚
    print(f"Error: {e}")
finally:
    session.close()

事务处理机制确保了在操作失败时,数据库能够保持一致的状态,防止部分数据更新或异常数据写入。


3. 🛠 Django ORM

Django ORM 是 Django 框架自带的对象关系映射工具,它通过 Python 类与数据库表之间的映射,允许开发者以对象的方式进行数据库操作,极大简化了 SQL 的编写。

Django ORM 的查询优化

Django ORM 提供了许多内置的查询优化工具。开发者可以通过 select_relatedprefetch_related 来优化关联查询,避免 N+1 查询问题。

# select_related: 用于一对一和多对一关联
posts = Post.objects.select_related('user').all()

# prefetch_related: 用于多对多和反向关联
posts = Post.objects.prefetch_related('comments').all()

通过这些方法,Django 可以在一次查询中加载关联的数据,减少数据库查询的次数,从而提高性能。

自定义 Manager 和 QuerySet

Django ORM 允许开发者通过自定义 ManagerQuerySet 来扩展默认的查询方法。Manager 是数据库模型的接口,可以通过自定义 Manager 来添加新的查询逻辑。

class ActiveUserManager(models.Manager):
    def get_queryset(self):
        return super().get_queryset().filter(is_active=True)

class User(models.Model):
    username = models.CharField(max_length=100)
    is_active = models.BooleanField(default=True)

    # 使用自定义 Manager
    objects = ActiveUserManager()

自定义 QuerySet 则可以提供链式调用的方法,用于构建复杂的查询逻辑。

class UserQuerySet(models.QuerySet):
    def active(self):
        return self.filter(is_active=True)

class User(models.Model):
    username = models.CharField(max_length=100)

    # 绑定自定义 QuerySet
    objects = UserQuerySet.as_manager()

数据库迁移(Django Migrations)

Django 的 Migrations 系统提供了一种简单的方式来管理数据库模式的变更。开发者可以通过命令自动生成迁移脚本,并执行迁移操作。

python manage.py makemigrations
python manage.py migrate

Migrations 使得在项目开发过程中,数据库结构的变化能够被轻松地跟踪和管理。


4. ⏩ 异步数据库操作

随着 Web 应用对高并发的需求不断增加,异步

数据库操作变得越来越重要。在 Python 中,databases 库和 Tortoise-ORM 是处理异步数据库操作的两大主流工具。

使用 databases 库处理异步数据库连接

databases 是一个专门用于异步数据库访问的库,它支持主流的数据库引擎,并且可以与 FastAPI 等异步框架无缝集成。

import databases
import sqlalchemy

# 定义数据库 URL
DATABASE_URL = "sqlite:///./test.db"

# 初始化数据库连接
database = databases.Database(DATABASE_URL)
metadata = sqlalchemy.MetaData()

# 定义表
users = sqlalchemy.Table(
    "users", metadata,
    sqlalchemy.Column("id", sqlalchemy.Integer, primary_key=True),
    sqlalchemy.Column("name", sqlalchemy.String, nullable=False)
)

# 异步数据库操作
async def fetch_users():
    query = users.select()
    return await database.fetch_all(query)

databases 库提供了简单易用的 API,使得异步数据库操作像同步操作一样直观。

使用 Tortoise-ORM 实现异步 ORM 操作

Tortoise-ORM 是一个轻量级的异步 ORM,支持多种数据库引擎,包括 PostgreSQL、MySQL 和 SQLite。它采用了 Django ORM 的设计风格,但支持异步操作,适用于高并发场景。

from tortoise import Tortoise, fields
from tortoise.models import Model

# 定义模型
class User(Model):
    id = fields.IntField(pk=True)
    name = fields.CharField(max_length=50)

# 连接数据库
async def init():
    await Tortoise.init(
        db_url="sqlite://./test.db",
        modules={"models": ["__main__"]}
    )
    await Tortoise.generate_schemas()

# 异步查询
async def get_users():
    users = await User.all()
    for user in users:
        print(user.name)

Tortoise-ORM 提供了类似 Django ORM 的查询接口,但其异步支持使得在高并发应用中表现更加出色。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Switch616

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值