Skip to content

Commit

Permalink
FV: throw BadMethodCallException when set_rules() called without
Browse files Browse the repository at this point in the history
  • Loading branch information
narfbg committed Oct 20, 2016
1 parent 34fe402 commit 5d05372
Show file tree
Hide file tree
Showing 4 changed files with 17 additions and 2 deletions.
6 changes: 5 additions & 1 deletion system/libraries/Form_validation.php
Expand Up @@ -164,7 +164,7 @@ public function __construct($rules = array())
* @param array $errors
* @return CI_Form_validation
*/
public function set_rules($field, $label = '', $rules = array(), $errors = array())
public function set_rules($field, $label = null, $rules = null, $errors = array())
{
// No reason to set rules if we have no POST data
// or a validation array has not been specified
Expand Down Expand Up @@ -197,6 +197,10 @@ public function set_rules($field, $label = '', $rules = array(), $errors = array

return $this;
}
elseif ( ! isset($rules))
{
throw new BadMethodCallException('Form_validation: set_rules() called without a $rules parameter');
}

// No fields or no rules? Nothing to do...
if ( ! is_string($field) OR $field === '' OR empty($rules))
Expand Down
6 changes: 6 additions & 0 deletions tests/codeigniter/libraries/Form_validation_test.php
Expand Up @@ -435,6 +435,12 @@ public function test_run()
$this->assertFalse($form_validation->run('fail'));
}

public function test_set_rules_exception()
{
$this->setExpectedException('BadMethodCallException');
$this->form_validation->set_rules('foo', 'bar');
}

public function test_has_rule()
{
$this->form_validation->reset_validation();
Expand Down
4 changes: 4 additions & 0 deletions user_guide_src/source/changelog.rst
Expand Up @@ -23,6 +23,10 @@ Release Date: Not Released
- Removed the *socket_type* configuration setting from the 'redis' driver.
- Changed data serialization logic in 'redis' driver for better performance.

- :doc:`Form Validation Library <libraries/form_validation>` changes include:

- Changed method ``set_rules()`` to throw a ``BadMethodCallException`` when its first parameter is not an array and the ``$rules`` one is unused.

- Database

- Changed method ``initialize()`` to return void and instead throw a ``RuntimeException`` in case of failure.
Expand Down
3 changes: 2 additions & 1 deletion user_guide_src/source/libraries/form_validation.rst
Expand Up @@ -1027,13 +1027,14 @@ Class Reference

.. php:class:: CI_Form_validation
.. php:method:: set_rules($field[, $label = ''[, $rules = ''[, $errors = array()]]])
.. php:method:: set_rules($field[, $label = null[, $rules = null[, $errors = array()]]])
:param string $field: Field name
:param string $label: Field label
:param mixed $rules: Validation rules, as a string list separated by a pipe "|", or as an array or rules
:param array $errors: A list of custom error messages
:returns: CI_Form_validation instance (method chaining)
:throws: BadMethodCallException If $field is not an array and $rules was not used
:rtype: CI_Form_validation
Permits you to set validation rules, as described in the tutorial
Expand Down

1 comment on commit 5d05372

@dafriend
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I am wondering if this block

// Houston, we have a problem...
if ( ! isset($row['field'], $row['rules']))
{
     continue;
}

doesn't short-circuit the intent of the 'BadMethodCallException' block and, in doing so, create inconsistent behavior?

Would something along these lines be more appropriate?

foreach ($field as $row)
{
    // Houston, we have a problem...
    if ( ! isset($row['field']))
    {
        continue;
    }

    // If the field label wasn't passed we use the field name
    $label = isset($row['label']) ? $row['label'] : $row['field'];

    // If rules are not passed use NULL which will result in an exception during the recursive call
    $rules = isset($row['rules']) ? $row['rules'] : NULL;

    // Add the custom error message array
    $errors = (isset($row['errors']) && is_array($row['errors'])) ? $row['errors'] : array();

    // Here we go!
    $this->set_rules($row['field'], $label, $rules, $errors);
}

Please sign in to comment.