Opened 11 years ago

Closed 11 years ago

Last modified 11 years ago

#20136 closed Cleanup/optimization (fixed)

Recommend note identifying that post_save signals will be fired on loaddata

Reported by: brandon@… Owned by: nobody
Component: Documentation Version: 1.5
Severity: Normal Keywords: loaddata
Cc: Triage Stage: Accepted
Has patch: yes Needs documentation: no
Needs tests: no Patch needs improvement: no
Easy pickings: yes UI/UX: no

Description

On: https://docs.djangoproject.com/en/dev/ref/django-admin/#loaddata-fixture-fixture

It says the following:

  • When fixture files are processed, the data is saved to the database as is. Model defined save methods and pre_save signals are not called.

However, it does not make specific mention about other signals. Recommend making the text explicit so that readers understand that other signals not mentioned here will be called (post_save et al).

Example:

Let's say you're testing on a local server and you have use post_save to send emails or other notifications. loaddata will resend all emails on load. This is behaviour that, in a test environment, one may wish to avoid.

Related: https://code.djangoproject.com/ticket/8399

Attachments (2)

20136.diff (1.4 KB ) - added by Tim Graham 11 years ago.
20136.2.diff (2.8 KB ) - added by Tim Graham 11 years ago.

Download all attachments as: .zip

Change History (10)

by Tim Graham, 11 years ago

Attachment: 20136.diff added

comment:1 by Tim Graham, 11 years ago

Has patch: set
Type: UncategorizedCleanup/optimization

Added a patch which also attempts to address #13299 since it's related.

comment:2 by brandon@…, 11 years ago

Just looking at the diff, I asked a similar question to 8399 and 13299. The answer suggested creating a decorator to block the signal from loaddata. Seems like it may be a better solution than increasing cyclomatic complexity in signal functions.

Source: http://stackoverflow.com/questions/15624817/have-loaddata-ignore-or-disable-post-save-signals/15625121#15625121

from functools import wraps
def disable_for_loaddata(signal_handler):
    """
    Decorator that turns off signal handlers when loading fixture data.
    """

    @wraps(signal_handler)
    def wrapper(*args, **kwargs):
        if kwargs['raw']:
            return
        signal_handler(*args, **kwargs)
    return wrapper
Then:

@disable_for_loaddata
def your_fun(**kwargs):
    ## stuff that won't happen if the signal is initiated by loaddata process

comment:3 by Anssi Kääriäinen, 11 years ago

If I am not mistaken both pre_save and post_save signals will be sent. There is a raw argument to the signal that can be used to detect when loaddata (or any other method wishing to insert the values as-is to the DB). See https://docs.djangoproject.com/en/dev/ref/signals/#django.db.models.signals.pre_save.

It seems the loaddata docs are currently plain wrong.

comment:4 by Tim Graham, 11 years ago

Patch needs improvement: set
Triage Stage: UnreviewedAccepted

I wouldn't be opposed to documenting the decorator method as I've used it before as well.

comment:5 by brandon@…, 11 years ago

That decorator creates some unintended consequences when used in conjunction with django-tastypie (API POST calls skip signals with that decorator). Perhaps not entirely relevant here, but "nice to know".

by Tim Graham, 11 years ago

Attachment: 20136.2.diff added

comment:6 by Tim Graham, 11 years ago

Patch needs improvement: unset

Anssi is correct, I've fixed that inaccuracy and added the decorator example.

comment:7 by Tim Graham <timograham@…>, 11 years ago

Resolution: fixed
Status: newclosed

In 2c62a509deb50e39375b0cd44cfc85a743978fdc:

Fixed #20136 - Fixed and expanded the docs for loaddata and model signals.

Thanks brandon@ and Anssi for the report.

comment:8 by Tim Graham <timograham@…>, 11 years ago

In 18a2fb19074ce6789639b62710c279a711dabf97:

[1.5.X] Fixed #20136 - Fixed and expanded the docs for loaddata and model signals.

Thanks brandon@ and Anssi for the report.

Backport of 2c62a509de from master

Note: See TracTickets for help on using tickets.
Back to Top