Skip to content

Commit

Permalink
feat: Show a list of errors if a form is submitted with invalid data
Browse files Browse the repository at this point in the history
  • Loading branch information
live627 committed Mar 25, 2021
1 parent 2d4e575 commit facb90a
Show file tree
Hide file tree
Showing 4 changed files with 54 additions and 44 deletions.
18 changes: 10 additions & 8 deletions src/Class-CustomForm.php
Expand Up @@ -173,7 +173,7 @@ public function validate(): bool
$found = isset(array_flip($this->type_vars)[$this->value]) || !empty($this->default);

if (!$found && $this->required)
$this->err = array('pf_invalid_value', $this->field['name']);
$this->err = array('customform_invalid_value', $this->field['text']);

return $found;
}
Expand Down Expand Up @@ -233,8 +233,8 @@ public function getValue(): string
}
public function validate(): bool
{
if ($this->exists && $this->required)
$this->err = array('pf_invalid_value', $this->field['name']);
if (!$this->exists && $this->required)
$this->err = array('customform_invalid_value', $this->field['text']);

//~ $class_name = 'CustomFormFieldMask_' . $this->field['mask'];
//~ if (!class_exists($class_name))
Expand All @@ -244,6 +244,8 @@ public function validate(): bool
//~ $mask->validate(): bool;
//~ if (false !== ($err = $mask->getError()))
//~ $this->err = $err;

return empty($this->err);
}
}

Expand Down Expand Up @@ -286,7 +288,7 @@ class CustomFormFieldMask_email extends CustomFormFieldMaskBase
public function validate(): bool
{
if (!preg_match('~^[0-9A-Za-z=_+\-/][0-9A-Za-z=_\'+\-/\.]*@[\w\-]+(\.[\w\-]+)*(\.[\w]{2,6})$~', $this->value))
$this->err = array('pf_invalid_value', $this->field['name']);
$this->err = array('customform_invalid_value', $this->field['text']);
}
}

Expand All @@ -298,7 +300,7 @@ public function validate(): bool
if (!empty($this->field['err']))
$this->err = $this->field['err'];
else
$this->err = array('pf_invalid_value', $this->field['name']);
$this->err = array('customform_invalid_value', $this->field['text']);
}
}

Expand All @@ -307,7 +309,7 @@ class CustomFormFieldMask_number extends CustomFormFieldMaskBase
public function validate(): bool
{
if (!preg_match('/^\s*([0-9]+)\s*$/', $this->value))
$this->err = array('pf_invalid_value', $this->field['name']);
$this->err = array('customform_invalid_value', $this->field['text']);
}
}

Expand All @@ -316,7 +318,7 @@ class CustomFormFieldMask_float extends CustomFormFieldMaskBase
public function validate(): bool
{
if (!preg_match('/^\s*([0-9]+(\.[0-9]+)?)\s*$/', $this->value))
$this->err = array('pf_invalid_value', $this->field['name']);
$this->err = array('customform_invalid_value', $this->field['text']);
}
}

Expand All @@ -325,7 +327,7 @@ class CustomFormFieldMask_nohtml extends CustomFormFieldMaskBase
public function validate(): bool
{
if (strip_tags($this->value) != $this->value)
$this->err = array('pf_invalid_value', $this->field['name']);
$this->err = array('customform_invalid_value', $this->field['text']);
}
}

Expand Down
4 changes: 4 additions & 0 deletions src/CustomForm.english.php
Expand Up @@ -81,6 +81,10 @@
$txt['customform_regex'] = 'Regex';
$txt['customform_regex_desc'] = 'Validate your own way.';

// Validation errors
$txt['customform_error_title'] = 'Oops, there were errors!';
$txt['customform_invalid_value'] = 'The value you chose for %1$s is invalid.';

// Help text for the general settings page.
$helptxt['customform_view_perms'] =
'This setting allows you to restrict the member groups that can see the list of the forms which they can access (At "index.php?action=form"). Note that even if they can see they list, they cannot see or use any forms which they do not have the permissions for.';
Expand Down
59 changes: 23 additions & 36 deletions src/CustomForm.php
Expand Up @@ -93,62 +93,48 @@ function CustomForm()
if (empty($data))
redirectExit("action=form;");

$fail_submit = false;
require_once($sourcedir . '/Class-CustomForm.php');

