У меня есть родительский класс, который должен наследоваться дочерними классами, которые станут моделями Django.Все дочерние классы имеют общее свойство x
, поэтому оно должно быть абстрактным свойством родителя.Разница между дочерними элементами заключается в том, является ли свойство атрибутом модели django или оно задано напрямую.
class A(Model, metaclass=abc.ABCMeta):
class Meta:
abstract = True
@property
@abc.abstractmethod
def x(self):
pass
class B(A):
x = "hello"
class C(A):
x = models.CharField(max_length=100, default='defaultC')
class D(A):
x = models.CharField(max_length=50, default='defaultD')
Так что в моем примере для некоторых дочерних классов известно свойство x
,но в других случаях его нужно выбрать.Но одна определенная вещь состоит в том, что всем потомкам класса A
нужен атрибут x
, так как это общее свойство, которое должно быть определено любыми потомками.
Проблема в том, что если я когда-либо создаю экземпляр классаиз C
или D
, я получаю следующее:
TypeError: Can't instantiate abstract class C with abstract methods x
Я думаю, что проблема заключается в закулисном метаклассе Django.Он удаляет любые атрибуты модели django и заменяет их отложенными атрибутами или чем-то еще, поэтому свойство никогда не определяется.
Я могу попытаться переместить атрибут модели в класс A
и позволить дочернему классу переопределить как статическое значение по мере необходимости:
class A(Model, metaclass=abc.ABCMeta):
class Meta:
abstract = True
x = models.CharField(max_length=100)
class B(A):
x = "hello"
class C(A):
x = models.CharField(max_length=100, default='defaultC')
class D(A):
x = models.CharField(max_length=50, default='defaultD')
Моя проблема в том, что это нене очень абстрактноC
и D
все еще нужно переопределить x
, чтобы установить их значения по умолчанию и максимальную длину.Меня также беспокоит, что люди, использующие класс A
в общем коде, примут, что атрибут x
будет полем базы данных django;когда вместо этого иногда это может быть статическое строковое значение.
Какой здесь идеальный подход?На самом деле я бы хотел, чтобы мой первый пример был возможен.