Thanks. I've got this working now, but am having trouble combining
polymorphism and multiple foreign keys to the same table. Here's
roughly what I'm doing:
class Entity(Base):
__tablename__ = 'entities'
id = Column(Integer, primary_key=True)
# ...bunch of columns...
type = Column(Unicode(20), nullable=False)
__mapper_args__ = {'polymorphic_on': type}
class Site(Entity): # Client account
__tablename__ = 'sites'
__mapper_args__ = {'polymorphic_identity': u'site'}
id = Column(Integer, ForeignKey('entities.id'), primary_key=True)
name = Column(Unicode(50), unique=True, nullable=False)
title = Column(Unicode(50), nullable=False)
# ...few more Entity derived models...
class Note(Entity):
__tablename__ = 'notes'
__mapper_args__ = {'polymorphic_identity': u'note',
'inherit_condition': (id == Entity.id)}
id = Column(Integer, ForeignKey('entities.id'), primary_key=True)
site_id = Column(Integer, ForeignKey('deals.id'), nullable=False)
site = relation(Site, foreign_keys=site_id,
primaryjoin=site_id == Site.id)
attached_to_id = Column(Integer, ForeignKey('entities.id'),
nullable=False)
attached_to = relation(Entity, foreign_keys=attached_to_id,
primaryjoin=attached_to_id == Entity.id,
backref=backref('notes', cascade='all, delete-
orphan'))
note = Column(Unicode(255), nullable=False)
I use Note.site to determine access rights and Note.attached_to to
determine containment. This declaration works until I try to delete a
site instance. SQLAlchemy throws up this exception:
...
File /usr/local/lib/python2.6/dist-packages/sqlalchemy/sql/
compiler.py, line 287, in construct_params
pd[self.bind_names[bindparam]] = bindparam.value()
TypeError: id() takes exactly one argument (0 given)
However, if I remove the backref on attached_to, everything works
fine. If I move the backref to Note.site, it fails with the same
error. If I remove attached_to* and keep the backref on site, it works
again. I'm not sure what's wrong.
Here's the full traceback, for reference.
Traceback (most recent call last):
File /home/jace/Projects/saproj/tests.py, line 76, in test_cascade
self.session.delete(site)
File /usr/local/lib/python2.6/dist-packages/sqlalchemy/orm/
session.py, line 1088, in delete
cascade_states = list(_cascade_state_iterator('delete', state))
File /usr/local/lib/python2.6/dist-packages/sqlalchemy/orm/
session.py, line 1534, in _cascade_state_iterator
for (o, m) in mapper.cascade_iterator(cascade, state, **kwargs):
File /usr/local/lib/python2.6/dist-packages/sqlalchemy/orm/
mapper.py, line 1229, in cascade_iterator
instance, instance_mapper, corresponding_state = iterator.next()
File /usr/local/lib/python2.6/dist-packages/sqlalchemy/orm/
properties.py, line 703, in cascade_iterator
instances = state.value_as_iterable(self.key, passive=passive)
File /usr/local/lib/python2.6/dist-packages/sqlalchemy/orm/
state.py, line 128, in value_as_iterable
x = impl.get(self, dict_, passive=passive)
File /usr/local/lib/python2.6/dist-packages/sqlalchemy/orm/
attributes.py, line 377, in get
value = callable_(passive=passive)
File /usr/local/lib/python2.6/dist-packages/sqlalchemy/orm/
strategies.py, line 563, in __call__
result = q.all()
File /usr/local/lib/python2.6/dist-packages/sqlalchemy/orm/
query.py, line 1286, in all
return list(self)
File /usr/local/lib/python2.6/dist-packages/sqlalchemy/orm/
query.py, line 1394, in __iter__
return self._execute_and_instances(context)
File /usr/local/lib/python2.6/dist-packages/sqlalchemy/orm/
query.py, line 1399, in _execute_and_instances
mapper=self._mapper_zero_or_none())
File /usr/local/lib/python2.6/dist-packages/sqlalchemy/orm/
session.py, line 737, in execute
clause, params or {})
File /usr/local/lib/python2.6/dist-packages/sqlalchemy/engine/
base.py, line 1086, in execute
return Connection.executors[c](self, object, multiparams, params)
File /usr/local/lib/python2.6/dist-packages/sqlalchemy/engine/
base.py, line 1149, in _execute_clauseelement
parameters=params
File /usr/local/lib/python2.6/dist-packages/sqlalchemy/engine/
base.py, line 1237, in __create_execution_context
return dialect.execution_ctx_cls(dialect, connection=self,
**kwargs)
File /usr/local/lib/python2.6/dist-packages/sqlalchemy/engine/
default.py, line 355, in __init__
grp,m in enumerate(parameters)]
File /usr/local/lib/python2.6/dist-packages/sqlalchemy/sql/
compiler.py, line 287, in construct_params
pd[self.bind_names[bindparam]] = bindparam.value()
TypeError: id() takes exactly one argument (0 given)
Thanks for the help.
On May 18, 10:42 pm, Michael Bayer mike...@zzzcomputing.com wrote:
Don't use None for the Column type (i.e., detected as the null type). Put
the type explicitly. This has been updated in the documentation recently
since the None