SQLAlchemy缓存超越事务的对象

时间:2012-04-02 19:26:43

标签: sqlalchemy

出于性能原因,我们的应用程序在启动时将某些SQLAlchemy模型实例加载到内存中。预计这些实例不会在应用程序的整个生命周期中发生变化,因此这是一个合理的解决方案。

在大多数情况下,这很好,但我观察到了DetachedInstanceError: Instance <ZZZ at 0x3a23510> is not bound to a Session; attribute refresh operation cannot proceed出现的孤立事件,导致持续的问题。这与我在尝试访问类似缓存对象上的延迟加载关系时(预期)会收到的错误相同。

该错误似乎是由访问.id属性引起的,我希望不要求任何类型的数据库刷新访问。真正困扰我的是我无法一致地重现这个异常。

我的问题是什么可能导致发生此异常,以及有哪些技术用于存储SQLAlchemy实例,而不是将它们带到事务之外?

1 个答案:

答案 0 :(得分:2)

如果对象在放入缓存之前已过期,则会丢失

.id。会话提交或回滚后,默认情况下会使所有属性到期,下次访问时会刷新。

由于对象可能已从数据库中删除或其主键被修改(两个条件都会发出ObjectDeletedError),因此.id不是给定的。

解决方案是在对象到期之前缓存对象,在会话到期之前从会话中清除(),或禁用expire_on_commit。