// Do we need to submit this form?
if (isset($_GET['submit']))
{
checkSession();
$vars = array();
$replace = array();
$i = -1;
$post_errors = array();
if ('' != ($sc_error = checkSession('post', '', false)))
$post_errors[] = array(['error_' . $sc_error, '']);
if ($context['require_verification'])
{
require_once($sourcedir . '/Subs-Editor.php');
$verificationOptions = array(
'id' => 'customform',
);
if (true !== ($verification_errors = create_control_verification($verificationOptions, true)))
foreach ($verification_errors as $verification_error)
$post_errors[] = ['error_' . $verification_error, ''];
}

// Check for valid post data from the forms fields.
foreach ($data as $field)
{
$i++;
$value = isset($_POST['CustomFormField'][$field['id_field']]) ? $_POST['CustomFormField'][$field['id_field']] : '';
$class_name = 'CustomForm_' . $field['type'];
$class_name = 'CustomForm_' . $field['type2'];
if (!class_exists($class_name))
fatal_error('Param "' . $field['type'] . '" not found for field "' . $field['text'] . '" at ID #' . $field['id_field'] . '.', false);
fatal_error('Param "' . $field['type2'] . '" not found for field "' . $field['text'] . '" at ID #' . $field['id_field'] . '.', false);

$type = new $class_name($field, $value, !empty($value));
$type = new $class_name($field, $_POST['CustomFormField'][$field['id_field']] ?? '');
$type->setOptions();
if (!$type->validate())
{
$post_errors[] = $type->getError();
// Do the 'fail form/field' stuff.
$data[$i]['failed'] = true;
$fail_submit = true;
$post_errors['id_field_' . $field['id_field']] = $type->getError();
continue;
}

// Add this fields value to the list of variables for the output post.
$vars[$field['title']] = $value;
}

// Check whether the visual verification code was entered correctly.
$context['require_verification'] =
$user_info['is_guest'] || !$user_info['is_mod'] && !$user_info['is_admin'] && !empty($modSettings['posts_require_captcha']) && ($user_info['posts'] < $modSettings['posts_require_captcha']);
if ($context['require_verification'])
{
require_once($sourcedir . '/Subs-Editor.php');
$verificationOptions = array(
'id' => 'register',
);
$context['visual_verification'] = create_control_verification($verificationOptions, true);

if (is_array($context['visual_verification']))
{
loadLanguage('Errors');
foreach ($context['visual_verification'] as $error)
fatal_error($txt['error_' . $error], false);
}
$vars[$field['title']] = $type->getValue();
}

// Do we have completly valid field data?
if (!$fail_submit)
if ($post_errors === [])
{
require_once($sourcedir . '/Subs-Post.php');
$msgOptions = array(
Expand Down Expand Up @@ -184,6 +170,7 @@ function CustomForm()
else
redirectexit("$exit");
}
$context['post_errors'] = $post_errors;
}

// Otherwise we shall show the submit form page.
Expand Down Expand Up @@ -228,7 +215,7 @@ function CustomForm()
'type' => $field['type'],
'html' => $type->getInputHtml(),
'required' => $required,
'failed' => isset($field['failed']),
'failed' => isset($post_errors['id_field_' . $field['id_field']]),
);
}

Expand All @@ -237,12 +224,12 @@ function CustomForm()
redirectExit("action=form;");

// Load the language files.
loadLanguage('CustomForm+Post');
loadLanguage('CustomForm+Post+Errors');

// Setup and load the necessary template related stuff.
$context['settings_title'] =
'<a href="' . $scripturl . '?action=form;">' . ((isset($modSettings['customform_view_title']) && ($modSettings['customform_view_title'] != '')) ? $modSettings['customform_view_title'] : $txt['customform_tabheader']) . '</a> : ' . $form_title;
$context['failed_form_submit'] = $fail_submit;
$context['failed_form_submit'] = empty($post_errors);
$context['template_function'] = $form_data['template_function'];
$context['post_url'] = $scripturl . '?action=form;n=' . $form_id . ';submit;';
$context['sub_template'] = 'submit_form';
Expand Down
17 changes: 17 additions & 0 deletions src/CustomForm.template.php
Expand Up @@ -21,7 +21,24 @@ function form_template_submit_form()
<tr class="titlebg">
<td colspan="3">', $context['settings_title'], '</td>
</tr>';
if (!empty($context['post_errors']))
{
echo '
<tr class="windowbg2">
<td colspan="3">
<div class="errorbox">
<strong>', $txt['customform_error_title'], '</strong>
<ul class="error">';

foreach ($context['post_errors'] as $error)
if (!empty($error))
echo '
<li>', sprintf($txt[$error[0]], $error[1]), '</li>';

echo '
</ul></td>
</tr>';
}
// Here you can add rows to the beginning of the table, if you want to...
/* Like this:
echo '
Expand Down

0 comments on commit facb90a

Please sign in to comment.