国产精品电影_久久视频免费_欧美日韩国产激情_成年人视频免费在线播放_日本久久亚洲电影_久久都是精品_66av99_九色精品美女在线_蜜臀a∨国产成人精品_冲田杏梨av在线_欧美精品在线一区二区三区_麻豆mv在线看

SQLModel, 一個神奇的 Python 庫

開發(fā)
「SQLModel」 是一個基于 Python 類型注解的現(xiàn)代 ORM(對象關系映射)庫,由 FastAPI 的作者 Sebastián Ramírez 開發(fā)。

一直使用SQlAlchemy和Pydantic組合,有人推薦使用SQLModel。今天學習一下。

1. 什么是 SQLModel?

「SQLModel」 是一個基于 Python 類型注解的現(xiàn)代 ORM(對象關系映射)庫,由 FastAPI 的作者 Sebastián Ramírez 開發(fā)。它結合了 「Pydantic」 的數(shù)據驗證和序列化能力與 「SQLAlchemy」 的數(shù)據庫操作能力。

核心特性:

  • 類型安全:完整的 Python 類型提示支持
  • 代碼簡潔:使用 Python 現(xiàn)代語法,代碼量少
  • 無縫集成:與 FastAPI 完美集成
  • 強大功能:基于 SQLAlchemy,具備所有高級數(shù)據庫功能
  • 開發(fā)體驗:優(yōu)秀的編輯器支持和自動補全

2. 使用場景

(1) Web API 開發(fā)
from fastapi import FastAPI
from sqlmodel import SQLModel, Field, Session, create_engine, select

app = FastAPI()

class User(SQLModel, table=True):
    id: int | None = Field(default=None, primary_key=True)
    username: str = Field(index=True)
    email: str

@app.get("/users/{user_id}")
def get_user(user_id: int, session: Session = Depends(get_session)):
    user = session.get(User, user_id)
    return user

(2) 數(shù)據密集型應用

  • 報表系統(tǒng)
  • 數(shù)據分析平臺
  • 內容管理系統(tǒng)

(3) 微服務架構

  • 每個服務獨立的數(shù)據庫模型
  • 類型安全的服務間通信
(4) 快速原型開發(fā)
  • 快速定義數(shù)據模型
  • 自動生成數(shù)據庫表結構

3. 基礎示例

(1) 基本模型定義

from sqlmodel import SQLModel, Field
from typing import Optional

class Hero(SQLModel, table=True):
    id: Optional[int] = Field(default=None, primary_key=True)
    name: str = Field(index=True)
    secret_name: str
    age: Optional[int] = None

(2) 數(shù)據庫設置

from sqlmodel import create_engine, Session

# 創(chuàng)建數(shù)據庫引擎
engine = create_engine("sqlite:///database.db")

# 創(chuàng)建表
SQLModel.metadata.create_all(engine)

# 獲取會話
def get_session():
    with Session(engine) as session:
        yield session

(3) CRUD 操作

# 創(chuàng)建
def create_hero(name: str, secret_name: str, age: int | None = None):
    with Session(engine) as session:
        hero = Hero(name=name, secret_name=secret_name, age=age)
        session.add(hero)
        session.commit()
        session.refresh(hero)
        return hero

# 讀取
def get_heroes():
    with Session(engine) as session:
        heroes = session.exec(select(Hero)).all()
        return heroes

# 更新
def update_hero(hero_id: int, new_age: int):
    with Session(engine) as session:
        hero = session.get(Hero, hero_id)
        hero.age = new_age
        session.add(hero)
        session.commit()
        return hero

# 刪除
def delete_hero(hero_id: int):
    with Session(engine) as session:
        hero = session.get(Hero, hero_id)
        session.delete(hero)
        session.commit()

4. 進階示例

(1) 關系模型

from sqlmodel import SQLModel, Field, Relationship
from typing import Optional, List

class Team(SQLModel, table=True):
    id: Optional[int] = Field(default=None, primary_key=True)
    name: str = Field(index=True)
    headquarters: str
    
    # 一對多關系
    heroes: List["Hero"] = Relationship(back_populates="team")

