文档明确指出ModelAdmin.delete_model()
必须删除该对象,并且它不用于否决目的。问题是,他们没有给出任何提示,你将如何实施否决应该你需要。
这里有一些背景,因为也许有一种更好的方式来实现我正在努力实现的目标。我正在Django 1.5应用程序中捕获iptables规则,并希望使用Admin页面来处理所有维护。我手头有两个与这个问题相关的模型:Chain和Target。以下是这些模型的关键:
class Chain(models.Model):
"""A netfilter chain."""
name = models.CharField(max_length=30, unique=True, primary_key=True)
built_in = models.BooleanField(
default=False,
help_text=u'This option should be selected if this chain is one of '
u'those provided by netfilter. Leaving this option '
u'unselected indicates that the chain is user-defined.'
)
table = models.ForeignKey(Table, verbose_name='netfilter table')
class Target(models.Model):
"""A netfilter target."""
name = models.CharField(
max_length=30, unique=True, primary_key=True,
help_text=u'This may be either an iptables built-in target or a '
u'user-defined chain. Built-in targets must be one of '
u'those supported by iptables.'
)
built_in = models.BooleanField(
default=False, verbose_name='built-in',
help_text=u'This option should be selected if this target is one of '
u'those provided by netfilter. Leaving this option '
u'unselected indicates that the target is user-defined.',
)
因此,Chain表将具有"FORWARD"、"INPUT"one_answers"OUTPUT"的记录,这些记录都内置并链接到"filter"表。当然,管理员也可以在这里输入其他用户定义的链,但会用built_in == False
设置这些链。
不过,目标队的情况变得很奇怪。它们可以引用Chain(嘿,ForeignKey在这里会很好!)或我不想公开为Chain的内置Target(例如,"ACCEPT"或"DROP")(嘿,ForegnKey在这里不会那么热门!.)。
现在是进退两难的局面。Admin UI在将目标链接到用户定义的链时有点笨拙,因为它没有定义为FK,所以我选择了常规字符输入字段,clean_name()
可以处理验证以确保目标的链存在。我一直纠结于如何防止删除目标引用的链。
您应该能够通过在Chain
管理员中重写has_delete_permission(request, obj)
来实现这一点。您可以检查obj
,看看是否有Targets
在引用它。请参阅文档。
不过,这不会阻止通过更改列表视图中的删除所选操作进行删除。您可以通过用自己的操作覆盖内置的delete_selected
操作来解决这个问题,如果不应该删除任何项目,该操作将拒绝执行删除操作。请参阅管理操作文档。