у меня есть связь Many To One между моделями и я пытаюсь обратиться к списку связанных обьектов, то есть к type_writer_infos в модели PortfolioInfo, то получаю ошибку.
class PortfolioInfo(Base):
__tablename__ = 'portfolio_info'
id: Mapped[uuid.uuid4] = mapped_column(UUID(as_uuid=True),
primary_key=True,
default=uuid.uuid4)
owner_name: Mapped[str] = mapped_column(String(40),
nullable=False)
type_writer_infos: Mapped[list['TypeWriterInfo']] = relationship(back_populates='portfolio_info')
class TypeWriterInfo(Base):
__tablename__ = 'type_writer_info'
id: Mapped[uuid.uuid4] = mapped_column(UUID(as_uuid=True),
primary_key=True,
default=uuid.uuid4)
info: Mapped[str] = mapped_column(String(150),
nullable=False)
portfolio_info_id: Mapped[uuid.uuid4] = mapped_column(ForeignKey('portfolio_info.id'))
portfolio_info: Mapped['PortfolioInfo'] = relationship(back_populates='type_writer_infos')
def __repr__(self):
return f'Info: {self.info}'
вот модели.
Вот пример
async def create_portfolio_info(self):
info = PortfolioInfo(
owner_name='Oleg Kuzmenko'
)
async with self.session.begin():
self.session.add(info)
lst = info.type_writer_infos
await self.session.commit()
print(lst)
return info
здесь всё ок, я внутри транзакции забираю список связанных обьектов и когда делаю принт ошибок нету, выдает список.
Но, если
async def create_portfolio_info(self):
info = PortfolioInfo(
owner_name='Oleg Kuzmenko'
)
async with self.session.begin():
self.session.add(info)
await self.session.commit()
lst = info.type_writer_infos
print(lst)
return info
я выношу это за пределы транзакции, то мне выдает
sqlalchemy.exc.MissingGreenlet: greenlet_spawn has not been called and asyncio event loop is already running; can't call await_fallback() here. Was IO attempted in an unexpected place? (Background on this error at: https://sqlalche.me/e/20/xd2s)
я и lazy='selectin' прописывал но не помогло. Вопрос, мне получается чтобы получать связанные обьекты, нужно всегда получать их внутри транзакции?
А почему не дословно из доки? https://docs.sqlalchemy.org/en/20/orm/extensions/asyncio.html#preventing-implicit-io-when-using-asyncsession stmt = select(A).options(selectinload(A.bs))
Ты отключал expire_on_commit?
async def create_portfolio_info(self): info = PortfolioInfo( owner_name='Oleg Kuzmenko' ) async with self.session.begin(): self.session.add(info) await self.session.commit() await self.session.refresh(info, attribute_names=['type_writer_infos']) print(info.type_writer_infos) return info решил это с помощью session.refresh, но не знаю, мне кажется это не самый лучший варинат как это можно было сделать
Обсуждают сегодня