解析敏感数据会将星号放在错误的位置



字符串参数被传递给函数 - 以下是可能输入数据的各种样本 该函数以字符串形式接收此数据,而不是数组、json 或其他数据格式 该函数应分析字符串并屏蔽敏感数据。 敏感数据应用 Asterix (*( 字符屏蔽(替换(。 敏感数据包括以下字段,但应根据需要轻松地将新的敏感字段添加到函数中:

信用卡号

信用卡到期日

信用卡CVV价值

该函数以与提供的格式相同的格式返回分析的字符串,但敏感数据现在被屏蔽。

<?php
$testData1 = "[orderId] => 212939129
[orderNumber] => INV10001
[salesTax] => 1.00
[amount] => 21.00
[terminal] => 5
[currency] => 1
[type] => purchase
[avsStreet] => 123 Road
[avsZip] => A1A 2B2
[customerCode] => CST1001
[cardId] => 18951828182
[cardHolderName] => John Smith
[cardNumber] => 5454545454545454
[cardExpiry] => 1025
[cardCVV] => 100";
$testData2 = "Request=Credit Card.Auth Only&Version=4022&HD.Network_Status_Byte=*&HD.Application_ID=TZAHSK!&HD."
. "Terminal_ID=12991kakajsjas&HD.Device_Tag=000123&07."
. "POS_Entry_Capability=1&07.PIN_Entry_Capability=0&07.CAT_Indicator=0&07."
. "Terminal_Type=4&07.Account_Entry_Mode=1&07.Partial_Auth_Indicator=0&07.Account_Card_Number="
. "4242424242424242&07.Account_Expiry=1024&07.Transaction_Amount=142931&07."
. "Association_Token_Indicator=0&17.CVV=200&17.Street_Address=123 Road SW&17.Postal_Zip_Code=90210&17.Invoice_Number=INV19291";

$testData3 = '{
"MsgTypId": 111231232300,
"CardNumber": "4242424242424242",
"CardExp": 1024,
"CardCVV": 240,
"TransProcCd": "004800",
"TransAmt": "57608",
"MerSysTraceAudNbr": "456211",
"TransTs": "180603162242",
"AcqInstCtryCd": "840",
"FuncCd": "100",
"MsgRsnCd": "1900",
"MerCtgyCd": "5013",
"AprvCdLgth": "6",
"RtrvRefNbr": "1029301923091239",
}';
$testData4 = "<?xml version='1.0' encoding='UTF-8'?>
<Request>
<NewOrder>
<IndustryType>MO</IndustryType>
<MessageType>AC</MessageType>
<BIN>000001</BIN>
<MerchantID>209238</MerchantID>
<TerminalID>001</TerminalID>
<CardBrand>VI</CardBrand>
<CardDataNumber>5454545454545454</AccountNum>
<Exp>1026</Exp>
<CVVCVCSecurity>300</Exp>
<CurrencyCode>124</CurrencyCode>
<CurrencyExponent>2</CurrencyExponent>
<AVSzip>A2B3C3</AVSzip>
<AVSaddress1>2010 Road SW</AVSaddress1>
<AVScity>Calgary</AVScity>
<AVSstate>AB</AVSstate>
<AVSname>JOHN R SMITH</AVSname>
<OrderID>23123INV09123</OrderID>
<Amount>127790</Amount>
</NewOrder>
</Request>";
$parseNew = array("name", "amt", "amount"); //some optional fields to parse
//this function will take a provided string, $data, and replace all credit card information including 16-digit numbers, expiry dates and 3-digit CVV numbers.
//$parseNew is an optional field to parse other sensitive information that matches the type of information entered into $parseNew, such as the transaction amount.
//if the strings in $parseNew matches any field in the data given, then that data will be parsed as well
//assign each piece of given test data to a variable for each to be passed into helcimTest
function helcimTest($data, $parseNew) {
$lines = explode("n", $data); //split data by new lines into an array
if (count($lines) == 1) { //if there aren't any new lines, then periods are used
$lines = explode(".", $data); //different splits can also be added with another if, like a ,
//print_r($lines);
}
for ($currLine = 0; $currLine < count($lines); $currLine++) { //loop through the lines and check for credit card information keywords as well as if theres any matches in $parseNew
$nonos = array("cvv", "exp", "expiry", "expire", "CVV", "Exp"); //keywords of default fields to be parsed, credit card numbers need to be searched for differently
$nonos = array_merge($nonos, $parseNew); //take optional parse data types and add it to array of default credit card data types
//checking credit card number first
$cardPos = strpos($lines[$currLine], "card"); //find "card" as part of Card Number 
if ($cardPos === false) {
$cardPos = strpos($lines[$currLine], "Card");
}
if ($cardPos > 0) { //if "card" is in the line, we check if "number" is also
$numberPos = strpos($lines[$currLine], "Number");
if ($numberPos === false) {
$numberPos = strpos($lines[$currLine], "number");
}
if ($numberPos > 0) {
$matches = array();
preg_match_all('!d+!', $lines[$currLine], $matches); //grabs all numbers in the line and throws them in an array
$numberLength = 0;
$digits = $matches[0]; //unpack array inside matches array
for ($i = 0; $i < count($digits); $i++) {
if (strlen($digits[$i]) == 16) {
$theNumber = $digits[$i];
$numberLength = strlen($digits[$i]);
}
}
if ($numberLength == 16) { //when all of these things are true then this number is definitely a credit card number
$lines[$currLine] = str_replace($theNumber, "****************", $lines[$currLine]);
//print_r($lines);         
}
}
}
//credit card number check complete
//now to check for everythign else
for ($i = 0; $i < count($nonos); $i++) {
$currNono = $nonos[$i]; //current type of data we are looking to parse
if(strpos($lines[$currLine], $currNono) > 0){ //check to see if current parsing field exists on current line
preg_match_all("/d+.d+|d+|[A-Za-z]+/", $lines[$currLine], $matches);
$sensData = $matches[0]; //unpack array from wihtin another array
print_r($sensData);
for($f = 0; $f < count($sensData); $f++){ //if we find any fields we want to parse
if (strcmp($sensData[$f], $currNono) == true && $f+1 != count($sensData)){
$hash = str_repeat("*", strlen($sensData[$f+1]));
$lines[$currLine] = str_replace($sensData[$f+1], $hash, $lines[$currLine]);
}
}
}
}
}
print_r($lines);
}
echo "Data set 1:nn"; //print results
helcimTest($testData1, $parseNew);
echo "Data set 2:nn";
helcimTest($testData2, $parseNew);
echo "Data set 3:nn";
helcimTest($testData3, $parseNew);
echo "Data set 4:nn";
helcimTest($testData4, $parseNew);

输出是这样显示的,一些值被正确解析,而另一些则感觉完全随机。该函数的第一部分仅处理信用卡号,该信用卡号始终正确解析,当函数到达其下半部分时,与结果相比,我列出的模式没有任何意义:

Data set 1:
Array
(
[0] => amount
[1] => 21.00
)
Array
(
[0] => cardExpiry
[1] => 1025
)
Array
(
[0] => cardCVV
[1] => 100
)
Array
(
[0] => [orderId] => 212939129
[1] =>             [orderNumber] => INV10001
[2] =>             [salesTax] => 1.00
[3] =>             [amount] => 21.00
[4] =>             [terminal] => 5
[5] =>             [currency] => 1
[6] =>             [type] => purchase
[7] =>             [avsStreet] => 123 Road
[8] =>             [avsZip] => A1A 2B2
[9] =>             [customerCode] => CST1001
[10] =>             [cardId] => 18951828182
[11] =>             [cardHolderName] => John Smith
[12] =>             [cardNumber] => ****************
[13] =>             [cardExpiry] => ****
[14] =>             [cardCVV] => ***
)
Data set 2:
Array
(
[0] => Account
[1] => Expiry
[2] => 1024
[3] => 07
)
Array
(
[0] => Request=Credit Card
[1] => Auth Only&Version=4022&HD
[2] => Network_Status_Byte=*&HD
[3] => Application_ID=TZAHSK!&HD
[4] => Terminal_ID=12991kakajsjas&HD
[5] => Device_Tag=000123&07
[6] => POS_Entry_Capability=1&07
[7] => PIN_Entry_Capability=0&07
[8] => CAT_Indicator=0&07
[9] => Terminal_Type=4&07
[10] => Account_Entry_Mode=1&07
[11] => Partial_Auth_Indicator=0&07
[12] => Account_Card_Number=****************&07
[13] => Account_******=****&**
[14] => Transaction_Amount=142931&07
[15] => Association_Token_Indicator=0&17
[16] => CVV=200&17
[17] => Street_Address=123 Road SW&17
[18] => Postal_Zip_Code=90210&17
[19] => Invoice_Number=INV19291
)
Data set 3:
Array
(
[0] => CardExp
[1] => 1024
)
Array
(
[0] => CardCVV
[1] => 240
)
Array
(
[0] => {
[1] =>                 "MsgTypId": 111231232300,
[2] =>                 "CardNumber": "****************",
[3] =>                 "CardExp": ****,
[4] =>                 "CardCVV": ***,
[5] =>                 "TransProcCd": "004800",
[6] =>                 "TransAmt": "57608",
[7] =>                 "MerSysTraceAudNbr": "456211",
[8] =>                 "TransTs": "180603162242",
[9] =>                 "AcqInstCtryCd": "840",
[10] =>                 "FuncCd": "100",
[11] =>                 "MsgRsnCd": "1900",
[12] =>                 "MerCtgyCd": "5013",
[13] =>                 "AprvCdLgth": "6",
[14] =>                 "RtrvRefNbr": "1029301923091239",
[15] =>             }
)
Data set 4:
Array
(
[0] => Exp
[1] => 1026
[2] => Exp
)
Array
(
[0] => CVVCVCSecurity
[1] => 300
[2] => Exp
)
Array
(
[0] => CurrencyExponent
[1] => 2
[2] => CurrencyExponent
)
Array
(
[0] => AVSname
[1] => JOHN
[2] => R
[3] => SMITH
[4] => AVSname
)
Array
(
[0] => <?xml version='1.0' encoding='UTF-8'?>
[1] =>                     <Request>
[2] =>                             <NewOrder>
[3] =>                                     <IndustryType>MO</IndustryType>
[4] =>                                     <MessageType>AC</MessageType>
[5] =>                                     <BIN>000001</BIN>
[6] =>                                     <MerchantID>209238</MerchantID>
[7] =>                                     <TerminalID>001</TerminalID>
[8] =>                                     <CardBrand>VI</CardBrand>
[9] =>                                     <CardDataNumber>****************</AccountNum>
[10] =>                                     <***>1026</***>
[11] =>                                     <CVVCVCSecurity>***</***>
[12] =>                                     <CurrencyCode>124</CurrencyCode>
[13] =>                                     <****************>*</****************>
[14] =>                                     <AVSzip>A2B3C3</AVSzip>
[15] =>                                     <AVSaddress1>2010 Road SW</AVSaddress1>
[16] =>                                     <AVScity>Calgary</AVScity>
[17] =>                                     <AVSstate>AB</AVSstate>
[18] =>                                     <*******>**** * *****</*******>
[19] =>                                     <OrderID>23123INV09123</OrderID>
[20] =>                                     <Amount>127790</Amount>
[21] =>                             </NewOrder>
[22] =>                     </Request>
)

一个问题:您确定您的 XML 数据是正确的吗?

<CardDataNumber>5454545454545454</AccountNum>

它不应该看起来像这样:

<CardDataNumber>5454545454545454</CardDataNumber>

或者像这样:

<AccountNum>5454545454545454</AccountNum>

此行中的相同问题:

<CVVCVCSecurity>300</Exp>

因此,如果您将代码部分从:

if (strcmp($sensData[$f], $currNono) == true && $f+1 != count($sensData)){
$hash = str_repeat("*", strlen($sensData[$f+1]));
$lines[$currLine] = str_replace($sensData[$f+1], $hash, $lines[$currLine]);
}

对此:

if ($f > 0 && $f < count($sensData)-1){
$hash = str_repeat("*", strlen($sensData[$f]));
$lines[$currLine] = str_replace($sensData[$f], $hash, $lines[$currLine]);
}

让我解释一下我的解决方案: if 语句现在检查 if $f 不是 0(括号中的第一个匹配项(并且不是匹配计数 - 1(因此括号中的最后一个匹配项(。如果是这样,则为内容,并随 Asterix (*( 字符的合适长度而更改。

在我的测试中,它做对了工作,如果您有任何问题,请发表评论!

提示!货币指数是匹配的,因为它包含Exp,如您所见:货币指数

相关内容

  • 没有找到相关文章

最新更新