来自管理员的Django信号

时间:2011-03-14 22:43:45

标签: django django-admin django-signals

我如何区分,例如,来自常规视图的post_save和来自管理员的post_save?

2 个答案:

答案 0 :(得分:3)

通过覆盖ModelAdmin.response_add,您可能会获得类似的功能,因为django管理员似乎没有发送任何信号。

在成功验证并添加所有数据(如相关字段以及对象本身)后,将调用response_add函数。

因此,通过覆盖我们自己的ModelAdmin类中的response_add方法,我们可以在admin成功添加之后执行代码,但不会在其他地方执行。

我在django 1.4中做了以下方式,任何评论或反馈都非常感谢!它似乎在我的情况下运行良好,但我对Django中的所有内部结构还不是很熟悉,如果这是建议的方法。但这听起来比对我来说更糟糕。

旁注:我猜你也可以通过覆盖ModelAdmin自己发出信号,但没有经验。

这是我用来覆盖response_add的代码,它只执行product_get_initial_info(obj.id),只在管理员中成功添加了产品:

class ProductAdmin(admin.ModelAdmin):
    prepopulated_fields = {"slug": ("title",)}
    inlines = [
        ProductInline,
    ]
    def response_add(self, request, obj, post_url_continue='../%s/'):
        if obj and obj.id:
            tasks.product_get_initial_info(obj.id)
        return super(ProductAdmin, self).response_add(request, obj, post_url_continue='../%s/')

相关的django源代码在这里: django/contrib/admin/options.py

class ModelAdmin(BaseModelAdmin):
    def add_view(self, request,...)
        # .... Many lines of code ...... not putting them here as they're not so relevant
        if all_valid(formsets) and form_validated:
            self.save_model(request, new_object, form, False)
            self.save_related(request, form, formsets, False)
            self.log_addition(request, new_object)
            # After saving everything response_add gets called with the newly created object
            return self.response_add(request, new_object)

答案 1 :(得分:2)

没有一种简单的方法可以做到这一点,这意味着你可能不会使用post_save信号将代码放在正确的位置。

也就是说,如果你真的想要,你可以使用threadlocal hack来访问请求对象,并确定当前运行的视图是否是管理视图。要了解如何执行threadlocal hack,请从django cookbook开始,但只保存整个请求而不是用户。请注意,许多人认为线程本地黑客是令人厌恶的。这是一个discussion。我认为他们有一个非常有用的地方,但不知道更多,我猜你有更好的解决方案。