formdefs: keep track of allocated field ids (#3363)
This commit is contained in:
parent
95b012f7d3
commit
8163d7e267
|
@ -405,3 +405,57 @@ def test_urlname_change():
|
|||
assert formdef.url_name == 'tests'
|
||||
|
||||
assert data_class.count() == 1
|
||||
|
||||
@postgresql
|
||||
def test_sql_table_add_and_remove_fields():
|
||||
test_formdef = FormDef()
|
||||
test_formdef.name = 'tests and and remove fields'
|
||||
test_formdef.fields = []
|
||||
test_formdef.store()
|
||||
assert test_formdef.table_name is not None
|
||||
data_class = test_formdef.data_class(mode='sql')
|
||||
assert data_class.count() == 0
|
||||
|
||||
test_formdef.fields = [
|
||||
fields.StringField(label='string'),
|
||||
fields.EmailField(label='email'),
|
||||
]
|
||||
|
||||
for field in test_formdef.fields:
|
||||
if field.id is None:
|
||||
field.id = test_formdef.get_new_field_id()
|
||||
test_formdef.store()
|
||||
|
||||
test_formdef.fields.append(
|
||||
fields.ItemField(label='item', items=('apple', 'pear', 'peach', 'apricot')))
|
||||
test_formdef.fields[-1].id = test_formdef.get_new_field_id()
|
||||
test_formdef.store()
|
||||
|
||||
data_class = test_formdef.data_class(mode='sql')
|
||||
data_class.select()
|
||||
|
||||
previous_id = test_formdef.fields[-1].id
|
||||
test_formdef.fields = test_formdef.fields[:-1]
|
||||
test_formdef.store()
|
||||
|
||||
data_class = test_formdef.data_class(mode='sql')
|
||||
data_class.select()
|
||||
|
||||
test_formdef.fields.append(fields.StringField(label='item'))
|
||||
test_formdef.fields[-1].id = test_formdef.get_new_field_id()
|
||||
test_formdef.store()
|
||||
|
||||
assert test_formdef.fields[-1].id != previous_id
|
||||
|
||||
data_class = test_formdef.data_class(mode='sql')
|
||||
data_class.select()
|
||||
|
||||
test_formdef.fields = test_formdef.fields[:-1]
|
||||
test_formdef.fields.append(
|
||||
fields.ItemField(label='item', items=('apple', 'pear', 'peach', 'apricot')))
|
||||
test_formdef.fields[-1].id = test_formdef.get_new_field_id()
|
||||
test_formdef.store()
|
||||
|
||||
data_class = test_formdef.data_class(mode='sql')
|
||||
data_class.select()
|
||||
|
||||
|
|
|
@ -160,14 +160,8 @@ class FieldDefPage(Directory):
|
|||
field_pos = self.objectdef.fields.index(self.field)
|
||||
fields = self.objectdef.fields
|
||||
new_field = copy.copy(self.field)
|
||||
def lax_int(s):
|
||||
try:
|
||||
return int(s)
|
||||
except (ValueError, TypeError):
|
||||
return -1
|
||||
# allocate a new id
|
||||
id = str(max([lax_int(x.id) for x in self.objectdef.fields]) + 1)
|
||||
new_field.id = id
|
||||
new_field.id = self.objectdef.get_new_field_id()
|
||||
fields.insert(field_pos+1, new_field)
|
||||
self.objectdef.store()
|
||||
if self.page_no:
|
||||
|
@ -372,12 +366,6 @@ class FieldsDirectory(Directory):
|
|||
get_session().message = ('error', _('Submitted form was not filled properly.'))
|
||||
return redirect('.')
|
||||
|
||||
def lax_int(s):
|
||||
try:
|
||||
return int(s)
|
||||
except (ValueError, TypeError):
|
||||
return -1
|
||||
|
||||
try:
|
||||
page_no = int(form.get_widget('page_no').parse())
|
||||
except (TypeError, ValueError):
|
||||
|
@ -399,22 +387,15 @@ class FieldsDirectory(Directory):
|
|||
insertion_point = len(self.objectdef.fields)
|
||||
|
||||
if form.get_widget('label').parse() and form.get_widget('type').parse():
|
||||
if self.objectdef.fields:
|
||||
id = str(max([lax_int(x.id) for x in self.objectdef.fields]) + 1)
|
||||
else:
|
||||
id = '1'
|
||||
self.objectdef.fields.insert(insertion_point,
|
||||
fields.get_field_class_by_type(form.get_widget('type').parse())(
|
||||
label = form.get_widget('label').parse(),
|
||||
type = form.get_widget('type').parse(),
|
||||
id = id))
|
||||
id =self.objectdef.get_new_field_id()))
|
||||
elif form.get_widget('form').parse():
|
||||
formdef = FormDef.get(form.get_widget('form').parse())
|
||||
for j, field in enumerate(formdef.fields):
|
||||
if self.objectdef.fields:
|
||||
field.id = str(max([lax_int(x.id) for x in self.objectdef.fields]) + 1)
|
||||
else:
|
||||
field.id = '1'
|
||||
field.id = self.objectdef.get_new_field_id()
|
||||
self.objectdef.fields.insert(insertion_point+j, field)
|
||||
else:
|
||||
get_session().message = ('error', _('Submitted form was not filled properly.'))
|
||||
|
|
|
@ -138,35 +138,8 @@ class FormDefUI:
|
|||
else:
|
||||
formdef.roles = []
|
||||
|
||||
def lax_int(s):
|
||||
try:
|
||||
return int(s)
|
||||
except ValueError:
|
||||
return -1
|
||||
|
||||
if not formdef.fields:
|
||||
formdef.fields = []
|
||||
if form.get_widget('fields'):
|
||||
new_fields = []
|
||||
for field in form.get_widget('fields').parse():
|
||||
if not field['label']:
|
||||
if field['id']:
|
||||
formdef.fields = [x for x in formdef.fields if x.id != field['id']]
|
||||
continue
|
||||
if field['id']:
|
||||
form_field = [x for x in formdef.fields if x.id == field['id']][0]
|
||||
else:
|
||||
form_field = FormField()
|
||||
if formdef.fields or new_fields:
|
||||
form_field.id = str(max([
|
||||
lax_int(x.id) for x in formdef.fields + new_fields]) + 1)
|
||||
else:
|
||||
form_field.id = '1'
|
||||
form_field.label = field['label']
|
||||
form_field.type = field['type']
|
||||
new_fields.append(form_field)
|
||||
|
||||
formdef.fields = new_fields
|
||||
|
||||
formdef.store()
|
||||
|
||||
|
@ -1076,11 +1049,6 @@ class FormsDirectory(AccessControlled, Directory):
|
|||
form = formdefui.new_form_ui()
|
||||
if form.get_widget('cancel').parse():
|
||||
return redirect('.')
|
||||
redo = False
|
||||
if form.get_widget('fields') and \
|
||||
form.get_widget('fields').get_widget('add_element').parse():
|
||||
form.clear_errors()
|
||||
redo = True
|
||||
|
||||
if form.is_submitted() and not form.has_errors() and not redo:
|
||||
try:
|
||||
|
|
|
@ -53,6 +53,13 @@ class FormField:
|
|||
self.real_field = fields.get_field_class_by_type(type)(**dict)
|
||||
|
||||
|
||||
def lax_int(s):
|
||||
try:
|
||||
return int(s)
|
||||
except (ValueError, TypeError):
|
||||
return -1
|
||||
|
||||
|
||||
class FormDef(StorableObject):
|
||||
_names = 'formdefs'
|
||||
_indexes = ['url_name']
|
||||
|
@ -84,6 +91,8 @@ class FormDef(StorableObject):
|
|||
last_modification_time = None
|
||||
last_modification_user_id = None
|
||||
|
||||
max_field_id = None
|
||||
|
||||
def migrate(self):
|
||||
changed = False
|
||||
|
||||
|
@ -147,6 +156,10 @@ class FormDef(StorableObject):
|
|||
self.table_name = sql.get_formdef_table_name(self)
|
||||
changed = True
|
||||
|
||||
if self.max_field_id is None and self.fields:
|
||||
self.max_field_id = max([lax_int(x.id) for x in self.fields])
|
||||
changed = True
|
||||
|
||||
if changed:
|
||||
self.store()
|
||||
|
||||
|
@ -171,6 +184,14 @@ class FormDef(StorableObject):
|
|||
setattr(sys.modules['wcs.formdef'], self.url_name.title(), cls)
|
||||
return cls
|
||||
|
||||
def get_new_field_id(self):
|
||||
if self.max_field_id is None:
|
||||
field_id = 1
|
||||
else:
|
||||
field_id = self.max_field_id + 1
|
||||
self.max_field_id = field_id
|
||||
return str(field_id)
|
||||
|
||||
def get_new_url_name(self):
|
||||
new_url_name = simplify(self.name)
|
||||
base_new_url_name = new_url_name
|
||||
|
@ -377,7 +398,6 @@ class FormDef(StorableObject):
|
|||
|
||||
return json.dumps(root)
|
||||
|
||||
|
||||
def export_to_xml(self, include_id=False):
|
||||
charset = get_publisher().site_charset
|
||||
root = ET.Element('formdef')
|
||||
|
@ -393,7 +413,9 @@ class FormDef(StorableObject):
|
|||
value = 'true'
|
||||
else:
|
||||
value = 'false'
|
||||
ET.SubElement(root, boolean_attribute).text = value
|
||||
ET.SubElement(root, boolean_attribute).text = value
|
||||
if self.max_field_id:
|
||||
ET.SubElement(root, 'max_field_id').text = str(self.max_field_id)
|
||||
only_allow_one = False
|
||||
allow_drafts = False
|
||||
fields = ET.SubElement(root, 'fields')
|
||||
|
@ -426,8 +448,15 @@ class FormDef(StorableObject):
|
|||
field_o.init_with_xml(field, charset, include_id=include_id)
|
||||
if not field_o.id:
|
||||
# this assumes all fields will have id, or none of them
|
||||
field_o.id = str(i)
|
||||
field_o.id = str(i+1)
|
||||
formdef.fields.append(field_o)
|
||||
|
||||
value = tree.find('max_field_id')
|
||||
if value is not None:
|
||||
formdef.max_field_id = int(value)
|
||||
else:
|
||||
formdef.max_field_id = max([lax_int(x.id) for x in formdef.fields])+1
|
||||
|
||||
if tree.find('category') is not None:
|
||||
category = tree.find('category').text.encode(charset)
|
||||
cats = Category.select()
|
||||
|
|
|
@ -142,6 +142,7 @@ def do_formdef_tables(formdef):
|
|||
|
||||
# add new fields
|
||||
for field in formdef.fields:
|
||||
assert field.id is not None
|
||||
sql_type = SQL_TYPE_MAPPING.get(field.key, 'varchar')
|
||||
if sql_type is None:
|
||||
continue
|
||||
|
|
Loading…
Reference in New Issue