Search code examples
pythonpython-2.7sqlalchemyrelationships

Dynamic behaviour of relationship with sqlalchemy


I have two tables, and one relationship one-to-many, defined has followed.

from sqlalchemy import Column, Integer, ForeignKey
from sqlalchemy.ext.declarative import declarative_base
from sqlalchemy.orm import relationship

Base = declarative_base()


class Parent(Base):
    __tablename__ = 'parent'
    id = Column(Integer, primary_key=True)
    children = relationship("Child", backref="parent")


class Child(Base):
    __tablename__ = 'child'
    id = Column(Integer, primary_key=True)
    parent_id = Column(Integer, ForeignKey('parent.id'))

If I try to access to Child.parent I get an error. But if I initialize an instance of child the error disappears.

I guess initializing a Child instance modified Child class, but I don't understand how. How can I have access to Child.parent without creating an instance of Child?

In [1]: Child.parent
---------------------------------------------------------------------------
AttributeError                            Traceback (most recent call last)
<ipython-input-2-8b757eeb36c4> in <module>()
----> 1 Child.parent

AttributeError: type object 'Child' has no attribute 'parent'

In [2]: Child()
Out[2]: <etl.es_utils.test_to_rm.Child at 0x7f38caf42c50>

In [3]: Child.parent

Solution

  • Instead of using backref, I define relationship on both sides and it solves the issue.

    from sqlalchemy import Column, Integer, ForeignKey
    from sqlalchemy.ext.declarative import declarative_base
    from sqlalchemy.orm import relationship
    
    Base = declarative_base()
    
    
    class Parent(Base):
        __tablename__ = 'parent'
        id = Column(Integer, primary_key=True)
        children = relationship("Child")
    
    
    class Child(Base):
        __tablename__ = 'child'
        id = Column(Integer, primary_key=True)
        parent_id = Column(Integer, ForeignKey('parent.id'))
        parent = relationship("Parent")