package Business::CardInfo; use Moose; use Moose::Util::TypeConstraints; our $VERSION = '0.02'; subtype 'CardNumber' => as 'Int' => where { validate($_) }; coerce 'CardNumber' => from 'Str' => via { my $cc = shift; $cc =~ s/\s//g; return $cc; }; no Moose::Util::TypeConstraints; has 'country' => ( isa => 'Str', is => 'rw', default => 'UK' ); has 'number' => ( isa => 'CardNumber', is => 'rw', required => 1, coerce => 1, trigger => sub { shift->clear_type } ); has 'type' => ( isa => 'Str', is => 'rw', lazy_build => 1, ); sub _build_type { my $self = shift; my $number = $self->number; #my @grp = (substr($number,0,1), substr($number,0,4),substr($number,0,6)); return "Visa Electron" if $self->_search([qw/417500 4917 4913 4508 4844/]); return "Visa" if $self->_search([qw/4/]); return "MasterCard" if $self->_search([51 .. 55]); if($self->country eq 'UK') { return "Diners Club" if $self->_search([36]); return "MasterCard" if $self->_search([54,55]); } return "Maestro" if $self->_search([qw/5020 5038 6304 6759 6761 4903 4905 4911 4936 564182 633110 6333 5033 5868/]); return "Solo" if $self->_search([qw/6334 6767/]); return "AMEX" if $self->_search([qw/34 37/]);; return "Diners Club" if $self->_search([300 .. 305,2014,2149,46,55]); return "Discover" if $self->_search([6011,65]); return "JCB" if $self->_search([qw/1800 2131 35/]); return "Unknown"; } sub _search { my ($self,$arr) = @_; foreach(@{$arr}) { return 1 if $self->number =~ /^$_/; } return 0; } sub validate { my $number = shift; my $num_length = length($number); return unless $num_length > 12; my ($i, $sum, $weight); for ($i = 0; $i < $num_length - 1; $i++) { $weight = substr($number, -1 * ($i + 2), 1) * (2 - ($i % 2)); $sum += (($weight < 10) ? $weight : ($weight - 9)); } return substr($number, -1) == (10 - $sum % 10) % 10 ? 1 : 0; } =head1 NAME Business::CardInfo - Get/Validate data from credit & debit cards =head1 SYNOPSIS use Business::CardInfo; my $card_info = Business::CardInfo->new(number => '4917 3000 0000 0008'); print $card_info->type, "\n"; # prints Visa Electron $card_info->number('5404 0000 0000 0001'); print $card_info->type, "\n"; # prints MasterCard =head1 DESCRIPTION =head1 ATTRIBUTES =head2 country =head2 number =head2 type Possible return values are: Visa Electron Visa MasterCard Diners Club Maestro Solo AMEX Discover JCB Unknown =head1 METHODS =head2 validate =head1 BUGS Please report any bugs or feature requests to C, or through the web interface at L. I will be notified, and then you'll automatically be notified of progress on your bug as I make changes. =head1 SUPPORT You can find documentation for this module with the perldoc command. perldoc Business::CardInfo You can also look for information at: =over 4 =item * RT: CPAN's request tracker L =item * AnnoCPAN: Annotated CPAN documentation L =item * CPAN Ratings L =item * Search CPAN L =back =head1 AUTHORS purge: Simon Elliott wreis: Wallace Reis =head1 ACKNOWLEDGEMENTS To Airspace Software Ltd , for the sponsorship. =head1 LICENSE This library is free software under the same license as perl itself. =cut 1;