Dependency rule tried to blank out primary key in SQLAlchemy, when foreign key constraint is part of composite primary key

Based on the comment by van I was able to work out a solution. The default relationship cascade is "save-update, merge". I had to set this to "save-update, merge, delete, delete-orphan".

Adding delete by itself did not change the behavior, delete-orphan was necessary.

Adding only delete-orphan made a deletion testcase fail, with the “dependency rule” assertion error, mentioned in the question:

class HierarchicModelTest(unittest.TestCase):
    def test_delete_parent_object(self):
        foo = Foo(**foo_data).save()
        self.assertEqual(Foo.query.count(), 1)
        self.assertEqual(FooCycle.query.count(), 1)

        s = get_session()
        s.delete(foo)
        s.flush()

        self.assertEqual(Foo.query.count(), 0)
        self.assertEqual(FooCycle.query.count(), 0)

  File "/home/xxx/xxx/xxx/backend/tests/test_core.py", line 128, in test_delete_parent_object
     s.flush()
  [...]
  AssertionError: Dependency rule tried to blank-out primary key column 'foocycle.foo_id' on instance '<FooCycle at 0x37a1710>'

From the SQLAlchemy docs:

delete-orphan cascade adds behavior to the delete cascade, such that a child object will be marked for deletion when it is de-associated from the parent, not just when the parent is marked for deletion.

So, the correct definition of the FooCycle Model is

class FooCycle(Base):
    __tablename__ = 'foocycle'

    foo_id = Column(
        String(50),
        ForeignKey('foo.id'),
        primary_key=True
    )
    some_number = Column(
        Integer,
        primary_key=True,
    )

    foo = relationship("Foo",
                       backref=backref("cycles",
                                        cascade="save-update, merge, "
                                                "delete, delete-orphan"))

Leave a Comment

Hata!: SQLSTATE[HY000] [1045] Access denied for user 'divattrend_liink'@'localhost' (using password: YES)