一个子类化abc的django模型导致元类冲突

14 投票
1 回答
2863 浏览
提问于 2025-04-17 09:30

我有一个模型和一个抽象基类,如下所示:

import abc
from django.db import models


class AbstractBase():
    __metaclass__ = abc.ABCMeta

    @abc.abstractmethod
    def my_method(self):
        return


class MyModel(models.Model, AbstractBase):
    @abc.abstractmethod
    def my_method(self):
        return 1

但是我遇到了以下错误:

元类冲突:派生类的元类必须是所有基类元类的(非严格)子类

我认为问题出在这里(正如这里所描述的 http://code.activestate.com/recipes/204197-solving-the-metaclass-conflict/),因为两个基类有两个不同的元类,所以 Python 无法决定应该使用哪个元类来创建子类对象。

为了解决这个问题,我去掉了多重继承,并使用以下注册方法来注册子类:

abc.register(Child)

不过我不太喜欢这种方法,因为它看起来像是“猴子补丁”。

有没有其他方法可以解决这个问题呢?

我尝试明确地将模型的元类分配给子类,但没有成功。我并不想通过写代码来解决这个问题。我觉得这应该通过改变我的类结构来解决。

1 个回答

2

除了创建一个新的元类,这个元类同时继承自 ABCMetaModelBase或者让 ABCMeta 继承自 ModelBase 你能做的事情不多。

不过,也许可以考虑不同的注册方式?比如像 contrib.admin.autodiscover 这样的? 或者使用类装饰器?又或者在 .py 文件的底部加个循环,调用 register 来处理合适的类(例如,for var in globals().values(): if isinstance(var, type) and issubclass(var, AbastractBase): register(var))?

编辑: 哎呀。我原本以为 ABCMeta 是个例子,而不是 ABCMeta。这就是我在没睡好的情况下浏览 StackOverflow 的结果。

撰写回答