class Hero(SQLModel, table=True):
    id: Optional[int] = Field(default=None, primary_key=True)
    name: str = Field(index=True)
    secret_name: str
    age: Optional[int] = None
    
    # 多對一關系
    team_id: Optional[int] = Field(default=None, foreign_key="team.id")
    team: Optional[Team] = Relationship(back_populates="heroes")

(2) 復雜查詢

from sqlmodel import select, and_, or_

# 條件查詢
def get_heroes_by_age(min_age: int, max_age: int):
    with Session(engine) as session:
        statement = select(Hero).where(
            and_(
                Hero.age >= min_age,
                Hero.age <= max_age
            )
        )
        heroes = session.exec(statement).all()
        return heroes

# 關聯(lián)查詢
def get_heroes_with_teams():
    with Session(engine) as session:
        statement = select(Hero, Team).join(Team)
        results = session.exec(statement).all()
        return results

# 分頁查詢
def get_heroes_paginated(skip: int = 0, limit: int = 10):
    with Session(engine) as session:
        statement = select(Hero).offset(skip).limit(limit)
        heroes = session.exec(statement).all()
        return heroes

(3) 事務處理

from sqlmodel import Session

def transfer_hero_to_team(hero_id: int, new_team_id: int):
    with Session(engine) as session:
        try:
            hero = session.get(Hero, hero_id)
            new_team = session.get(Team, new_team_id)
            
            ifnot hero ornot new_team:
                raise ValueError("Hero or Team not found")
            
            # 更新關聯(lián)
            old_team_id = hero.team_id
            hero.team_id = new_team_id
            
            session.add(hero)
            session.commit()
            
            return {"message": "Transfer successful"}
            
        except Exception as e:
            session.rollback()
            raise e

(4) 繼承和多態(tài)

class BaseUser(SQLModel):
    id: Optional[int] = Field(default=None, primary_key=True)
    email: str = Field(unique=True, index=True)
    is_active: bool = True

class RegularUser(BaseUser, table=True):
    __tablename__ = "regular_users"
    username: str

class AdminUser(BaseUser, table=True):
    __tablename__ = "admin_users"
    admin_level: int = Field(default=1)

(5) 混合 Pydantic 模型

from pydantic import EmailStr

# 僅用于驗證的 Pydantic 模型
class UserCreate(SQLModel):
    username: str
    email: EmailStr
    password: str

class UserResponse(SQLModel):
    id: int
    username: str
    email: str
    is_active: bool

# 數(shù)據庫模型
class User(SQLModel, table=True):
    id: Optional[int] = Field(default=None, primary_key=True)
    username: str = Field(index=True)
    email: str = Field(unique=True, index=True)
    hashed_password: str
    is_active: bool = True

(6) FastAPI 集成

from fastapi import FastAPI, Depends, HTTPException
from sqlmodel import Session, select

app = FastAPI()

@app.post("/users/", response_model=UserResponse)
def create_user(user: UserCreate, session: Session = Depends(get_session)):
    # 檢查用戶是否存在
    existing_user = session.exec(
        select(User).where(User.email == user.email)
    ).first()
    
    if existing_user:
        raise HTTPException(status_code=400, detail="Email already registered")
    
    # 創(chuàng)建用戶
    hashed_password = get_password_hash(user.password)
    db_user = User(
        username=user.username,
        email=user.email,
        hashed_password=hashed_password
    )
    
    session.add(db_user)
    session.commit()
    session.refresh(db_user)
    
    return db_user

@app.get("/users/{user_id}", response_model=UserResponse)
def read_user(user_id: int, session: Session = Depends(get_session)):
    user = session.get(User, user_id)
    ifnot user:
        raise HTTPException(status_code=404, detail="User not found")
    return user

5. 優(yōu)缺點分析

(1) 優(yōu)點

① 開發(fā)效率高

# 傳統(tǒng) SQLAlchemy
from sqlalchemy import Column, Integer, String
from sqlalchemy.ext.declarative import declarative_base

Base = declarative_base()

