workflow: guarantee jump identifiers unicity on new workflows (#74132) #303
|
@ -4044,3 +4044,45 @@ def test_forms_last_test_result(pub, formdef):
|
|||
for url in ('/backoffice/forms/1/', '/backoffice/forms/1/fields/'):
|
||||
resp = app.get(url)
|
||||
assert '<h2>form title</h2>' in resp.text
|
||||
|
||||
|
||||
def test_jump_identifiers_unicity(pub):
|
||||
create_superuser(pub)
|
||||
|
||||
# create a workflow with existing identifier duplication
|
||||
Workflow.wipe()
|
||||
workflow = Workflow(name='foo')
|
||||
st1 = workflow.add_status(name='bar')
|
||||
st2 = workflow.add_status(name='baz')
|
||||
choice1 = st1.add_action('choice')
|
||||
choice1.by = ['logged-users']
|
||||
choice1.status = 'wf-%s' % st2.id
|
||||
choice1.label = 'choice1'
|
||||
choice1.identifier = 'id1'
|
||||
choice2 = st1.add_action('choice')
|
||||
choice2.by = ['logged-users']
|
||||
choice2.status = 'wf-%s' % st2.id
|
||||
choice2.label = 'choice2'
|
||||
choice2.identifier = 'id1'
|
||||
workflow.store()
|
||||
|
||||
app = login(get_app(pub))
|
||||
# check that we can edit the action even a duplication on identifier exists
|
||||
resp = app.get('/backoffice/workflows/%s/status/%s/items/%s/' % (workflow.id, st1.id, choice2.id))
|
||||
resp.form['set_marker_on_status'] = True
|
||||
resp = resp.form.submit('submit')
|
||||
resp = resp.follow()
|
||||
assert resp.location == 'http://example.net/backoffice/workflows/%s/status/%s/' % (workflow.id, st1.id)
|
||||
|
||||
# change identifier
|
||||
resp = app.get('/backoffice/workflows/%s/status/%s/items/%s/' % (workflow.id, st1.id, choice2.id))
|
||||
resp.form['identifier'] = 'id2'
|
||||
resp = resp.form.submit('submit')
|
||||
resp = resp.follow()
|
||||
assert resp.location == 'http://example.net/backoffice/workflows/%s/status/%s/' % (workflow.id, st1.id)
|
||||
|
||||
# try to re introduce a duplication leads to a form error
|
||||
resp = app.get('/backoffice/workflows/%s/status/%s/items/%s/' % (workflow.id, st1.id, choice2.id))
|
||||
resp.form['identifier'] = 'id1'
|
||||
resp = resp.form.submit('submit')
|
||||
assert 'A jump with the same identifier already exists.' in resp.text
|
||||
|
|
|
@ -1348,6 +1348,13 @@ class Workflow(StorableObject):
|
|||
user_roles = set(user.get_roles())
|
||||
return management_roles.intersection(user_roles)
|
||||
|
||||
def get_identified_jumps(self):
|
||||
for item in self.get_all_items():
|
||||
if isinstance(item, WorkflowStatusItem):
|
||||
identifier = getattr(item, 'identifier', None)
|
||||
if identifier:
|
||||
yield (item, identifier)
|
||||
|
||||
|
||||
class XmlSerialisable:
|
||||
node_name = None
|
||||
|
@ -2729,6 +2736,20 @@ class WorkflowStatusItem(XmlSerialisable):
|
|||
for parameter in self.get_parameters():
|
||||
self.add_parameters_widgets(form, [parameter])
|
||||
|
||||
def clean_identifier(self, form):
|
||||
widget = form.get_widget('identifier')
|
||||
value = widget.parse()
|
||||
if not value:
|
||||
|
||||
return False
|
||||
if value == self.identifier:
|
||||
# we don't want to block if a duplication of identifier already exists
|
||||
return False
|
||||
for jump, jump_identifier in self.get_workflow().get_identified_jumps():
|
||||
if jump is not self and jump_identifier == value:
|
||||
widget.set_error(_('A jump with the same identifier already exists.'))
|
||||
return True
|
||||
return False
|
||||
|
||||
def submit_admin_form(self, form):
|
||||
for f in self.get_parameters():
|
||||
widget = form.get_widget(f)
|
||||
|
|
Loading…
Reference in New Issue
Je voulais commenter le self.parent.parent que je trouve toujours peu lisible mais il n'y avait pas vraiemnt d'autre possibilité, j'ai fait #312 comme ça il pourra être écrit self.get_workflow().get_identified_jumps() et ça sera plus clair.
Voilà.