SQLAlchemy @property вызывает ошибку «Неизвестное поле» в Marshmallow с dump_only

Я использую flask-marshmallow (marshmallow=v3.0.0rc1, flask-marshmallow=0.9.0) и flask-sqlalchemy (sqlalchemy=1.2.16, flask-sqlalchemy=2.3.2)

У меня есть эта модель и схема.

from marshmallow import post_load, fields
from .datastore import sqla_database as db
from .extensions import marshmallow as ma

class Study(db.Model):
    _id = db.Column(db.Integer, primary_key=True)
    name = db.Column(db.String, nullable=False)

    tests = db.relationship("Test", backref="study", lazy='select', cascade="all, delete-orphan")

    @property
    def test_count(self):
        return len(self.tests)

class StudySchema(ma.ModelSchema):
    test_count = fields.Integer(dump_only=True)
    class Meta:
        model = Study
        sqla_session = db.session

schema = StudySchema()
payload = request.get_json()
schema.load(data=payload, instance=Study.query.get(payload["_id"]))
schema.session.commit()

Если я выполняю операцию PUT с этой полезной нагрузкой {'_id': 1, 'name': 'Study1', 'test_count': 0}, я получаю следующее исключение marshmallow.exceptions.ValidationError: {'test_count': ['Unknown field.']}

Если я удалю dump_only=True, я получу это исключение AttributeError: can't set attribute, что имеет смысл для меня, потому что он пытается установить test_count без метода установки в классе модели.

Чего я не понимаю, так это почему атрибут не игнорируется с помощью dump_only. Почему Marshmallow все еще пытается проверить и понять это поле во время загрузки, когда оно помечено как dump_only?


person Josh    schedule 27.01.2019    source источник
comment
Какая у вас версия зефира и фляжного зефира?   -  person Fine    schedule 28.01.2019
comment
sqlalchemy=1.2.16 flask-sqlalchemy=2.3.2 зефир=v3.0.0rc1 flask-зефир=0.9.0   -  person Josh    schedule 28.01.2019


Ответы (1)


В marshmallow 2 поля unknown или dump_only игнорируются при вводе. Если только пользователь не решит добавить к ним собственную проверку ошибок.

В marshmallow 3 мы изменили это, чтобы предложить три возможности (см. неизвестные ключи" rel="noreferrer">документы):

  • ПОДНИМАТЬ (по умолчанию)
  • ИСКЛЮЧИТЬ (как зефир 2)
  • ВКЛЮЧИТЬ (передавать данные без проверки)

Были дискуссии о том, как обращаться с полями dump_only, и мы пришли к выводу, что с точки зрения клиента их следует рассматривать как неизвестные поля (см. https://github.com/marshmallow-code/marshmallow/Issues/875).

Суть в том, что полезная нагрузка PUT не должна включать поля dump_only. Или вы можете установить политику EXCLUDE для своей схемы, но я бы предпочел первый вариант.

person Jérôme    schedule 28.01.2019
comment
Это именно та информация, которая мне была нужна. Благодарю вас! - person Josh; 29.01.2019