package HTML::FormHandler::Types; # ABSTRACT: Moose type constraints $HTML::FormHandler::Types::VERSION = '0.40068'; use strict; use warnings; use MooseX::Types -declare => [ 'PositiveNum', 'PositiveInt', 'NegativeNum', 'NegativeInt', 'SingleDigit', 'SimpleStr', 'NonEmptySimpleStr', 'Password', 'StrongPassword', 'NonEmptyStr', 'Email', 'State', 'Zip', 'IPAddress', 'NoSpaces', 'WordChars', 'NotAllDigits', 'Printable', 'PrintableAndNewline', 'SingleWord', 'Collapse', 'Upper', 'Lower', 'Trim', ]; our $class_messages = { PositiveNum => "Must be a positive number", PositiveInt => "Must be a positive integer", NegativeNum => "Must be a negative number", NegativeInt => "Must be a negative integer", SingleDigit => "Must be a single digit", SimpleStr => 'Must be a single line of no more than 255 chars', NonEmptySimpleStr => "Must be a non-empty single line of no more than 255 chars", Password => "Must be between 4 and 255 chars", StrongPassword =>"Must be between 8 and 255 chars, and contain a non-alpha char", NonEmptyStr => "Must not be empty", State => "Not a valid state", Email => "Email is not valid", Zip => "Zip is not valid", IPAddress => "Not a valid IP address", NoSpaces =>'Must not contain spaces', WordChars => 'Must be made up of letters, digits, and underscores', NotAllDigits => 'Must not be all digits', Printable => 'Field contains non-printable characters', PrintableAndNewline => 'Field contains non-printable characters', SingleWord => 'Field must contain a single word', }; use MooseX::Types::Moose ( 'Str', 'Num', 'Int' ); subtype PositiveNum, as Num, where { $_ >= 0 }, message { "Must be a positive number" }; subtype PositiveInt, as Int, where { $_ >= 0 }, message { "Must be a positive integer" }; subtype NegativeNum, as Num, where { $_ <= 0 }, message { "Must be a negative number" }; subtype NegativeInt, as Int, where { $_ <= 0 }, message { "Must be a negative integer" }; subtype SingleDigit, as PositiveInt, where { $_ <= 9 }, message { "Must be a single digit" }; subtype SimpleStr, as Str, where { ( length($_) <= 255 ) && ( $_ !~ m/\n/ ) }, message { $class_messages->{SimpleStr} }; subtype NonEmptySimpleStr, as SimpleStr, where { length($_) > 0 }, message { $class_messages->{NonEmptySimpleStr} }; subtype Password, as NonEmptySimpleStr, where { length($_) >= 4 && length($_) <= 255 }, message { $class_messages->{Password} }; subtype StrongPassword, as Password, where { ( length($_) >= 8 ) && length($_) <= 255 && (m/[^a-zA-Z]/) }, message { $class_messages->{StrongPassword} }; subtype NonEmptyStr, as Str, where { length($_) > 0 }, message { $class_messages->{NonEmptyStr} }; subtype State, as Str, where { my $value = $_; my $state = <{State} }; subtype Email, as Str, where { my $value = shift; require Email::Valid; my $valid; return ( $valid = Email::Valid->address($value) ) && ( $valid eq $value ); }, message { $class_messages->{Email} }; subtype Zip, as Str, where { /^(\s*\d{5}(?:[-]\d{4})?\s*)$/ }, message { $class_messages->{Zip} }; subtype IPAddress, as Str, where { /^(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)$/ }, message { $class_messages->{IPAddress} }; subtype NoSpaces, as Str, where { ! /\s/ }, message { $class_messages->{NoSpaces} }; subtype WordChars, as Str, where { ! /\W/ }, message { $class_messages->{WordChars} }; subtype NotAllDigits, as Str, where { ! /^\d+$/ }, message { $class_messages->{NotAllDigits} }; subtype Printable, as Str, where { /^\p{IsPrint}*\z/ }, message { $class_messages->{Printable} }; subtype PrintableAndNewline, as Str, where { /^[\p{IsPrint}\n]*\z/ }, message { $class_messages->{PrintableAndNewline} }; subtype SingleWord, as Str, where { /^\w*\z/ }, message { $class_messages->{SingleWord} }; subtype Collapse, as Str, where{ ! /\s{2,}/ }; coerce Collapse, from Str, via { s/\s+/ /g; return $_; }; subtype Lower, as Str, where { ! /[[:upper:]]/ }; coerce Lower, from Str, via { lc }; subtype Upper, as Str, where { ! /[[:lower:]]/ }; coerce Upper, from Str, via { uc }; subtype Trim, as Str, where { ! /^\s+/ && ! /\s+$/ }; coerce Trim, from Str, via { s/^\s+// && s/\s+$//; return $_; }; 1; __END__ =pod =encoding UTF-8 =head1 NAME HTML::FormHandler::Types - Moose type constraints =head1 VERSION version 0.40068 =head1 SYNOPSIS These types are provided by MooseX::Types. These types must not be quoted when they are used: has 'posint' => ( is => 'rw', isa => PositiveInt); has_field 'email' => ( apply => [ Email ] ); Types declared using Moose::Util::TypeConstraints, on the other hand, must be quoted: has_field 'text_both' => ( apply => [ PositiveInt, 'GreaterThan10' ] ); To import these types into your forms, you must either specify (':all') or list the types you want to use: use HTML::FormHandler::Types (':all'); or: use HTML::FormHandler::Types ('Email', 'PositiveInt'); =head1 DESCRIPTION It would be possible to import the MooseX types (Common, etc), but for now we'll just re-implement them here in order to be able to change the messages and keep control of what types we provide. From MooseX::Types::Common: 'PositiveNum', 'PositiveInt', 'NegativeNum', 'NegativeInt', 'SingleDigit', 'SimpleStr', 'NonEmptySimpleStr', 'Password', 'StrongPassword', 'NonEmptyStr', =head1 Type Constraints These types check the value and issue an error message. =over =item Email Uses Email::Valid =item State Checks that the state is in a list of two uppercase letters. =item Zip =item IPAddress Must be a valid IPv4 address. =item NoSpaces No spaces in string allowed. =item WordChars Must be made up of letters, digits, and underscores. =item NotAllDigits Might be useful for passwords. =item Printable Must not contain non-printable characters. =item SingleWord Contains a single word. =back =head2 Type Coercions These types will transform the value without an error message; =over =item Collapse Replaces multiple spaces with a single space =item Upper Makes the string all upper case =item Lower Makes the string all lower case =item Trim Trims the string of starting and ending spaces =back =head1 AUTHOR FormHandler Contributors - see HTML::FormHandler =head1 COPYRIGHT AND LICENSE This software is copyright (c) 2017 by Gerda Shank. This is free software; you can redistribute it and/or modify it under the same terms as the Perl 5 programming language system itself. =cut