class User(Base):
    __tablename__ = 'users'
    id = Column(Integer, primary_key=True)
    name = Column(String)
    email = Column(String)

# SQLModel - 更簡潔
class User(SQLModel, table=True):
    id: int | None = Field(default=None, primary_key=True)
    name: str
    email: str

② 類型安全

# 編輯器支持自動補全和類型檢查
user = User(name="John", email="john@example.com")
print(user.name)  # 編輯器知道這是字符串

 ③ 與 FastAPI 完美集成

@app.post("/users/")
def create_user(user: UserCreate):  # 自動驗證和文檔生成
    return User.from_orm(user)

④ 數(shù)據驗證

from pydantic import validator

class User(SQLModel, table=True):
    email: str
    
    @validator('email')
    def validate_email(cls, v):
        if '@' not in v:
            raise ValueError('Invalid email')
        return v

⑤ 現(xiàn)代化語法

# 使用現(xiàn)代 Python 特性
class Config:
    arbitrary_types_allowed = True

(2) 缺點

 ① 相對較新

  • 社區(qū)生態(tài)不如 Django ORM 或成熟期的 SQLAlchemy
  • 可能遇到邊緣情況的 bug

② 學習曲線

# 需要理解 SQLAlchemy 和 Pydantic 的概念
# 對于新手來說概念較多

③ 性能考慮

# 額外的驗證層可能帶來輕微性能開銷
# 但在大多數(shù) Web 應用中可忽略不計

④ 遷移成本

  • 從現(xiàn)有 SQLAlchemy 項目遷移需要重構
  • 某些高級 SQLAlchemy 功能可能不支持

⑤ 文檔和資源

  • 相比成熟的 ORM,學習資源較少
  • 社區(qū)案例相對有限

6. 與其他 ORM 對比

(1) vs Django ORM

# Django ORM
class User(models.Model):
    name = models.CharField(max_length=100)
    email = models.EmailField()

# SQLModel - 更 Pythonic,類型安全
class User(SQLModel, table=True):
    name: str
    email: str

(2) vs SQLAlchemy Core

# SQLAlchemy Core - 更靈活但更冗長
users = Table('users', metadata,
    Column('id', Integer, primary_key=True),
    Column('name', String),
    Column('email', String)
)

# SQLModel - 更簡潔
class User(SQLModel, table=True):
    id: int | None = Field(default=None, primary_key=True)
    name: str
    email: str

(3) vs Pony ORM

# Pony ORM - 獨特的語法
class User(db.Entity):
    name = Required(str)
    email = Required(str)

# SQLModel - 標準的 Python 語法
class User(SQLModel, table=True):
    name: str
    email: str

7. 優(yōu)秀實踐

(1) 項目結構

myproject/
├── models/
│   ├── __init__.py
│   ├── base.py
│   ├── user.py
│   └── post.py
├── schemas/
│   ├── request.py
│   └── response.py
├── crud/
│   └── user.py
├── database.py
└── main.py

(2) 配置管理

# database.py
from sqlmodel import create_engine, Session
import os

DATABASE_URL = os.getenv("DATABASE_URL", "sqlite:///./test.db")

engine = create_engine(
    DATABASE_URL,
    echo=True,  # 開發(fā)時顯示 SQL 語句
    connect_args={"check_same_thread": False}  # SQLite 需要
)

def get_session():
    with Session(engine) as session:
        yield session

(3) 錯誤處理

from sqlmodel import SQLModel, Field, Session
from contextlib import contextmanager

@contextmanager
def session_scope():
    """提供事務范圍的會話"""
    session = Session(engine)
    try:
        yield session
        session.commit()
    except Exception:
        session.rollback()
        raise
    finally:
        session.close()

def safe_create_user(user_data: dict):
    with session_scope() as session:
        user = User(**user_data)
        session.add(user)
        return user

8. 總結

SQLModel 是一個現(xiàn)代化的 ORM 選擇,特別適合:

  • 新項目:尤其是使用 FastAPI 的項目
  • 類型安全要求高:需要完整類型提示的項目
  • 開發(fā)效率優(yōu)先:希望減少樣板代碼的團隊
  • 現(xiàn)代 Python 技術棧:使用 Python 3.6+ 新特性的項目

