SQLAlchemy before_update调用after_delete

时间:2014-04-21 13:18:13

标签: python sqlalchemy

任何人都能说出我做错了什么

我有注册事件的方法(before_update,after_delete,before_insert) https://github.com/ITCase/sqlalchemy_mptt/blob/b0efead7a8ee5acc063b68ee3bfc756af4689d6e/sqlalchemy_mptt/mixins.py#L69

@classmethod
def register_tree(cls):
    event.listen(cls, "before_insert", cls.mptt_before_insert)
    event.listen(cls, "after_delete", cls.mptt_after_delete)
    event.listen(cls, "before_update", cls.mptt_before_update)

当我注册事件并尝试删除行(https://github.com/ITCase/sqlalchemy_mptt/blob/b0efead7a8ee5acc063b68ee3bfc756af4689d6e/sqlalchemy_mptt/tests.py#L104)时。

class Tree(Base, BaseNestedSets):
    __tablename__ = "tree"

    id = Column(Integer, primary_key=True)

Tree.register_tree()

def test_delete_node(self):
    node = self.session.query(Tree).filter(Tree.id == 4).one()
    self.session.delete(node)
    # id lft rgt lvl parent tree
    self.assertEqual([(1, 1, 16, 1, None, 1),
                      (2, 2, 5, 2, 1, 1),
                      (3, 3, 4, 3, 2, 1),
                      (7, 6, 15, 2, 1, 1),
                      (8, 7, 10, 3, 7, 1),
                      (9, 8, 9, 4, 8, 1),
                      (10, 11, 14, 3, 7, 1),
                      (11, 12, 13, 4, 10, 1)], self.result.all())

调用before_update方法而不是after_delete。但如果我评论before_update事件(https://github.com/ITCase/sqlalchemy_mptt/blob/b0efead7a8ee5acc063b68ee3bfc756af4689d6e/sqlalchemy_mptt/mixins.py#L72),它的工作正常。

@classmethod
def register_tree(cls):
    event.listen(cls, "before_insert", cls.mptt_before_insert)
    event.listen(cls, "after_delete", cls.mptt_after_delete)
    # event.listen(cls, "before_update", cls.mptt_before_update) <-- IF comment this, called after_delete method. It's OK.

构建状态https://travis-ci.org/ITCase/sqlalchemy_mptt/builds/23428309

出了什么问题?

1 个答案:

答案 0 :(得分:0)

在那里解决https://groups.google.com/forum/#!msg/sqlalchemy/gdwuMjNfrPc/v2ChQjGjWwoJ

事实证明,当删除带子节点的节点时,sqlalchemy默认情况下首先更新子节点(设置parent_id = None)然后删除节点。当我设置cascade =&#34; all,delete&#34;它逐个删除节点(没有更新)。