Commit c24e22bb authored by Jeremy Kerr's avatar Jeremy Kerr
Browse files

forms: change MultiplePatchForm from a ModelForm to a Form

ModelForm was causing validation issues, especially with no-change
fields on required model fields.

Add a test for updating a required field (state) through

Change it to a normal form, and call instance.setattr manually. This
makes the new test pass.
Signed-off-by: default avatarJeremy Kerr <>
parent 01733fbd
......@@ -176,38 +176,22 @@ class MultipleBooleanField(forms.ChoiceField):
def is_no_change(self, value):
return value == self.no_change_choice[0]
class MultiplePatchForm(PatchForm):
class MultiplePatchForm(forms.Form):
state = OptionalModelChoiceField(queryset = State.objects.all())
archived = MultipleBooleanField()
def __init__(self, project, *args, **kwargs):
super(MultiplePatchForm, self).__init__(project = project,
*args, **kwargs)
super(MultiplePatchForm, self).__init__(*args, **kwargs)
self.fields['delegate'] = OptionalDelegateField(project = project,
required = False)
def _clean_fields(self):
super(MultiplePatchForm, self)._clean_fields()
# remove optional fields
opts = self.instance._meta
for f in opts.fields:
if not in self.cleaned_data:
field = self.fields.get(, None)
if field is None:
if field.is_no_change(self.cleaned_data[]):
del self.cleaned_data[]
def save(self, instance, commit = True):
opts = instance.__class__._meta
if self.errors:
raise ValueError("The %s could not be changed because the data "
"didn't validate." % opts.object_name)
data = self.cleaned_data
# remove 'no change fields' from the data
# Update the instance
for f in opts.fields:
if not in data:
......@@ -217,10 +201,13 @@ class MultiplePatchForm(PatchForm):
if field.is_no_change(data[]):
del data[]
setattr(instance,, data[])
return forms.save_instance(self, instance,
self._meta.fields, 'changed', commit)
if commit:
return instance
class UserPersonLinkForm(forms.Form):
email = forms.EmailField(max_length = 200)
......@@ -72,6 +72,25 @@ class MultipleUpdateTest(TestCase):
['The submitted form data was invalid'])
def testDelegateChange(self):
delegate = create_maintainer(defaults.project)
data = {'action': 'Update',
'project': str(,
'form': 'patchlistform',
'archived': '*',
'state': '*',
'delegate': str(,
for patch in self.patches:
data['patch_id:%d' %] = 'checked'
url = reverse('patchwork.views.patch.list',
args = [defaults.project.linkname])
response =, data)
self.failUnlessEqual(response.status_code, 200)
for patch in [Patch.objects.get(pk = for p in self.patches]:
self.assertEquals(patch.delegate, delegate)
def tearDown(self):
for p in self.patches:
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment