SQLAlchemy integration with the marshmallow (de)serialization library
npx @tessl/cli install tessl/pypi-marshmallow-sqlalchemy@1.4.0SQLAlchemy integration with the marshmallow (de)serialization library. This package provides seamless integration between SQLAlchemy ORM models and marshmallow serialization/deserialization schemas, enabling automatic generation of marshmallow schemas from SQLAlchemy models with support for relationships, foreign keys, and field validation.
pip install marshmallow-sqlalchemyfrom marshmallow_sqlalchemy import SQLAlchemySchema, SQLAlchemyAutoSchema, auto_fieldFor field conversion utilities:
from marshmallow_sqlalchemy import ModelConverter, fields_for_model, field_forFor relationship fields:
from marshmallow_sqlalchemy import Related, RelatedList, Nestedimport sqlalchemy as sa
from sqlalchemy.orm import DeclarativeBase, sessionmaker
from marshmallow_sqlalchemy import SQLAlchemyAutoSchema, SQLAlchemySchema, auto_field
# Define SQLAlchemy model
class Base(DeclarativeBase):
pass
class Author(Base):
__tablename__ = "authors"
id = sa.Column(sa.Integer, primary_key=True)
name = sa.Column(sa.String, nullable=False)
email = sa.Column(sa.String, unique=True)
# Automatic schema generation
class AuthorAutoSchema(SQLAlchemyAutoSchema):
class Meta:
model = Author
load_instance = True
# Manual schema with auto_field
class AuthorManualSchema(SQLAlchemySchema):
class Meta:
model = Author
load_instance = True
id = auto_field()
name = auto_field()
email = auto_field(dump_only=True)
# Usage
engine = sa.create_engine("sqlite:///:memory:")
Session = sessionmaker(engine)
session = Session()
schema = AuthorAutoSchema()
author_data = {"name": "John Doe", "email": "john@example.com"}
# Deserialize to dict
result = schema.load(author_data)
# Deserialize to model instance
author_instance = schema.load(author_data, session=session)marshmallow-sqlalchemy uses a layered architecture:
SQLAlchemySchema and SQLAlchemyAutoSchema provide the main schema classesModelConverter handles translation between SQLAlchemy types and marshmallow fieldsRelated and RelatedList handle SQLAlchemy relationshipsLoadInstanceMixin provides model instance loading capabilitiesThis design enables bidirectional data transformation between SQLAlchemy model instances and JSON/dictionary representations, with automatic field type inference from database column definitions.
Two approaches for creating schemas from SQLAlchemy models: automatic generation with SQLAlchemyAutoSchema and manual field declaration with SQLAlchemySchema and auto_field.
class SQLAlchemySchema(LoadInstanceMixin.Schema, Schema):
"""Schema for SQLAlchemy model or table with manual field declaration."""
class SQLAlchemyAutoSchema(SQLAlchemySchema):
"""Schema that automatically generates fields from model columns."""
def auto_field(
column_name: str | None = None,
*,
model: type[DeclarativeMeta] | None = None,
table: sa.Table | None = None,
**kwargs
) -> SQLAlchemyAutoField:
"""Mark a field to autogenerate from a model or table."""Comprehensive system for converting SQLAlchemy columns and properties to appropriate marshmallow fields, with support for all standard and database-specific types.
class ModelConverter:
"""Converts SQLAlchemy models into marshmallow fields."""
def fields_for_model(
self,
model: type[DeclarativeMeta],
*,
include_fk: bool = False,
include_relationships: bool = False,
fields: Iterable[str] | None = None,
exclude: Iterable[str] | None = None,
base_fields: dict | None = None,
dict_cls: type[dict] = dict,
) -> dict[str, fields.Field]: ...
def fields_for_model(model, **kwargs) -> dict[str, fields.Field]: ...
def field_for(model, property_name: str, **kwargs) -> fields.Field: ...Specialized fields for handling SQLAlchemy relationships with automatic serialization/deserialization of related model instances.
class Related(fields.Field):
"""Field for SQLAlchemy relationships."""
class RelatedList(fields.List):
"""List field for one-to-many and many-to-many relationships."""class SQLAlchemySchemaOpts(LoadInstanceMixin.Opts, SchemaOpts):
"""Options class for SQLAlchemySchema."""
model: type[DeclarativeMeta] | None
table: sa.Table | None
load_instance: bool
sqla_session: Session | None
transient: bool
model_converter: type[ModelConverter]
class SQLAlchemyAutoSchemaOpts(SQLAlchemySchemaOpts):
"""Options class for SQLAlchemyAutoSchema."""
include_fk: bool
include_relationships: bool
class MarshmallowSQLAlchemyError(Exception):
"""Base exception class from which all exceptions related to marshmallow-sqlalchemy inherit."""
class ModelConversionError(MarshmallowSQLAlchemyError):
"""Raised when an error occurs in converting a SQLAlchemy construct to a marshmallow object."""
class IncorrectSchemaTypeError(ModelConversionError):
"""Raised when a SQLAlchemyAutoField is bound to Schema that is not an instance of SQLAlchemySchema."""