SQLModel is a Python library that unifies SQLAlchemy's ORM capabilities with Pydantic's data validation, simplifying interaction with SQL databases. It aims to reduce code duplication by using a single class definition for both database models and data schemas. SQLModel is currently in version 0.0.38 and maintains an active development cadence with frequent releases, often including bug fixes, dependency updates, and sometimes breaking changes.
pip install sqlmodelVerified import paths — ran on the pinned version, not inferred.
This quickstart demonstrates how to define a `SQLModel` table, create a database engine (using SQLite in this case), create the database tables, and then insert and query data. It showcases the combined power of Pydantic-like model definition with SQLAlchemy's ORM operations. The `echo=True` in `create_engine` will print SQL statements to the console.
Upgrade your Python environment to 3.10 or newer. For older Python versions, use SQLModel < 0.0.35.
Upgrade Pydantic to version 2 (e.g., `pip install pydantic==2.*`). Be aware that Pydantic v2 has its own breaking changes. If you must use Pydantic v1, pin SQLModel to `<0.0.31` or use `pydantic<2`.
Always use a new `Session` context manager for each logical unit of work. For FastAPI, use `Depends` to inject a session per request. Ensure all operations on a model instance occur within the same session that loaded it.
Install the correct async driver (e.g., `pip install sqlmodel[aiosqlite]`). Use `create_async_engine` with a proper async database URL (e.g., `sqlite+aiosqlite:///./test.db`). Manage async sessions with `async with AsyncSession(engine) as session:`.
Structure your code so model definitions are fully loaded before `SQLModel.metadata.create_all()` is invoked. For complex applications, consider using a database migration tool like Alembic.
Use `from typing import TYPE_CHECKING` and import classes inside an `if TYPE_CHECKING:` block for type-checking tools. For example: `if TYPE_CHECKING: from .other_model import OtherModel`.
pip install sqlmodel
pip install psycopg2-binary (replace 'psycopg2-binary' with the appropriate driver for your database, e.g., 'aiosqlite' for SQLite, 'mysqlclient' for MySQL)
Define the field using Optional and Field(default=None, primary_key=True), for example: id: Optional[int] = Field(default=None, primary_key=True)
For queries, use SQLModel's direct attribute access, e.g., select(Hero.name) or session.exec(select(Hero).where(Hero.name == 'Deadpond')) instead of SQLAlchemy Core syntax. If a raw Table object is truly needed, access SQLModelClass.__table__.