Я наткнулся на точно такую же проблему, к счастью, я ее исправил.
Исходное решение (которое вы использовали) исходит от этого вопроса , мое решение основано наit:
class ForeignKeyLinksMetaclass(MediaDefiningClass):
def __new__(cls, name, bases, attrs):
new_class = super(
ForeignKeyLinksMetaclass, cls).__new__(cls, name, bases, attrs)
def foreign_key_link(instance, field):
target = getattr(instance, field)
return u'<a href="../../%s/%s/%d/">%s</a>' % (
target._meta.app_label, target._meta.module_name,
target.id, unicode(target)
)
for name in new_class.list_display:
if name[:8] == 'link_to_':
method = partial(foreign_key_link, field=name[8:])
method.__name__ = name[8:]
method.allow_tags = True
setattr(new_class, name, method)
return new_class
Ну, единственное, что вам нужно, это заменить оригинальный ModelAdminWithForeignKeyLinksMetaclass на приведенный выше.
Однако это еще не конец.Самое интересное, почему оригинальное решение вызывает проблемы.Ответ на этот вопрос лежит здесь (строка 31) и здесь (строка 244).
Когда DEBUG включен, Django пытается проверить все зарегистрированные ModelAdmins (первая ссылка).Там cls - это класс SomeAdmin (т.е. экземпляр его метакласса).Когда вызывается hasattr , python пытается найти атрибут field в классе SomeAdmin или в одном из его суперклассов.Поскольку это невозможно, вызывается __getattr__ его класса (то есть метакласс SomeAdmin ), где к классу SomeAdmin добавляется новый метод.Следовательно, когда дело доходит до визуализации интерфейса, SomeAdmin уже исправлен, и Django может найти требуемое поле (вторая ссылка).
Когда DEBUG имеет значение False, Django пропускает проверку.Когда интерфейс отображается, Django пытается найти поле (опять-таки, вторая ссылка), но на этот раз SomeAdmin не исправлен, более того model_admin не является классом SomeAdmin , это его экземпляр .Таким образом, пытаясь найти атрибут name в model_admin , python не может этого сделать, а также не может найти его в своем классе ( SomeAdmin ) каккак и в любом из его суперклассов, поэтому возникает исключение.