@ISA = qw(Exporter AutoLoader Business::OnlinePayment);
@EXPORT = qw();
@EXPORT_OK = qw();
-$VERSION = '0.01';
+$VERSION = '0.02';
$DEBUG ||= 0;
$self->build_subs(qw( authorization_source_code returned_ACI
transaction_sequence_num transaction_identifier
- validation_code ));
+ validation_code local_transaction_date
+ local_transaction_time AVS_result_code ));
}
sub revmap_fields {
my %content = $self->content;
my $action = lc($content{'action'});
- #die 'eSec only supports "Authorization Only" transactions'
- # unless $action eq 'authorization only';
-
- #my %typemap = (
- # "VISA card" => 'visa',
- # "MasterCard" => 'mastercard',
- # "Discover card" => 'discover', #not supported...
- # "American Express card" => 'amex',
- # "Diner's Club/Carte Blanche" => 'dinersclub',
- # "enRoute" => 'enroute', #not supported...
- # "JCB" => 'jcb',
- # "BankCard" => 'bankcard',
- #);
- #my $cardtype = $self->test_transaction
- # ? 'testcard'
- # : $typemap{cardtype($content{'card_number'})};
-
- #? what's supported
- if ( $self->transaction_type() =~
+
+ #? what's supported
+ if ( $self->transaction_type() =~
/^(cc|visa|mastercard|american express|discover)$/i ) {
$self->required_fields(qw/type action amount card_number expiration/);
} else {
if ( $page =~ /^(\d+)\s+\-\s+(\S.*)$/ ) {
die "VirtualNet protocol error: $page";
- #$self->is_success(0);
- #$self->result_code($1);
- #$self->error_message($2);
- #$self->error_message($page);
- } else {
- warn "protocol sucessful, decoding VisaNet-II response\n" if $DEBUG;
-
- isEvenParity($page) or die "VisaNet-II response not even parity";
-
- $page =~ s/(.)/pack('C', unpack('C',$1) & 0x7f)/ge; #drop parity bits
-
- #warn $page;
+ }
- my %response;
- if ( $action eq 'authorization only' ) {
- %response = $self->eis1080_response( $page );
- } elsif ( $action eq 'post authorization' ) {
- %response = $self->eis1081_response( $page );
- #} elsif ( $action eq 'normal authorization' ) {
- # croak 'Normal Authorization not supported';
- #} elsif ( $action eq 'credit' ) {
- # croak 'Credit not (yet) supported';
- }
+ warn "protocol sucessful, decoding VisaNet-II response\n" if $DEBUG;
-# $self->is_success($response{is_success});
-# $self->result_code($response{result_code});
-# $self->error_message($response{error_message});
-# $self->authorization($response{authorization});
+ isEvenParity($page) or die "VisaNet-II response not even parity";
+ $page =~ s/(.)/pack('C', unpack('C',$1) & 0x7f)/ge; #drop parity bits
- for my $field ( qw( is_success result_code error_message authorization
- authorization_source_code returned_ACI
- transaction_identifier validation_code
- transaction_sequence_num ) ) {
- $self->$field($response{$field});
- }
+ my %response;
+ if ( $action eq 'authorization only' ) {
+ %response = $self->eis1080_response( $page );
+ } elsif ( $action eq 'post authorization' ) {
+ %response = $self->eis1081_response( $page );
+ #} elsif ( $action eq 'normal authorization' ) {
+ # croak 'Normal Authorization not supported';
+ #} elsif ( $action eq 'credit' ) {
+ # croak 'Credit not (yet) supported';
+ }
+ for my $field ( qw( is_success result_code error_message authorization
+ authorization_source_code returned_ACI
+ transaction_identifier validation_code
+ transaction_sequence_num local_transaction_date
+ local_transaction_time AVS_result_code ) ) {
+ $self->$field($response{$field});
}
}
$content .= $self->merchant_id; # 10-21 12 Merchant Number
$content .= $self->store; # 22-25 4 Store Number
$content .= $self->terminal; # 26-29 4 Terminal Number
- $content .= 'C'; # 30 1 Device Code: C="P.C."
+ $content .= 'Q'; # 30 1 Device Code:
+ # Q="Third party software developer"
+ #$content .= 'C'; # 30 1 Device Code: C="P.C."
#$content .= 'M'; # 30 1 Device Code: M="Main Frame"
$content .= $industry_code; # 31 1 Industry Code
$content .= '840'; # 32-34 3 Currency Code: 840=U.S. Dollars
# ***FIXME***
$content .= '705'; # 49-51 3 Time Zone Differential: 705=EST
$content .= $self->mcc; # 52-55 4 Metchant Category Code: 5999
- $content .= 'N'; # 56 1 Requested ACI (Authorization
+ $content .= 'Y'; # 56 1 Requested ACI (Authorization
# Characteristics Indicator):
- # N=Device is not CPS capable
+ # Y=Device is CPS capable
$content .= $seq; # 57-60 4 Tran Sequence Number
$content .= '56'; # 61-62 2 Auth Transaction Code:
# 56=Card Not Present
my( $self, $response) = @_;
my %response;
- $response =~ /^$STX(.{67})([\w ]{0,15})$FS([\w ]{0,4})$FS.*$ETX(.)$/
+ #$response =~ /^$STX(.{67})([\w ]{0,15})$FS([\w ]{0,4})$FS.*$ETX(.)$/
+ $response =~ /^$STX(.{67})([\w ]{0,15})$FS([\w ]{0,4})$FS(\d{3})$ETX(.)$/
or die "can't decode (eis1080) response: $response\n". join(' ', map { sprintf("%x", unpack('C',$_)) } split('', $response) );
( $response{transaction_identifier},
$response{validation_code},
+ my $group3version,
my $lrc
- ) = ($2, $3, $4);
+ ) = ($2, $3, $4, $5);
+
+ die "group iii version $group3version ne 014"
+ unless $group3version eq '014';
warn "$response\n".
join(' ', map { sprintf("%x", unpack('C',$_)) } split('', $response) ).
$response{result_code} = $response{response_code};
$response{error_message} = $response{auth_response_text};
$response{authorization} = $response{approval_code};
- #$response{returned_ACI} = $response{returned_ACI};
- #$response{authorization_source_code} = $response{authorization_source_code};
- #$response{transaction_sequence_num} = $response{transaction_sequence_num};
%response;
}
# 28-39 12 NUM Merchant Number (4.121)
$header .= $self->store; # 40-43 4 NUM Store Number (4.187)
$header .= $self->terminal; # 44-47 4 NUM Terminal Number 9911 (4.195)
- $header .= 'C'; # 48 1 A/N Device Code: C="P.C." (4.62)
+ $header .= 'Q'; # 48 1 A/N Device Code:
+ # Q="Third party software developer" (4.62)
+ #$header .= 'C'; # 48 1 A/N Device Code: C="P.C." (4.62)
#$header .= 'M'; # 48 1 A/N Device Code M="Main Frame" (4.62)
$header .= $industry_code; # 49 1 A/N Industry Code (4.94)
$header .= '840'; # 50-52 3 NUM Currency Code (4.52)
#14-35 22 A/N Cardholder Account Number Left-Justified/Space-Filled 4.30
$detail .= substr( $param->{card_number}.' ', 0, 22 );
- $detail .= 'N'; # 36 1 Requested ACI (Authorization
+ $detail .= 'Y'; # 36 1 Requested ACI (Authorization
# Characteristics Indicator):
# N (4.163)
# 37 1 A/N Returned ACI (4.168)
- $detail .= $param->{returned_ACI} || 'N';
+ $detail .= $param->{returned_ACI} || ' ';
# *** 38 1 A/N Authorization Source Code (4.13)
$detail .= $param->{authorization_source_code} || '6';
# 45-50 6 A/N Authorization Code Left-Justified/Space-Filled (4.12)
$detail .= $param->{authorization};
- my $time = time;
-
- my $mmdd = substr(time2str('0%m%d',$time),-4);
- $detail .= $mmdd; # 51-54 4 NUM Local Transaction Date MMDD (4.113)
-
- my $hhmmss = time2str('%H%M%S',$time);
- $detail .= $hhmmss; # 55-60 6 NUM Local Transaction Time HHMMSS (4.114)
+ # 51-54 4 NUM Local Transaction Date MMDD (4.113)
+ die "missing local_transaction_date"
+ unless $param->{local_transaction_date};
+ $detail .= substr($param->{local_transaction_date}, 0, 4);
+
+ # 55-60 6 NUM Local Transaction Time HHMMSS (4.114)
+ die "missing local_transaction_time"
+ unless $param->{local_transaction_time};
+ #die "length of local_transaction_time ". $param->{local_transaction_time}.
+ # " != 6"
+ # unless length($param->{local_transaction_time}) == 6;
+ $detail .= $param->{local_transaction_time};
- $detail .= '0'; #***FIXME (from auth) 61 1 A/N AVS Result Code 4.3
+ #(from auth) 61 1 A/N AVS Result Code 4.3
+ die "missing AVS_result_code"
+ unless $param->{AVS_result_code};
+ $detail .= $param->{AVS_result_code};
# 62-76 15 A/N Transaction Identifier Left-Justified/Space-Filled 4.206
- $detail .= substr($param->{transaction_identifier}. (' 'x15), 0, 15);
+ my $transaction_identifier =
+ length($param->{transaction_identifier})
+ ? substr($param->{transaction_identifier}. (' 'x15), 0, 15)
+ : '000000000000000';
+ $detail .= $transaction_identifier;
# 77-80 4 A/N Validation Code 4.218
$detail .= substr($param->{validation_code}.' ', 0, 4);
transaction_identifier => $tx->transaction_identifier,
validation_code => $tx->validation_code,
transaction_sequence_num => $tx->transaction_sequence_num,
- #description => 'Business::OnlinePayment::BankOfAmerica visa test',
+ local_transaction_date => $tx->local_transaction_date,
+ local_transaction_time => $tx->local_transaction_time,
+ AVS_result_code => $tx->AVS_result_code,
+ #description => 'Business::OnlinePayment::VirtualNet test',
action => 'Post Authorization',
# order_number => $ordernum,
# amount => '0.01',
# authorization => $auth,
- # description => 'Business::OnlinePayment::BankOfAmerica visa test',
+ # description => 'Business::OnlinePayment::VirtualNet test',
);
$capture->submit();
=head1 COMPATIBILITY
-This module implements the interface documented at
+This module implements the interface that used to be documented at
http://www.vitalps.com/sections/int/int_Interfacespecs.html
-Specifically, start with
+Specifically, start with the "VirtualNet Specification"
+(available at http://www.420.am/~ivan/VirtualNet_Specification_0011.pdf)
+
+Then EIS 1080 (the 6.4.1 version does not appear to be available, but 6.3
+is available at http://www.420.am/~ivan/Final_EIS_1080_v6_3.pdf)
+
+Then EIS 1081 (available at http://www.420.am/~ivan/EIS_1081_v_6_4.pdf).
+
+EIS 1051 and 1052 are probably not necessary, and do not seem to be
+avilable.
+
+Old URLs:
http://www.vitalps.com/pdfs_specs/VirtualNet%020Specification%0200011.pdf
-and then http://www.vitalps.com/pdfs_specs/EIS%0201080%020v6_4_1.pdf and
+http://www.vitalps.com/pdfs_specs/EIS%0201080%020v6_4_1.pdf and
http://www.vitalps.com/pdfs_specs/EIS_1081_v_6_4.pdf and maybe even
http://www.vitalps.com/pdfs_specs/EIS%0201051.pdf and
http://www.vitalps.com/pdfs_specs/EIS%0201052.pdf