marshmallow-sqlalchemy
marshmallow-sqlalchemy copied to clipboard
marhsmallow auto generated field using `enum.Enum` raises error on load
Hi,
When I define SQLAlchemy columns using enum.Enum the auto generated marshmallow field fails validation when I try to load:
import enum
import marshmallow as ma
import sqlalchemy as sa
from marshmallow_sqlalchemy import SQLAlchemyAutoSchema
from sqlalchemy.orm import declarative_base, scoped_session, sessionmaker
engine = sa.create_engine("sqlite:///:memory:")
session = scoped_session(sessionmaker(bind=engine))
Base = declarative_base()
class ColorEnum(str, enum.Enum):
RED = 1
GREEN = 2
BLUE = 3
class Item(Base):
__tablename__ = 'items'
id = sa.Column(sa.Integer, primary_key=True)
color = sa.Column(sa.Enum(ColorEnum))
class ItemSchema(SQLAlchemyAutoSchema):
class Meta:
model = Item
load_instance = True
data = {'color': 'RED'}
item = ItemSchema().load(data, session=session)
This raises marshmallow.exceptions.ValidationError: {'color': ['Must be one of: RED, GREEN, BLUE.']}
If I define a Enum field explicitly on ItemSchema:
color = ma.fields.Enum(ColorEnum)
It loads correctly.
Also works if I define the enum using sa.Enum with strings on Item:
color = sa.Column(sa.Enum("RED", "GREEN", "BLUE"))
After #611, if I understood correctly, I shouldn't need to define the field explicitly, or is there something I'm missing? Thank you!
From my debugging, it looks like this validator is interfering with the checks that fields.Enum does by default.
And validators are run AFTER deserialization.
So, this is basically doing a validator check for: 1 in {"RED", "GREEN", "BLUE"} when we use sa.Enum(ColorEnum)
i unfortunately don't have time to dig into this in the next few weeks. would definitely appreciate a PR from a kind soul
finally got around to looking into this. @AbdealiLoKo's diagnosis was correct. I've fixed this in https://github.com/marshmallow-code/marshmallow-sqlalchemy/pull/640. i'll release it today