Reputation: 1439
After upgrading from Django 1.8 (python 2.7) to Django 2.0 (python 3.6) I have an error with this form and reverse m2m widget:
models.py
class Treatment(Model):
...
class Specialty(Model):
treatment = models.ManyToManyField(Treatment, related_name='specialties', blank=True)
...
. This is the Form for the treatment model. It allows to also edit the specialties (reverse m2m). It worked fine before the upgrade.
forms.py
class TreatDetail(forms.ModelForm):
specialties = forms.ModelMultipleChoiceField(
queryset=Specialty.objects.all().order_by('specialty_de'),
required=False,
widget=FilteredSelectMultiple('Specialties', False),
)
def save(self, commit=True):
treatment = super(TreatDetail, self).save(commit=False)
if commit:
treatment.save()
if treatment.pk:
treatment.specialties = self.cleaned_data['specialties']
self.save_m2m()
return treatment
def __init__(self, *args, **kwargs):
super(TreatDetail, self).__init__(*args, **kwargs)
if self.instance and self.instance.pk:
self.fields['specialties'].initial = self.instance.specialties.all()
class Meta:
model = Treatment
fields = (
'top_treatment',
'treatment_de',
....)
I get this Error:
TypeError at /customadmin/treatdetail/2/de/ Direct assignment to the reverse side of a many-to-many set is prohibited. Use specialties.set() instead.
treatment.specialties = self.cleaned_data['specialties']
Of course I tried:
treatment.specialties.set = self.cleaned_data['specialties']
The error disappears, but the reverse m2m relation is not saved.
Can anybody help here?
Upvotes: 1
Views: 565
Reputation: 2671
You are doing that wrong. You have to add item to M2M
relation in Django 2.0 like this:
treatment.specialties.add(self.cleaned_data['specialties'])
If self.cleaned_data['specialties']
is a list of specialties - you have to iterate over them and add one by one in the same way to your treatment.specialties
.
Upvotes: 2