Documentation for Validator::Custom 1.0 and earlier

This page is a document prior to Validator::Custom 1.0. The latest version of the documentation is here.

Validator::Custom is useful for validation ( value validation ) of HTML form data It is a module. It features the ability to write validation rules with a small amount of description, the ability to set error messages for each constraint, the frequently used functions provided from the beginning, and the highly flexible design that allows easy addition of user-defined constraints.

use Validator::Custom;
my $vc = Validator::Custom->new;

# data
my $data = {
  price => 1200
  name =>'Perl',
  password =>'secret',
  passwrod2 =>'secret'
};

# Create rules
my $rule = $vc->create_rule($data, $rule);
$rule->require('price')->check('int')->message('price must be number');

$rule->optional('name')
  ->check('not_blank')->message('name is empty')
  ->check({length => [0, 20])->message('name is too long');

$rule->require('password')
  ->check('not_blank')->message('password is empty')
  ->check('ascii')->message('password contains invalid caharcters');

$rule->require(['password', 'password2'])->name('password_check')
  ->check('duplication')->message('Two password not match')
  ->copy(0);

# Validation
my $vresult = $vc->validate($data, $rule);

# Check the result
if ($vresult->is_ok) {
  # Safe data
  my $safe_data = $vresult->data;
}
else {
  # Error message
  my $errors = $vresult->messages;
}

Click here for the old grammar for rule creation. It is recommended to write in the new grammar above.

# Create rules (old grammar)
my $rule = [
  price => [
    [int =>'price must be number']
  ],,
  name => [
    [not_blank =>'name is empty'],
    [{length => [0, 20]} =>'name is too long']
  ],,
  password => [
    [not_blank =>'password is empty'],
    [ascii =>'password contains invalid caharcters']
  ],,
  {password_check => ['password', 'password2']}
    => {copy => 0}
    => [
      [duplication =>'Two password not match']
    ]
];;

This document will be rewritten to the new grammar, so please refer to the official grammar for the old grammar.

Install Validator::Custom

Use the cpan command to install Validator::Custom .

cpan Validator::Custom

It can be installed on both Windows and Unix-like operating systems. You can't install without root privileges with the cpan command, so if you want to install in your local environment, use a tool such as cpanm.

Validator::Create Custom Object

Use the new method to create a Validator::Custom object.

use Validator::Custom;
my $vc = Validator::Custom->new;

Use this object for validation.

Basics of validation

I will explain the basics of validation. See the source code below.

use Validator::Custom;
my $vc = Validator::Custom->new;

# data
my $data = {price => 1200};

# Create rules
my $rule = $vc->create_rule;
$rule->require('price')->check('int');

# Validation
my $vresult = $vc->validate($data, $rule);

# Check the result
if ($vresult->is_ok) {print "OK\n"}
else {print "Not OK\n"}

Data

The data to be validated must be a hash reference.

# data
my $data = {price => 1200};

Rules

Next, create a rule for validation.

# rule
my $rule = $vc->create_rule;
$rule->require('price')->check('int');

First, create a Validator::Custom::Rule object using the create_rule method.

my $rule = $vc->create_rule;

Then use the require method to describe the name of the key that must exist.

$rule->require('price')

You can also use optional instead of require if the key is arbitrary.

$rule->optional('price')

Next, describe the constraints.

$rule->require('price')->check('int');

This time we only check one key, but if you want to check multiple values, you can continue to write.

$rule->require('name')->check('string');

Validation

Use the validate method for validation.

# Validation
my $vresult = $vc->validate($data, $rule);

The return value is a Validator::Custom::Result object.

Confirmation of results

You can check the result using the Validator::Custom::Result object.

my $ok = $vresult->is_ok;

You can check if the validation result is correct with the is_ok method.

Validation of multiple values

Let's create a rule for validating multiple values.

# Data containing multiple values
my $data = {price => 1200, title =>'Perl'};

# Rules for validating multiple values
my $rule = $vc->create_rule;
$rule->require('price')->check('int');
$rule->require('title')->check('ascii');

To validate multiple values, just write require multiple times as follows: The contents of the rule are as follows.

my $rule = $vc->create_rule;
$rule->require('price')->check('int');
$rule->require('title')->check('ascii');

Register user - defined constraints - register_constraint

I was able to express various constraints using the constraints provided by default, and and or conditions. In addition to this, Validator::Custom allows you to create new user-defined constraints.

Here, I will simply register a constraint to check whether the email is in the correct format. Use the register_constraint method to register the constraint.

# Register a constraint to check if Email is in the correct format
$vc->register_constraint(
  email => sub {
    my $value = shift;
    
    # Returns 1 if correct, 0 if incorrect
    return 0 unless defined $value;
    return $value =~ /^. + @. +$/? 1: 0;
  }
);

The format for registering constraints is as follows.

$vc->register_constraint(
  Constraint name => Processing for constraints
);

You can also register multiple constraints at once.

$vc->register_constraint(
  Constraint name 1 => Processing for constraint 1,
  Constraint name 2 => Processing for constraint 2
);

The processing for constraints is a subroutine reference. Try to return 1 if the data is correct and 0 if it is incorrect.

sub constraint name {
  ...
  if (correct) {
    return 1;
  }
  else {
    return 0;
  }
}

The registered constraints can be used in the rules.

# Validation of multiple valuesRules for doing
my $rule = $vc->create_rule;
$rule->require('admin_email')->check('email');
my $data = {admin_email =>'foo@my.com'};

Register constraint function

Validator::Custom makes it easy to register constraint functions for validation. Use the register_constraint method to register the constraint function.

$vc->register_constraint(
  tel_num => sub {
    my $value = shift;
    $value =~ /^[\d-]+$/? 1: 0;
  }
);

Returns 1 if the value is correct and 0 if the value is incorrect. Note that you should not return an array reference as a true value. This is because array reference are used when treating constraint functions as filters.

The constraint function registered in this way can be used in the rule.

$rule->require('tel')->check('tel_num');

Multiple constraint functions can be registered at the same time.

$vc->register_constraint(
  tel_num => sub {
     my $value = shift;
     $value =~ /^[\d-]+$/? 1: 0;
  },
  hiragana => sub {...}
);

Item does not have to exist require => 0/Validator::Custom Reference

If the item may or may not exist , use the optional method instead of the require method.

my $rule = $vc->create_rule;
$rule->optional('name')->check('int');

The above rule states that name may or may not exist, and if it does, it must be an int.

At least one item contains a value

You may want to enter multiple text boxes and check that at least one of them contains a value. In such a case, a little ingenuity is required. It's a good idea to merge the values in the textbox and then check that it's not empty.

# At least one item contains a value
my $vc = Validator::Custom->new;
$data = {name1 =>'Ken', name2 =>'', name3 =>'Taro'};
$rule = [
  {key => qr/^name\d+$/} => [
    'merge',
    'trim',
    'not_blank'
  ],,
];;
my $result = $vc->validate($data, $rule);

and rules using conditions

This page is a document about Version 0.xx. The latest version of the documentation is here.

When performing validation, you may want to state whether multiple conditions are met. For example, when you want to write a condition that is greater than 1000 and less than 2000.

Let's create a rule using the and condition. Just call the check method multiple times. Here we use the constraints greater_than and less_than. You can also pass arguments by specifying constraints in the hash reference.

# data
my $data = {price => 1200};

# Rules using and conditions
my $rule = $vc->create_rule;
$rule->require('price')
  ->check({greater_than => 1000})
  ->check({less_than => 2000});

or rules using conditions

When performing validation, you may want to state whether one condition is met. For example, you may want to write a condition that is blank or an integer.

Let's create a rule using the or condition. Use the check_or method to describe the or condition.

# data
my $data = {price => 1200};

# or rules using conditions
my $rule = $vc->create_rule;
$rule->require('price')->check_or('blank', 'int');

and use condition and or condition at the same time

You can also use the and condition and the or condition at the same time.

$rule->require('price')
  ->check_or('blank', 'int')
  ->check({greater_than => 1000});

Specifying arguments in constraints

Some of the constraints provided by default can take arguments. equal_to , between , etc.

To pass an argument, specify the constraint name part using a hash reference as follows.

{Constraint name => Arguments}

Here is an example of equal_to and between :

my $rule = $vc->create_rule;
$rule->require('price')->check({'equal_to' => 1000});
$rule->require('age')->check({between => [1, 20]});
my $data = {price => 1000, age => 19};

The argument can be a string, a number, an array reference, or a hash reference, as long as it is a scalar value.

to_array (filter) - convert array to reference

If you want to convert the value to an array reference, use the to_array filter.

# data
my $data = {languages =>'Japanese'};

# rule
my $rule = $vc->create_rule;
$rule->require('languages')->filter('to_array');

my $vresult = $vc->validate($data, $rule);
print $vresult->data->{languages}; # ['Japanese']

to_array converts data that is not an array reference to an array reference. If it was originally an array reference, it does nothing.

This is useful for converting to an array reference when you don't know if one value will come or multiple values will come, such as checkboxes.

in_array (constraint function) - Check if the value is contained in the array value

When checking an HTML form, you may not want to allow values other than a certain value. In such cases, use the in_array constraint function.

# data
my $data = {food =>'sushi'};

# rule
my $rule = $rule->create_rule;
$rule->require('food')->check({'in_array' => [qw/sushi bread apple /]});

The argument of the in_array constraint function specifies an array reference that contains the allowed values.

{'in_array' => [qw/sushi bread apple /]}

Apply to multiple values such as checkboxes

There are multiple check box values. If you want all of the multiple values to be included in a certain value, write as follows.

# Multiple values
my $data = {food => ['sushi', 'cake']};

# rule
my $rule = $vc->create_rule;
$rule->require('food')
  ->each(1)->check({'in_array' => [qw/sushi bread apple /]);

my $is_valid = $vc->validate($data, $rule);

By using the each method, you can check each value of the element.

It's a little confusing, but it's useful to remember.

Application

For example, a rule that at least one is checked and all its values are 001 or 002 is applied as follows:

# rule
$rule->require('food')
  ->filter('to_array')
  ->check('selected_at_least')
  ->each(1)
  ->check({'in_array' => [qw/001 002 /]});

Validator::Custom makes it easy to validate HTML forms.

selected_at_least (constraint function) - at least one is selected

In an HTML form, you may want to find out if at least one of the checkboxes is selected. In such cases, use the selected_at_least constraint function.

# data
my $data = {hobby => ['music', 'movie']};

# rule
my $rule = $vc->create_rule;
$rule->require('hobby')->check({selected_at_least => 1});

The selected_at_least constraint function can specify at least how many must be selected in the argument. In this example, 1 is specified, which means at least one.

Use the constraint function registered in the constraint function

When writing constraint functions for validation with Validator::Custom, you may want to use low-level constraint functions.

Write as follows.

use Validator::Custom;
my $vc = Validator::Custom->new;

$vc->register_constraint(
  int_plus_alpha => sub {
    my ($value, $args, $vc) = @_;
    
    my $is_int = $vc->constraints->{'int'}->($value);
    
    my $is_valid = $is_int && $value < 1000;
    
    return $is_valid;
  }
);

The point of the constraint function is that the Validator::Custom object is passed as the third argument.

The constraints attribute returns a hash reference that includes the constraint function, so you can use the already registered constraint function as follows.

my $is_int = $vc->constraints->{'int'}->($value);

uint(constraint function) - Non - negative integer

You may want to allow only non-negative integers in your HTML form. In such cases, use the uint constraint function.

# data
my $data = {age => 19};

# rule
my $rule = $vc->create_rule;
$rule->require('age')->check('uint');

my $is_valid = $vc->validate($data, $rule);

Internally, the regular expression "^[0-9]+$" is used.

duplication (constraint function) - Check that email addresses match

In the HTML form, you may want to have two passwords entered and check that the passwords are the same. In such cases, use the duplication constraint function.

# data
my $data = {mail1 =>'a@somehost.com', mail2 =>'a@somehost.com'};

# rule
my $rule = $vc->create_rule;
$rule->require(['mail1', 'mail2'])->name('mail_check')
  ->check('duplication');

Note that validation will fail if neither of the two values is undefined.

length(constraint function) - Check string length

You may want to check the length of a string in an HTML form. In such cases, use the length constraint function.

# data
my $data = {value1 =>'aaa', value2 =>'bbbbb'};

# rule
my $rule = $vc->create_rule;
# Length is 3
$rule->require('value1')->check({'length' => 3});
# Length 2 or more and 5 or less
$rule->require('value2')->check({'length' => [2, 5]});
# Length 2 or more
$rule->require('value3')->check({'length' => {min => 2, max => 5}});
# Length 2 or more
$rule->require('value4')->check({'length' => {min => 2, max => 5}});
# Length is 5 or less
$rule->require('value4')->check({'length' => {max => 5}});

You can check the length. If the string is an decoded string, you can check the length of the string. If the string is a byte string, check the number of bytes.

defined(constraint function) - defined

Use the defined constraint function to specify that it is defined .

my $data => {name =>'Ken'};
my $rule = $vc->create_rule;
$rule->require('name')->check('defined');

In the case of HTML form, you can use not_blank instead of define because you only need to be able to check if it is an empty string.

decimal (constraint function) - Positive number (specify the number of digits)

This page is a document about Version 0.xx. The latest version of the documentation is here.

Use the decimal constraint function to specify that it is a number . Numerical numbers include positive integers and decimals. Please note that it does not include negative numbers. You can specify the maximum number of digits before the decimal point and the maximum number of digits after the decimal point with the argument.

my $data = {num1 => '123', num2 => '1.45'};
my $rule = $vc->create_rule;
$rule->require('num1')->check({'decimal' => 3});
$rule->require('num2')->check({'decimal' => [1, 2]});

blank (constraint function) - empty string

Use the blank constraint function to specify that it is a empty string .

my $data = {name =>''};
my $rule = $vc->create_rule;
$rule->require('name')->check('blank');

I don't think there is any particular opportunity to use it in HTML form validation.

between (constraint function) - a number between A and B

Use the between constraint function to specify that it is a number between A and B . Note that it includes A and B at both ends.

my $data = {age => 19};
my $rule = $vc->create_rule;
$rule->require('age')->check({between => [1, 20]});

It does not consider whether between is an integer. If you want to apply an integer constraint, please also use the int constraint function.

ascii (constraint function) - ASCII graphic characters

You may want to allow only ASCII print characters (hexadecimal numbers 21-7E), such as HTML form passwords. In such cases, use the ascii constraint function.

my $data = {password =>'ajf & $# -'};
my $rule = $vc->create_rule;
$rule->require('password')->check('ascii');

Since it is a range of graphic characters, not the entire ASCII code, validation will fail if tabs, spaces, etc. are included.

duplication (constraint function) - Check that two values are the same

If you want to check that two values match , use the C constraint function. Validation will always fail if either value is undefined.

Multiple values

my $data = {password1 =>'secret', password2 =>'secret'};
my $rule = $vc->create_rule;
$rule->require(['passwrod1', 'password2'])->name('password_check')
  ->check('duplication');

If you want to check multiple values, you can pass an array reference to the require method. In this case, add the name method to the key value.

Actually check the password

When actually checking the password, also check that the password is not empty and that the password consists only of ASCII graphic characters. Also, regarding the restriction that the two passwords match, specify 0 for the copy option because the value corresponding to the identification key is not required for the validated secure data.

The rules are as follows.

$rule->require('password')
  ->check('not_blank')->message('password is empty')
  ->check('ascii')->message('password contains invalid character');
$rule->require(['password1', 'password2'])->name('password_check')
  ->check('duplication')->message('Two password is not matched')

regex (constraint function) - matches regular expression

In a HTML form , use the regex constraint function if you want to check that it matches a regular expression .

# data
my $data = {num => '123'};

# rule
my $rule = $vc->create_rule;
$rule->require('num')->check({'regex' => qr/\d{0,3} /});

not_space (constraint function) - not whitespace

In a HTML form , use the not_space constraint function if you want to check that it is not whitespace . A space character is a string that consists only of a space character, a tab character, and a line break character. This includes cases where the string does not exist. It does not include whitespace in Unicode.

# data
my $data = {name =>'Ken'};

# rule
my $rule = $vc->create_rule;
$rule->require('name')->check('not_space');

not_defined(constraint function) - value not defined

In a HTML form , use the not_defined constraint function if you want to check that the value is undefined .

# data
my $data = {name =>'Ken'};

# rule
my $rule = $vc->create_rule;
$rule->require('name')->check('not_defined');

less_than (constraint function) - a number is less than a certain number

In a HTML form , use the less_than constraint function if you want to check that a number is less than a certain number .

# data
my $data = {num => 20};

# rule
my $rule = $vc->create_rule;
$rule->require('num')->check({'less_than' => 25});

int(constraint function) - integer

In a HTML form , use the int constraint function if you want to check that it is a integer .

# data
my $data = {age => 19};

# rule
my $rule = $vc->create_rule;
$rule->require('age')->check('int');

http_url (constraint function) - HTTP or HTTPS URL

In a HTML form , use the http_url constraint function if you want to check that it is a HTTP or HTTPS URL .

# data
my $data = {url =>'http://somehost.com'};

# rule
my $rule = $vc->create_rule;
$rule->require('url')->check('http_url');

greater_than (constraint function) - greater than a certain number

In a HTML form , use the greater_than constraint function if you want to check that it is greater than a certain number .

# data
my $data = {price => 1000};

# rule
my $rule = $vc->create_rule;
$rule->require('price')->check({'greater_than' => 900});

equal_to (constraint function) - equal numbers

In a HTML form , use the equal_to constraint function if you want to check that numbers are equal .

# data
my $data = {price => 1000};

# rule
my $rule = $vc->create_rule;
$rule->require('price')->check({'equal_to' => 1000});

Related Informatrion