관계를 사용하여 생성자에 객체를 추가하는 방법은 무엇입니까? 생성자가 평가 될 때 ID는 아직 준비되지 않았습니다. 단순한 경우 사전에 계산하여 목록을 제공하는 것이 가능합니다. 아래 예제에서 나는 블랙 박스와 비슷한 방식으로 complex_cls_method
라고 말하려고했습니다.SQLAlchemy 모델의 생성자에서 관계를 통해 데이터를 저장하는 방법은 무엇입니까?
from sqlalchemy import create_engine, MetaData, Column, Integer, String, ForeignKey
from sqlalchemy.ext.declarative import declarative_base
from sqlalchemy.orm import relationship
from sqlalchemy.orm import sessionmaker
DB_URL = "mysql://user:[email protected]/exampledb?charset=utf8"
engine = create_engine(DB_URL, encoding='utf-8', convert_unicode=True, pool_recycle=3600, pool_size=10)
session = sessionmaker(autocommit=False, autoflush=False, bind=engine)()
Model = declarative_base()
class User(Model):
__tablename__ = 'user'
id = Column(Integer, primary_key=True)
simple = Column(String(255))
main_address = Column(String(255))
addresses = relationship("Address",
cascade="all, delete-orphan")
def __init__(self, addresses, simple):
self.simple = simple
self.main_address = addresses[0]
return # because the following does not work
self.addresses = Address.complex_cls_method(
user_id_=self.id, # <-- this does not work of course
key_="address",
value_=addresses
)
class Address(Model):
__tablename__ = 'address'
id = Column(Integer, primary_key=True)
keyword = Column(String(255))
value = Column(String(255))
user_id = Column(Integer, ForeignKey('user.id'), nullable=False)
parent_id = Column(Integer, ForeignKey('address.id'), nullable=True)
@classmethod
def complex_cls_method(cls, user_id_, key_, value_):
main = Address(keyword=key_, value="", user_id=user_id_, parent_id=None)
session.add_all([main])
session.flush()
addrs = [Address(keyword=key_, value=item, user_id=user_id_, parent_id=main.id) for item in value_]
session.add_all(addrs)
return [main] + addrs
if __name__ == "__main__":
# Model.metadata.create_all(engine)
user = User([u"address1", u"address2"], "simple")
session.add(user)
session.flush()
# as it can't be done in constructor, these additional statements needed
user.addresses = Address.complex_cls_method(
user_id_=user.id,
key_="address",
value_=[u"address1", u"address2"]
)
session.commit()
문제는 사용자의 생성자와 함께이 작업을 수행하는 구문 우아한 (기술적으로 타당) 방법이있다, 또는은 Session.flush가 원하는 객체를 추가 한 후에는 안전한 단지 사용자 클래스의 별도의 메소드를 호출하는 것입니다 관계 (예제 코드에서와 같이)?
생성자를 모두 포기하는 것은 가능하지만 결과로 나타나는 서명 변경으로 덜 바람직한 옵션은 중요한 리팩토링을 필요로합니다.
"1 대 다 관계가있는 뭔가를 추가하는 유일한 방법은 먼저 플러시하는 것입니다. 다음으로 ..."는 다소 잘못되었습니다. SQLA는 지속적인 복잡한 객체 그래프를 처리 할 수 있습니다 (일반적으로) - 그것의 판매 포인트 중 하나입니다. 게시물의 정보를 너무 많이 생략했습니다. 예를 들면 :'User.main_address'는 무엇입니까? 주소에 자체 참조 외래 키를 표시했으나이를 사용하는 방식이 아닙니다. [mcve]를 입력하십시오. 여기서 설명하는 대신 실제로 수행하려는 작업을 최소한으로 표시하십시오. –
이제 (비) 작동 예제와 간단한 설명이 있습니다. –