在選擇 SQLModel 時,需要考慮項目的具體需求、團隊的技術背景以及對新興技術的接受程度。對于大型企業(yè)級應用,可能需要評估其成熟度;而對于初創(chuàng)公司和快速迭代的項目,SQLModel 的開發(fā)效率優(yōu)勢非常明顯。

責任編輯:趙寧寧 來源: 程序員老朱
相關推薦

2025-06-04 08:05:00

Peewee?數(shù)據庫開發(fā)

2025-08-01 09:07:00

RapidFuzz字符串匹配庫Python

2025-06-09 10:15:00

FastAPIPython

2025-06-05 10:00:00

GensimPython

2025-06-04 10:05:00

Gooey開源Python

2025-05-29 10:00:00

ZODBPython數(shù)據庫

2025-06-05 08:10:00

PyneconePythonWeb 應用

2025-06-10 08:00:00

Pygalpython

2025-06-09 07:25:00

filelock數(shù)據庫

2025-08-01 06:15:00

RQPython

2025-05-27 08:00:00

Pythonemoji

2024-04-01 05:00:00

GUIpythonDearPyGui

2025-05-28 08:00:00

Pythonpython-jos開發(fā)

2024-05-23 15:20:36

SQLModelPython

2025-06-03 10:00:00

LiteLLMPython

2025-06-03 08:30:00

PotteryRedisPython

2014-04-23 11:11:27

Linux下載管理器uGet

2020-06-08 07:52:31

Python開發(fā)工具

2023-01-16 18:16:49

CinnamonLinux桌面環(huán)境

2011-11-02 12:38:12

華為華為ARG3
點贊
收藏

51CTO技術棧公眾號

