On 25/02/2011 17:13, Michael Bayer wrote:
can't reproduce. See attached. This test includes randomization of all key
data structures in the UOW which smokes out any issues in dependency sorting.
Okay, so after about an hour of stripping down code, please find
attached a minimal reproducible test case.
As noted in the comments, if sessionmaker isn't used, all is well.
Even if sessionmaker is used, if the user is passed to Grant instead of
the username, all is well.
However, if you pass the username *and* use sessionmaker, you'll
intermittently get:
IntegrityError: (IntegrityError) (1452, 'Cannot add or update a child
row: a foreign key constraint fails (`acl_tests`.`grant`, CONSTRAINT
`grant_ibfk_1` FOREIGN KEY (`username`) REFERENCES `user` (`username`)
ON DELETE CASCADE)') 'INSERT INTO `grant` (username) VALUES (%s)'
('testname',)
...as the insert of the grant is tried before the insert of the user.
I'm using:
Python 2.6.6
SQLAlchemy 0.6.6
MySQL_python 1.2.3
The MySQL server is running version 5.1.49-3 of debian's mysql-server
package.
Good luck!
Chris
--
Simplistix - Content Management, Batch Processing & Python Consulting
- http://www.simplistix.co.uk
--
You received this message because you are subscribed to the Google Groups
"sqlalchemy" group.
To post to this group, send email to [email protected].
To unsubscribe from this group, send email to
[email protected].
For more options, visit this group at
http://groups.google.com/group/sqlalchemy?hl=en.
from sqlalchemy import Column, String, ForeignKey, create_engine
from sqlalchemy.ext.declarative import declarative_base
from sqlalchemy.orm import relationship, scoped_session, sessionmaker, Session
from unittest import TestCase, main
Base = declarative_base()
class User(Base):
__tablename__ = 'user'
__table_args__ = {'mysql_engine':'InnoDB'}
username = Column(String(50), primary_key=True)
grants = relationship("Grant",
cascade="all",
lazy="dynamic")
class Grant(Base):
__tablename__ = 'grant'
__table_args__ = {'mysql_engine':'InnoDB'}
username = Column(String(50),
ForeignKey('user.username',ondelete='cascade'),
primary_key=True)
user = relationship("User")
class TestCascades(TestCase):
def test_delete_user(self):
engine = create_engine('mysql://scott:tiger@localhost/test',
echo=True)
# uncomment the following line and run until IntegrityErrors
# appear! (it's intermittent, though, so don't be surprised
# if it passes a few times...)
Session = sessionmaker()
session = Session(bind=engine)
Base.metadata.drop_all(session.bind)
Base.metadata.create_all(session.bind)
user = User(username='testname')
session.add(user)
# passing the username rather than the user object here is
# also important, if the user object is passed, things work
# as expected regardless of whether or not sessionmaker is used.
session.add(Grant(username=user.username))
self.assertEqual(session.query(User).count(),1)
if __name__ == '__main__':
main()