Business-OCV

 view release on metacpan or  search on metacpan

OCV.pm  view on Meta::CPAN

# VPPs, which in turn requires both a multiple-VPP license from Ingenico and
# multiple merchant IDs and/or terminal IDs from the bank). The client (us) 
# simply specifies which account to use and the server allocates the first 
# available VPP allocated to that account. It returns the MerchantID and
# TerminalID as part of the RESPONSE message, if the client is interested.
#
#  The account number 0 is the 'Default' account and cannot be removed.
# The Default account is for the OCV Server's internal use and must not be 
# used by clients. Note that the Default account must have a VPP assigned to 
# it (which is why you get 6 accounts when you purchase a 5 account license). 
# Further, when processing concurrent transactions, if an account is busy 
# you'll get a SERVER BUSY response so it pays to allocate as many VPPs to 
# an account as possible (and make sure to retry BUSY responses).
#
# OCV DEVELOPMENT SERVER BUGS
#
#  The OCV 'Development Server' supplied by Ingenico for testing and 
# development purposes has a few bugs which mean it's not an entirely
# reliable means of testing your code. As of v.1.15, it:
#  - often locks up and/or crashes with dud messages
#  - does not respond well to polled requests. It 'locks' the account after 

OCV.pm  view on Meta::CPAN

		minamount	=>    100,	# minimum accepted amount (cents)
		maxamount	=> 100000,	# maximum accepted amount (cents)

		# list of strings to censor from the debug log
		# - generally intended to filter 'dynamic' data (i.e. card numbers),
		#   but can be initialised with a static list of strings
		# - card numbers are added with each transaction in _transaction()
		debugfilter	=> [],

		# parameters for dealing with SERVER BUSY
		busywait		=> 6,	# average time between attempts t = (T/2,3T/2)
		busyattempts	=> 15,	# maximum number of attempts
	};

	# merge arguments
	while (my ($k, $v) = each %{$args})
	{
		$self->{$k} = $v;
	}

	bless ($self, $class);

OCV.pm  view on Meta::CPAN

	}

	return $m;
}

############################################
# The following are wrappers around _transaction, one for each "transaction"
# type. Note that due to the way the arguments are parsed, arguments listed 
# before the @_ can be overridden by the caller (@_); arguments listed after 
# @_ can't be overridden by the caller.
# - the 'nb' subroutines are 'non busy' (or 'non blocking', take your pick),
#   that is they'll simply return when SERVER BUSY responses are encountered
#   The non-'nb' subs will attempt to retry BUSY responses, up to a point.
# - all transactions need a unique Transaction Reference ID, except for status
# - note that new transaction references should be generated for each attempt, 
#   successful or not, busy or not.
sub nbpurchase
{
	my $self = shift;
	my $n = ref($self->{'txnref'}) eq 'CODE' ? &{$self->{'txnref'}} : 
		$self->{'txnref'}++;

	$self->_transaction(TT_TRANS_PURCHASE, TxnRef => $n, @_, AuthNum => '');
}

sub nbrefund

OCV.pm  view on Meta::CPAN

# _transaction will default to the last one.
{
	shift->_transaction(TT_TRANS_STATUS, 
		CardData => '', CardExpiry => '', Amount => '', AuthNum => '', 
		@_,
		PolledMode => POLL_BLOCK);
}

# the following set of subroutines will transparently retry the transaction
# in the face of SERVER BUSY responses (up to a limit)
sub _busy
{
	my ($s, $self, @a) = @_;
	my $m;
	my $n = $self->{'busyattempts'};	# maximum no. of attempts
	$m = $s->($self, @a);
	while ($m and $m->ResponseCode eq TRANS_BUSY and $n-- > 0)
	{
		select(undef, undef, undef, $self->{'busywait'} * (0.5 + rand));
		$m = $s->($self, @a);
	}

	return $m;
}

sub purchase   { _busy(\&nbpurchase,   @_) }
sub refund     { _busy(\&nbrefund,     @_) }
sub preauth    { _busy(\&nbpreauth,    @_) }
sub completion { _busy(\&nbcompletion, @_) }
sub status     { _busy(\&nbstatus,     @_) }


############################################
# now the 'miscellaneous' requests

sub statistics
# Server statistics
# - sends a Statistics request, receives one of two response
# Arguments:
#  Reset - set to 1 to reset statistics.

utilities/totals  view on Meta::CPAN

		warn "REQUEST found: " . (defined $txn{$txnref} ? 'yes' : 'no') . "\n"
			if $DEBUG > 2;

		# RESPONSE for completed transaction (e.g. from superfluous STATUS)
		next unless defined $txn{$txnref};

		# ok, extract the PURCHASE data (the amount) 
		my ($amt, $a) = @{$txn{$txnref}};

		# if the response is 'final', cross it off
		# - server may have been busy, one or more RESPONSEs should be
		#   forthcoming containing the final txn status
		$txn{$txnref} = undef unless $m->Retry;

		# extract the most-used fields once
		# - excuse the abbreviated variable names, I'm a lazy typist :-)
		my ($r, $d, $c) = ($m->Result, $m->SettleDate, $m->CardBin);

		warn "SettleDate = $d\n" if $DEBUG == 2;
		warn "SettleDate = $d, Result = $r, AccountNum = $a\n" if $DEBUG > 2;



( run in 0.669 second using v1.01-cache-2.11-cpan-87723dcf8b7 )