I'm still having problems with this (sorry about the huge delay, I got side-tracked for a while). After creating parent/child/attribute table rows, I get one of two errors when I try to print parent.attributes:
If I use the column name "id" in my child table I get this error: sqlalchemy.exceptions.InvalidRequestError: Column 'child.id' is not available, due to conflicting property 'id':<sqlalchemy.orm.properties.ColumnProperty object at 0x2b8d77fea410> Perhaps using "id" is a bad idea? I see most people use something like "child_id"; I'm just not a fan of the redundancy. When I use child_id instead I get this error: sqlalchemy.exceptions.InvalidRequestError: No column child.child_id is configured on mapper Mapper|Parent|parent... These exceptions are the two possible error paths when _getpropbycolumn receives a key error when doing "prop = self.columntoproperty(column)" (sqlalchemy/orm/mapper.py:983) Any help would be much appreciated! Here is the code: from sqlalchemy import * metadata = BoundMetaData("sqlite:///:memory:") metadata.engine.echo = True session = create_session(bind_to = metadata.engine) parent_table = Table('parent', metadata, Column('id', Integer, primary_key=True), Column('name', Unicode), ) child_table = Table('child', metadata, Column('child_id', Integer, primary_key=True), Column('parent_id', Integer, ForeignKey('parent.id')), ) attribute_table = Table('attribute', metadata, Column('id', Integer, primary_key=True), Column('child_id', Integer, ForeignKey('child.child_id')), ) class Parent(object): pass class Child(object): pass class Attribute(object): pass parent_mapper = mapper( Parent, parent_table, properties = dict( children = relation(Child, backref='parent'), attributes = relation(Attribute, primaryjoin = and_(attribute_table.c.child_id == child_table.c.child_id, child_table.c.parent_id == parent_table.c.id), foreign_keys=[attribute_table.c.child_id], backref = backref('parent', foreign_keys=[attribute_table.c.child_id], primaryjoin = and_(attribute_table.c.child_id == child_table.c.child_id, child_table.c.parent_id == parent_table.c.id)), viewonly = True, ) )) child_mapper = mapper( Child, child_table,) attribute_mapper = mapper( Attribute, attribute_table, properties = dict( child = relation(Child, backref=backref('attributes'), viewonly=True), ) ) metadata.create_all() parent = Parent() child = Child() child.parent = parent attr = Attribute() attr.child = child session.save(parent) session.flush() print parent.attributes On May 24, 10:19 am, Michael Bayer <[EMAIL PROTECTED]> wrote: > On May 24, 2007, at 10:02 AM, Patrick McKinnon wrote: > > > sqlalchemy.exceptions.ArgumentError: Cant locate any foreign key > > columns in primary join condition 'attribute.child_id = child.id AND > > child.parent_id = parent.id' for relationship 'Parent.attributes > > (Attribute)'. Specify 'foreign_keys' argument to indicate which > > columns in the join condition are foreign. > > 0.3.7 is more strict about analyzing relationships and in this case > nothing in the join condition expresses a foreign key relationship > between the "parent" and "attribute" table. when only primaryjoin is > present, it assumes a one-to-many or many-to-one relationship between > two tables. what youre doing here is trying to "skip" over. > > > parent_mapper = mapper( > > Parent, > > parent_table, > > properties = dict( > > children = relation(Child, backref='parent'), > > attributes = relation(Attribute, > > primaryjoin = and_(attribute_table.c.child_id == > > child_table.c.id, child_table.c.parent_id == parent_table.c.id), > > backref = 'parent', > > ) > > ) > > ) > > so to "force" it: > > parent_mapper = mapper( > Parent, > parent_table, > properties = dict( > children = relation(Child, backref='parent'), > attributes = relation(Attribute, > primaryjoin = and_(attribute_table.c.child_id == > child_table.c.id, child_table.c.parent_id == parent_table.c.id), > foreign_keys=[attribute_table.c.child_id], > backref = backref('parent', foreign_keys= > [attribute_table.c.child_id], primaryjoin = and_ > (attribute_table.c.child_id == > child_table.c.id, child_table.c.parent_id == > parent_table.c.id),), > ) > ) > ) > > however you want to put "viewonly=True" for the "attributes" > relationship, since that relationship will not persist correctly at all. > > the "correct" way would be to just deal with the attributes > explicitly as they are attached to each child object. Normally id > try to use the "associationproxy" extension here but your > "attributes" property is actually the product of many individual > Child objects which is a little unusual. --~--~---------~--~----~------------~-------~--~----~ You received this message because you are subscribed to the Google Groups "sqlalchemy" group. To post to this group, send email to sqlalchemy@googlegroups.com 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 -~----------~----~----~----~------~----~------~--~---