Python类属性与SQLAlchemy关系

0 投票
1 回答
904 浏览
提问于 2025-04-16 22:58

好的,我有两个问题:

第一个问题和sqlalchemy有关。我被迫使用sqlite,并且需要实现一些级联删除。现在我发现使用关系可以解决这个问题,但这些关系通常应该在父表中声明。不过由于一些设计上的决定,我被迫在子表中做这个,所以我写了类似这样的代码:

class Operation(Base):
    """
    The class used to log any action executed in Projects.
    """
    __tablename__ = 'OPERATIONS'

    id = Column(Integer, primary_key=True)
    parameters = Column(String)
    ..... rest of class here ....

class DataType(Base):

    __tablename__ = 'DATA_TYPES'
    id = Column(Integer, primary_key=True)
    gid = Column(String)
    ...more params...
    parent_operation = relationship(Operation, backref=backref("DATA_TYPES", 
                                                    order_by=id, 
                                                    cascade="all,delete"))
    ...rest of class...

现在这个看起来是有效的,但我对一些事情仍然不太确定。

  • 首先,从现在开始,我可以对parent_operation做些什么?我看到级联删除是有效的,但除了实际声明之外,我并没有使用parent_operation。

    • 其次,上面提到的“DATA_TYPES”,它是backref中的第一个参数,这个名字需要是子表的名字,还是每个模型都需要唯一的名字呢?

    • 最后,在我的情况下,Operation和DataType类在同一个模块中,所以我可以把Operation作为关系中的第一个参数。如果情况不是这样,它们在不同的模块中,我如果还想声明这个关系,应该传递'Operation'还是'OPERATION'给关系(类名还是表名?)


我的第二个问题更偏向于核心Python,但由于它和上面的问题有些关联,我还是把它放在这里。我需要动态地添加一个类属性。基本上,我需要添加一个像上面声明的那样的关系。

class BaseClass(object)    

def __init__(self):
    my_class = self.__class__
    if not hasattr(my_class, self.__class__.__name__):
        reference = "my_class." + self.__class__.__name__ + "= relationship\
        ('DataType', backref=backref('" + self.__class__.__name__ + "', \
        cascade='all,delete'))"
        exec reference

我需要这样做的原因比较复杂,和一些设计决定有关(基本上,我需要每个扩展这个类的类都要有一个与'DataType'类的关系声明)。我知道使用exec语句并不是一个好习惯。那么有没有更好的方法来实现这个呢?

祝好,
博格丹

1 个回答

0

关于你问题的第二部分,记住,在你的类构造函数里写的任何东西都不会被SqlAlchemy处理。在你的例子中,你可以简单地在自己的类里声明关系(注意,这个类并不需要继承你的declarative_base类),然后在任何子类中继承它,像这样:

class BaseDataType(object):
    parent_operation = relationship(Operation, backref="datatype")

class DataTypeA(Base, BaseDataType):
    id = Column(Integer, primary_key=True)

class DataTypeB(Base, BaseDataType):
    id = Column(Integer, primary_key=True)

SqlAlchemy的文档里有很多不错的例子,可以帮助你理解可以做些什么:

http://www.sqlalchemy.org/docs/orm/extensions/declarative.html#mixing-in-relationships

撰写回答