> Hi, I'm looking for a ActiveX component that can validate South-African
credit card numbers (Visa/ MasterCard) eg check if credit card number is
valid. Where can i find such a component? Using Delphi 6.
> Regards Lennie
I would be surprised if South-African credit cards numbers would be
different
from any others. Here is a unit that came through one of the Delphi lists
that is supposed to validate. I have not made use of this, so let us know
if this works for you.
Glenn Lawler
----------------------------------------------------------------
unit CreditCard;
interface
uses SysUtils, WinTypes, WinProcs, Classes;
function VerifyCard(CardNumber, CheckDigit: String; var MessageText:
string): Boolean;
implementation
const
CardPrefixes: array[ 1..19 ] of string =
( '2014', '2149', '300', '301', '302',
'303', '304', '305', '34', '36', '37',
'38', '4', '51', '52', '53', '54', '55', '6011' );
CardTypes: array[ 1..19 ] of String =
( 'enRoute',
'enRoute',
'Diners Club/Carte Blanche',
'Diners Club/Carte Blanche',
'Diners Club/Carte Blanche',
'Diners Club/Carte Blanche',
'Diners Club/Carte Blanche',
'Diners Club/Carte Blanche',
'American Express',
'Diners Club/Carte Blanche',
'American Express',
'Diners Club/Carte Blanche',
'Visa',
'MasterCard',
'MasterCard',
'MasterCard',
'MasterCard',
'MasterCard',
'Discover' );
function RemoveChar(const Input: String; DeletedChar: Char): String;
var
Index: Word; { counter variable
}
begin
{ all this function does is iterate through string looking for char, if
found }
{ it deletes it
}
Result := Input;
for Index := Length( Result ) downto 1 do
if Result[ Index ] = DeletedChar then Delete( Result, Index, 1 );
end;
function ShiftMask( Input: Integer ): Integer;
begin
{ simply a wrapper for this left bit shift operation
}
result := ( 1 shl ( Input - 12 ) );
end;
function ConfirmChecksum( CardNumber: String ): Boolean;
var
CheckSum: Integer; { Holds the value of the operation
}
Flag: Boolean; { used to indicate when ready
}
Counter: Integer; { index counter
}
PartNumber: String; { used to extract each digit of number
}
Number: Integer; { used to convert each digit to integer
}
begin
{*********************************************************************
*******
This is probably the most confusing part of the code you will see, I
know
that it is some of the most confusing I have ever seen. Basically, this
function is extracting each digit of the number and subjecting it to the
checksum formula established by the credit card companies. It works
from
the end to the front.
**********************************************************************
******}
{ get the starting value for our counter }
Counter := Length( CardNumber );
CheckSum := 0;
PartNumber := '';
Number := 0;
Flag := false;
while ( Counter >= 1 ) do
begin
{ get the current digit }
PartNumber := Copy( CardNumber, Counter, 1 );
Number := StrToInt( PartNumber ); { convert to integer }
if ( Flag ) then { only do every other digit }
begin
Number := Number * 2;
if ( Number >= 10 ) then Number := Number - 9;
end;
CheckSum := CheckSum + Number;
Flag := not( Flag );
Counter := Counter - 1;
end;
result := ( ( CheckSum mod 10 ) = 0 );
end;
function GetMask( CardName: String ): Integer;
begin
{ the default case }
result := 0;
if ( CardName = 'MasterCard' ) then result := ShiftMask( 16 );
if ( CardName = 'Visa' ) then result := ( ShiftMask( 13 ) or ShiftMask(
16 ) );
if ( CardName = 'American Express' ) then result := ShiftMask( 15 );
if ( CardName = 'Diners Club/Carte Blanch' ) then result := ShiftMask(
14 );
if ( CardName = 'Discover' ) then result := ShiftMask( 16 );
end;
function VerifyCard( CardNumber, CheckDigit: String; var MessageText:
String ): Boolean;
var
StrippedNumber: String; { used to hold the number bereft of extra
chars }
Index: Integer; { general purpose counter for loops, etc
}
TheMask: Integer; { number we will use for the mask
}
FoundIt: Boolean; { used to indicate when something is
found }
CardName: String; { stores the name of the type of card
}
PerformChecksum: Boolean; { the enRoute type of card doesn't get it
}
begin
{ first, get rid of spaces, dashes }
StrippedNumber := RemoveChar( CardNumber, ' ' );
StrippedNumber := RemoveChar( StrippedNumber, '-' );
CheckDigit := Trim(CheckDigit);
{ if the string was zero length, then FALSE! }
if ( StrippedNumber = '' ) or (CheckDigit = '') then
begin
result := false;
exit;
end;
If StrippedNumber[1] <> CheckDigit[1] then
begin
result := false;
exit;
end;
{ initialize return variables }
MessageText := '';
result := true;
{ set our flag variable }
FoundIt := false;
{ check for invalid characters right off the bat }
for Index := 1 to Length( StrippedNumber ) do
begin
case StrippedNumber[ Index ] of
'0'..'9': FoundIt := FoundIt; { non op in other words }
else
MessageText := 'Invalid Credit Card Number';
result := false;
exit;
end;
end;
{ now let's determine what type of card it is }
for Index := 1 to 19 do
begin
if ( Pos( CardPrefixes[ Index ], StrippedNumber ) = 1 ) then
begin
{ we've found the right one }
FoundIt := true;
CardName := CardTypes[ Index ];
TheMask := GetMask( CardName );
end;
end;
{ if we didn't find it, indicates things are already awry }
if ( not FoundIt ) then
begin
CardName := 'Unknown Card';
TheMask := 0;
MessageText := 'Unknown Card';
result := false;
exit;
end;
{ check the length }
if ( ( Length( StrippedNumber ) > 28 ) and result ) then
begin
MessageText := 'Invalid Card Length';
result := false;
exit;
end;
{ check the length }
if ( ( Length( StrippedNumber ) < 12 ) or ( ( ShiftMask( Length(
StrippedNumber ) ) and TheMask ) = 0 ) ) then
begin
MessageText := 'Invalid Card Length';
result := false;
exit;
end;
{ check the checksum computation }
if ( CardName = 'enRoute' ) then
PerformChecksum := false
else
PerformChecksum := true;
if ( PerformChecksum and ( not ConfirmChecksum( StrippedNumber ) ) )
then
begin
MessageText := 'Invalid Card Number';
result := false;
exit;
end;
{ if result is still true, then everything is OK }
if ( result ) then
MessageText := CardName;
{ if the string was zero length, then OK too }
if ( StrippedNumber = '' ) then
result := true;
end;
begin
end.
-----------------------------------------------------
Home page: http://groups.yahoo.com/group/delphi-en/
To unsubscribe: [EMAIL PROTECTED]
Yahoo! Groups Links
<*> To visit your group on the web, go to:
http://groups.yahoo.com/group/delphi-en/
<*> To unsubscribe from this group, send an email to:
[EMAIL PROTECTED]
<*> Your use of Yahoo! Groups is subject to:
http://docs.yahoo.com/info/terms/