Django Admin中具有多表继承的ValueError

时间:2010-05-15 14:02:16

标签: django django-admin multi-table

我创建了两个继承模型Entry的新类:

class Entry(models.Model):
    LANGUAGE_CHOICES = settings.LANGUAGES

    language = models.CharField(max_length=2, verbose_name=_('Comment language'), choices=LANGUAGE_CHOICES)
    user = models.ForeignKey(User)
    country = models.ForeignKey(Country, null=True, blank=True)

    created = models.DateTimeField(auto_now=True)

class Comment(Entry):
    comment = models.CharField(max_length=2000, blank=True, verbose_name=_('Comment in English'))

class Discount(Entry):
    discount = models.CharField(max_length=2000, blank=True, verbose_name=_('Comment in English'))
    coupon = models.CharField(max_length=2000, blank=True, verbose_name=_('Coupon code if needed'))

通过admin.site.register将这些新模型添加到管理员后,我在尝试通过管理员创建评论或折扣时收到ValueError。添加条目工作正常。

错误消息:

ValueError at / admin / reviews / discount / add / 无法指定“''”:“Discount.discount”必须是“Discount”实例。 请求方法:GET 请求网址:http://127.0.0.1:8000/admin/reviews/discount/add/ 异常类型:ValueError 例外价值:
无法指定“''”:“Discount.discount”必须是“Discount”实例。 例外位置:/Library/Python/2.6/site-packages/django/db/models/fields/related.py in set ,第211行 Python可执行文件:/ usr / bin / python Python版本:2.6.1

2 个答案:

答案 0 :(得分:6)

出现此错误的原因是因为我使用了与模型名称一起使用的相同列名。 Karen T.在Django mailing list中提供了以下答案:

  

问题似乎是你有   在评论模型中命名了一个字段   同名,只有小写。   注释继承自Entry,使用   多表继承。这增加了一个   OneToOneField在评论中回归   进入,有副作用   在Entry中添加'comment'属性。   这是让你的属性   访问与之关联的评论   因进入而进入   注释中的OneToOneField,以及   默认情况下,它被赋予了名称   相关模型,全小写。

     

在   然后在评论时出现问题   模型“继承”所有   条目的字段/属性:   继承了'comment'属性   进入显然超过了   指定的评论字段。那是   可能是一个错误,但它似乎   自1.0以来一直在那里。我还没有   做了任何研究,看看是否已经   报道。

     

作为一种解决方法,你可以   将您的字段命名为其他内容   型号名称全部小写,或者你   可以明确指定   儿童模型中的OneToOneField,   指定parent_link = True和   除了型号名称之外的其他东西   所有小写​​的相关名称。

答案 1 :(得分:0)

Hunch说你可以将你的Entry类声明为一个抽象类,除非你需要一个Entry作为一个实际的对象,

...rest of Entry model here...
created = models.DateTimeField(auto_now_add=True) ## ONLY set date when created, not every save

class Meta:
   abstract = True

...methods for your model etc...