Opened 4 years ago

Closed 4 years ago

Last modified 4 years ago

#31879 closed Uncategorized (invalid)

Changing a model formset's queryset has no effect when self.forms is accessed

Reported by: kemar Owned by: nobody
Component: Forms Version: 3.1
Severity: Normal Keywords: formsets
Cc: Triage Stage: Unreviewed
Has patch: no Needs documentation: no
Needs tests: no Patch needs improvement: no
Easy pickings: no UI/UX: no

Description

The Model formsets documentation suggests a way to override the default queryset:

class BaseAuthorFormSet(BaseModelFormSet):
    def __init__(self, *args, **kwargs):
        super().__init__(*args, **kwargs)
        self.queryset = Author.objects.filter(name__startswith='O')

However, accessing self.forms anywhere before self.queryset will trigger get_queryset() and silently populate self._queryset with all objects in the model so that the next self.queryset will have no effect:

class BaseAuthorFormSet(BaseModelFormSet):
    def __init__(self, *args, **kwargs):
        super().__init__(*args, **kwargs)
        for form in self.forms:
            form.empty_permitted = False
        self.queryset = Author.objects.filter(name__startswith='O')  # No effect.

Can't tell if it's a bug or an intended behaviour?

Change History (2)

comment:1 by Carlton Gibson, 4 years ago

Resolution: invalid
Status: newclosed

This is expected behaviour. We call get_queryset() when generating the forms — if you generate them before setting the queryset attribute then it'll be too late to have effect. The underlying _queryset cache is an optimisation for almost all use-cases. It can be cleared, or you can override get_queryset() if needed.

Please don't use the issue tracker for this kind of usage question. See TicketClosingReasons/UseSupportChannels. Thanks.

comment:2 by kemar, 4 years ago

Understood. Thank you for taking the time to answer so carefully.

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