marshmallow-sqlalchemy
marshmallow-sqlalchemy copied to clipboard
AssertionError: Dependency rule tried to blank-out primary key column
Hello, I have a problem with nested that have a foreign key which is also a primary key. What I'm trying to accomplish is extremely simple.
Base: Any = declarative_base()
Session: Any = orm.scoped_session(orm.sessionmaker())
class Author(Base):
__tablename__="authors"
name = Column(String, primary_key=True)
desc = Column(String, nullable=False)
book_id = Column(Integer, ForeignKey("books.book_id"), primary_key=True)
class AuthorSchema(ModelSchema):
class Meta:
model = Author
sqla_session = Session
class Book(Base):
__tablename__ = "books"
book_id = Column(Integer, primary_key=True)
authors = relationship("Author", backref="book")
class BookSchema(ModelSchema):
authors = fields.Nested(AuthorSchema, many=True)
class Meta:
model = Book
sqla_session = Session
This is quite straightforward. I would like to have a book instance linked to multiple authors.
Then, suppose I loads a JSON ponting to an existent book instance and suppose I would like to change desc
value of an author. I then commit the change and get an AssertionError.
Let`s see the code:
engine = create_engine("postgresql://localhost", echo=False)
Base.metadata.create_all(engine)
Session.configure(bind=engine)
session = Session()
book = Book(book_id=6934389)
author1 = Author(name="myname", desc='mydesc')
book.authors = [author1]
session.add(book)
session.commit()
schema = BookSchema()
json_book = schema.dumps(book)
schema = BookSchema()
book = schema.loads(json_book)
book.authors[0].desc = 'newdesc'
session.add(book)
session.commit()
session.close()
Result
Traceback (most recent call last):
File "/models/db_models.py", line 264, in <module>
session.commit()
File "/.venv/lib/python3.7/site-packages/sqlalchemy/orm/session.py", line 1027, in commit
self.transaction.commit()
File "/.venv/lib/python3.7/site-packages/sqlalchemy/orm/session.py", line 494, in commit
self._prepare_impl()
File ".venv/lib/python3.7/site-packages/sqlalchemy/orm/session.py", line 473, in _prepare_impl
self.session.flush()
File "/.venv/lib/python3.7/site-packages/sqlalchemy/orm/session.py", line 2459, in flush
self._flush(objects)
File "/.venv/lib/python3.7/site-packages/sqlalchemy/orm/session.py", line 2597, in _flush
transaction.rollback(_capture_exception=True)
File "/.venv/lib/python3.7/site-packages/sqlalchemy/util/langhelpers.py", line 68, in __exit__
compat.reraise(exc_type, exc_value, exc_tb)
File "/.venv/lib/python3.7/site-packages/sqlalchemy/util/compat.py", line 153, in reraise
raise value
File "/.venv/lib/python3.7/site-packages/sqlalchemy/orm/session.py", line 2557, in _flush
flush_context.execute()
File "/.venv/lib/python3.7/site-packages/sqlalchemy/orm/unitofwork.py", line 422, in execute
rec.execute(self)
File "/.venv/lib/python3.7/site-packages/sqlalchemy/orm/unitofwork.py", line 540, in execute
self.dependency_processor.process_saves(uow, states)
File "/.venv/lib/python3.7/site-packages/sqlalchemy/orm/dependency.py", line 584, in process_saves
state, child, None, True, uowcommit, False
File "/.venv/lib/python3.7/site-packages/sqlalchemy/orm/dependency.py", line 604, in _synchronize
sync.clear(dest, self.mapper, self.prop.synchronize_pairs)
File "/.venv/lib/python3.7/site-packages/sqlalchemy/orm/sync.py", line 87, in clear
"column '%s' on instance '%s'" % (r, orm_util.state_str(dest))
AssertionError: Dependency rule tried to blank-out primary key column 'authors.book_id' on instance '<Author at 0x10f9a3190>'
Any idea of how can I solve this?
Thank you very much!
I have the same error: "AssertionError: Dependency rule tried to blank-out primary key column", while loading a json data for an existing object. The error doesn't even occur when doing a session.add / session.merge, but directly when an autoflush is generated inside the load. The object whose primary key is being deleted is present in the json, so I guess the autoflush is generated for a partial data. Anyway it makes no sense to try to wipe the primary key (juste like your example). Especially as it's just in the load. It's very annoying.
i get the same error, any news on this? 👀