Вставка новых записей с отношением "один ко многим" в колба-sqlalchemy
Я следую учебнику по коллоидным sqlalchemy по объявлению моделей относительно отношений "один ко многим". Код примера выглядит следующим образом:
class Person(db.Model):
id = db.Column(db.Integer, primary_key=True)
name = db.Column(db.String(50))
addresses = db.relationship('Address', backref='person',
lazy='dynamic')
class Address(db.Model):
id = db.Column(db.Integer, primary_key=True)
email = db.Column(db.String(50))
person_id = db.Column(db.Integer, db.ForeignKey('person.id'))
Теперь мне интересно, как вставить новые записи в БД, используя такую модель. Я предполагаю, что мне нужен конструктор init, но мне трудно понять, как его реализовать и использовать. Главная проблема для меня здесь заключается в том, что Лицо зависит от адреса и адреса имеет ForeignKey к Лицу, поэтому он должен знать о Человеке заранее.
Plase поможет мне понять, как это должно быть выполнено.
Спасибо заранее.
Ответы
Ответ 1
Вам не нужно писать конструктор, вы можете рассматривать свойство addresses
в экземпляре Person
как список:
a = Address(email='[email protected]')
p = Person(name='foo')
p.addresses.append(a)
Или вы можете передать список адресов конструктору Person
a = Address(email='[email protected]')
p = Person(name='foo', addresses=[a])
В любом случае вы можете получить доступ к адресам в вашем экземпляре Person
так:
db.session.add(p)
db.session.add(a)
db.session.commit()
print p.addresses.count() # 1
print p.addresses[0] # <Address object at 0x10c098ed0>
print p.addresses.filter_by(email='[email protected]').count() # 1
Ответ 2
В некоторых случаях существует исключение типа "объект списка не имеет атрибута _sa_instance_state".
a = Address(email='[email protected]')
p = Person(name='foo', addresses=a)
Решите это исключение.
Ответ 3
Самое главное, глядя на эту модель, - это понять, что эта модель имеет отношение от одного к другому, то есть одно лицо имеет более одного адреса, и мы сохраним эти адреса в списке в нашем случае.
Итак, класс Person с его init будет выглядеть примерно так.
class Person(db.Model):
id = db.Column(db.Integer, primary_key=True)
name = db.Column(db.String(50))
addresses = db.relationship('Address', backref='person',
lazy='dynamic')
def __init__(self,id,name,addresses = []):
self.id = id
self.name = name
self.addresses = addresses
Итак, этот класс Person будет ожидать id, имя и список, содержащий объекты типа Address. Я сохранил это значение по умолчанию как пустой список.
Надеюсь, это поможет.:)