Opened 7 years ago

Last modified 5 months ago

#12134 new Bug

contrib.admin.RelatedFieldWidgetWrapper.__deepcopy__() should copy() the widget attrs

Reported by: ubernostrum Owned by: nobody
Component: contrib.admin Version: 1.1
Severity: Normal Keywords:
Cc: Triage Stage: Accepted
Has patch: no Needs documentation: no
Needs tests: no Patch needs improvement: no
Easy pickings: no UI/UX: no


Otherwise it ends up with a shallow copy which reuses the same attrs dict across separate widget instances, playing merry hell with form classes which want to change widget attrs on a per-(form)-instance basis.

Attachments (1)

12134.diff (489 bytes) - added by ubernostrum 7 years ago.

Download all attachments as: .zip

Change History (7)

Changed 7 years ago by ubernostrum

comment:1 Changed 7 years ago by brosner

  • Needs documentation unset
  • Needs tests unset
  • Patch needs improvement unset
  • Triage Stage changed from Unreviewed to Accepted

comment:2 Changed 6 years ago by lukeplant

I think we need some more analysis of why this patch is correct/needed. Here are some simplified extracts of current code:

class RelatedFieldWidgetWrapper(forms.Widget):
    def __init__(self, widget, rel, admin_site):
        self.attrs = widget.attrs
        self.widget = widget
        # <snip>

    def __deepcopy__(self, memo):
        obj = copy.copy(self)
        obj.widget = copy.deepcopy(self.widget, memo)
        obj.attrs = self.widget.attrs
        memo[id(self)] = obj
        return obj

This means:

wrapper1 = RelatedFieldWidgetWrapper(some_widget, some_rel, some_admin_site)
wrapper2 = copy.deepcopy(wrapper1) # as happens when widget is copied via BaseForm.__init__()

assert wrapper1.attrs is wrapper1.widget.attrs
assert wrapper2.attrs is wrapper2.widget.attrs
assert wrapper1.widget is not wrapper2.widget

That all seems to be correct. The attached patch would actually break the second assert, which I'm pretty sure will break the ability of the class instance to work as a wrapper.

comment:3 Changed 5 years ago by mattmcc

  • Severity set to Normal
  • Type set to Bug

comment:4 Changed 4 years ago by aaugustin

  • UI/UX unset

Change UI/UX from NULL to False.

comment:5 Changed 4 years ago by aaugustin

  • Easy pickings unset

Change Easy pickings from NULL to False.

comment:6 Changed 5 months ago by timgraham

I think #26213 gives a demonstration of a behavior which this ticket may fix.

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