Как я могу организовать отношения SQLAlchemy для доступа как JSON-подобный dict? - PullRequest
0 голосов
/ 11 мая 2018

У меня есть приложение, в котором у каждого пользователя может быть много разных размеров одежды, связанных с его учетной записью.Я смоделировал эти ассоциации с помощью таблиц ассоциаций и связал их с помощью relationship() s в моих моделях.До того, как я начал пытаться поместить отношения в словарь, они были связаны на верхнем уровне, например:

class User(db.Model):

    id = db.Column(db.Integer, primary_key=True)

    # user many-to-many size associations (using link tables)
    sz_shirt_dress_sleeve = db.relationship(
        'SizeKeyShirtDressSleeve',
        secondary=LinkUserSizeShirtDressSleeve,
        backref=db.backref('users', lazy='dynamic'))
    sz_shirt_dress_neck = db.relationship(
        'SizeKeyShirtDressNeck',
        secondary=LinkUserSizeShirtDressNeck,
        backref=db.backref('users', lazy='dynamic'))
    sz_shirt_casual = db.relationship(
        'SizeKeyShirtCasual',
        secondary=LinkUserSizeShirtCasual,
        backref=db.backref('users', lazy='dynamic'))

И я мог получить к ним доступ так:

>>> from app.models import User
>>> u1 = User.query.first()
>>> u1.sz_shirt_dress_sleeve
[Dress shirt sleeve size: 3000]

Потому чтоВ конечном итоге у меня будет ~ 20 таких отношений, и, поскольку я хочу получить к ним более программный доступ в другом месте, я бы хотел сохранить их в формате JSON, подобном следующему:

class User(db.Model):

    id = db.Column(db.Integer, primary_key=True)

    sizes = {
        'shirt-sleeve': {
            'key': 'shirt-sleeve',
            'values': db.relationship(
                'SizeKeyShirtDressSleeve',
                secondary=LinkUserSizeShirtDressSleeve,
                backref=db.backref('users', lazy='dynamic'))
        }
    }

Сделав это, я быбыть в состоянии получить доступ к списку размеров следующим образом:

>>> <some_user>.sizes['shirt-sleeve']['values']
[3000, 3050, 3100]

Вышеупомянутая попытка подгонки этих ассоциаций внутри dict, как я обнаружил, не работает, потому что "[использование SQLAlchemyметаклассы] не собирают эти объекты внутри чего-то другого, например, словаря. " Ну дерьмо.

Обходным путем я попытался успокоить верхний уровень метакласса, ощущая это:

class User(db.Model):

    id = db.Column(db.Integer, primary_key=True)

    sz_shirt_dress_neck = db.relationship(
        'SizeKeyShirtDressNeck',
        secondary=LinkUserSizeShirtDressNeck,
        backref=db.backref('users', lazy='dynamic'))

    sizes = {
        'shirt-neck': {
            'key': 'shirt-neck',
            'values': lambda self: self.sz_shirt_dress_neck
        }
    }

Это не сработало (хотя и не сработало):

>>> from app.models import User
>>> u1 = User.query.first()
>>> u1.sizes['shirt-neck']['values']
<function User.<lambda> at 0x102aedb70>

Как сохранить эти отношения в словаре, похожем на JSON?(и небольшой вопрос: где я могу научиться принципам проектирования, чтобы научить меня, если я должен сделать это таким образом? Я самоучка, и эти более крупные концепции дизайна на самом деле не охватываются документацией / учебными пособиями)

1 Ответ

0 голосов
/ 11 мая 2018

Определите метод в вашей модели, измените объект User и верните его:

class User(db.Model):
    # your codes...
    def as_dict(self):
        self.sizes = {
            'shirt-neck': {
                'key': 'shirt-neck',
                'values': self.sz_shirt_dress_neck
            },
            # another one
        }
        return self


>>> u1 = User.query.first()
>>> if u1:
...     user = u1.as_dict()
...     user.sizes
...