亚洲最新av网址| 国产欧美啪啪| av免费不卡国产观看| 成人av网站在线| 中文字幕av不卡| 成人美女免费网站视频| 久久精品青草| 亚洲五码中文字幕| 日韩欧美在线番号| 不卡的电视剧免费网站有什么| 精品国产区一区二区三区在线观看| 日韩精品无码一区二区三区免费 | 国产精品av久久久久久麻豆网| 国产精品免费在线免费| 污网站在线免费看| 午夜精品福利视频网站| 成人网18入口| 国产亚洲va综合人人澡精品| 日韩伦理精品| 国产综合在线视频| 欧美va天堂| 欧美美女18p| 亚洲图片在线| 成人黄色短视频在线观看| 国产a级网站| 国产精品美女www爽爽爽| 黄色一级片国产| 精品一区二区三区视频在线观看| 天堂资源在线亚洲视频| 精品一二线国产| 99精品一区二区三区的区别| 国产精品一区二区免费不卡| 久久精品国产sm调教网站演员| 99视频一区二区| 最新天堂中文在线| 亚洲成人黄色影院| 在线观看精品一区二区三区| 精品国精品国产尤物美女| 亚洲午夜天堂| 欧美国产乱视频| 任你弄精品视频免费观看| 国产精品天天狠天天看| 欧美精品一区在线播放| 神马香蕉久久| 亚洲91精品在线观看| 妖精一区二区三区精品视频| 热re99久久精品国产66热| 精品国产乱码| 九九九九精品| 国产麻豆精品95视频| 日本国产在线播放| 日韩一区有码在线| 污导航在线观看| 欧美日韩成人综合| 韩国美女久久| 久久久久久久久电影| 99久久视频| 日韩欧美第二区在线观看| 极品少妇一区二区| 妺妺窝人体色www在线小说| 亚洲尤物视频在线| 色婷婷视频在线观看| 另类专区欧美制服同性| 91精品国产乱码久久久久久久| 日韩精品第一页| 中文字幕av免费专区久久| 深夜福利在线视频| 亚洲欧洲黄色网| 色婷婷色综合| 国产内射老熟女aaaa| 一个色综合网站| 在线播放蜜桃麻豆| 欧美国产第二页| 亚洲激情精品| 成人免费毛片播放| 欧美人成免费网站| 日韩影片在线观看| 精品在线视频一区二区| 久久日韩粉嫩一区二区三区| 久草福利在线视频| 久久久999国产| 在线观看日韩av电影| 黄色免费视频大全| 欧美日韩视频在线第一区| 久久wwww| 日韩三级电影| 午夜av一区二区| 国产一区二区三区四区五区3d| 91黄色国产视频| 97久久超碰国产精品电影| 日本中文字幕在线2020| 91精品国产91久久久久久最新| 日本人妖一区二区| 五丁香在线视频| 欧美黄色片视频| 美女视频免费一区| 欧洲一级在线观看| 8x拔播拔播x8国产精品| 国产成人精品午夜视频免费| 中文字幕一区二区三区四区五区人 | 午夜精品久久久久久99热软件| 香蕉视频国产精品| 日韩精品在线观看av| 欧美中文一区二区三区| 黑人久久a级毛片免费观看| 国产精品美女在线播放| 欧美写真视频网站| 成人女性视频| www.久久久精品| 一区二区三区四区精品| 国产精品久久777777毛茸茸 | 日韩精品在线视频美女| 2023国产精品久久久精品双| 久热精品在线观看视频| 日韩在线免费高清视频| 美女一区二区视频| 免费av在线网址| 91入口在线观看| 亚洲一卡二卡三卡四卡 | 亚洲欧美在线x视频| 一区二区三区国产盗摄| 日韩av成人| 国产精品美女久久| 亚洲精品视频一区| 波多野结衣欧美| 97xxxxx| 美女撒尿一区二区三区| 99国产精品久久久久| av成人免费看| 国产自产在线视频| 一本一本久久a久久精品牛牛影视 一本色道久久综合亚洲精品小说 一本色道久久综合狠狠躁篇怎么玩 | av资源一区| 免费电影一区| 欧美日韩亚洲综合| 亚洲免费网站| 成人在线观看亚洲| 欧美日韩一区综合| 亚洲国产精品视频在线观看| 久久激情五月激情| 欧美大片高清| 91九色在线观看视频| 欧美多人爱爱视频网站| 亚洲视频免费观看| 欧美自拍偷拍| 国产三级在线免费观看| 久久久久久久久久码影片| 日韩精品一区二区三区视频播放| 日本欧美大码aⅴ在线播放| 成人免费图片免费观看| 成人免费在线网| 欧美成人h版在线观看| 国产精品成人一区二区三区夜夜夜| 99re热精品视频| 免费观看羞羞视频网站| 91免费电影网站| 欧美日韩国产免费一区二区| 麻豆精品久久精品色综合| 欧美一级做a| 国产主播色在线| 国产一区免费视频| 亚洲精品天天看| 国产亚洲欧美日韩日本| 精品国产乱码| 国产视频一区二区| 国产伦精品一区二区三区四区视频_ | 日韩理论片久久| 91麻豆蜜桃一区二区三区| 操欧美女人视频| 天堂中文资源在线| 亚洲精品在线免费看| 欧美人与性动交a欧美精品| 午夜精品久久久久久| 日韩精品一二三| 538任你躁精品视频网免费| 蜜桃视频在线观看视频| eeuss中文| 国产精品久久久亚洲| 精品国产污网站| 中文字幕乱码久久午夜不卡| 国产精品草草| 国产成人精品一区二三区在线观看 | 免费看啪啪网站| 欧美超级乱淫片喷水| 精品久久久久久亚洲精品| 极品销魂美女一区二区三区| 日韩有码av| 大桥未久在线播放| 免费av高清| 中国黄色录像片| 国产欧美精品久久久| 精品呦交小u女在线| 亚洲综合激情另类小说区| 国内成+人亚洲+欧美+综合在线| 精品国产一区二区三区噜噜噜 | 欧美三级视频在线播放| 99久久国产免费看| 99国产精品视频免费观看一公开 | 亚洲精品网址在线观看| 亚洲国产va精品久久久不卡综合| 另类小说综合欧美亚洲|