67

信用卡类型可以仅从信用卡号确定吗?

这是推荐的还是我们应该总是询问客户他们使用的信用卡类型?

我搜索了一下,发现了这个算法:http ://cuinl.tripod.com/Tips/o-1.htm ,这可靠吗?

4

15 回答 15

32

是的,您提到的网站是正确的。许多网站,包括。我相信 Google Checkout 依赖于卡类型的自动检测。它很方便,使 UI 不那么混乱(少一个输入框)并节省时间。前进!

于 2009-08-20T19:04:40.917 回答
21

我听说有一个很好的理由让他们选择(即使你能弄清楚)。以便他们知道您接受的信用卡列表。

于 2009-08-20T19:07:43.250 回答
11

作为消费者,我讨厌先选卡。我只想开始输入数字。

Wroblewski 的Web 表单设计第 153-154 页讨论了这个问题。它在“不必要的输入”一章的“删除问题”部分。给出的示例是 Paypal,它会在您输入号码时突出显示卡的类型。

于 2009-08-20T19:25:57.927 回答
7

我很确定,至少对于 MasterCard、Visa、Discover 和 American Express 来说,这是准确的。我从来没有和其他任何人一起工作过。

请参阅此页面的最底部: http ://www.merchantplus.com/resources/pages/credit-card-logos-and-test-numbers/

这也可能对你有用” http://www.beachnet.com/~hstiles/cardtype.html

这很有趣: http ://en.wikipedia.org/wiki/Bank_card_number

于 2009-08-20T19:07:17.277 回答
5

这是我使用的适用于当前卡片范围的脚本。还对号码进行有效性检查。

/**
* checks a given string for a valid credit card
* @returns:
*   -1  invalid
*       1   mastercard
*       2   visa
*       3   amex
*       4   diners club
*       5   discover
*       6   enRoute
*       7   jcb
*/
function checkCC(val) {
    String.prototype.startsWith = function (str) {
        return (this.match("^" + str) == str)
    }

    Array.prototype.has=function(v,i){
        for (var j=0;j<this.length;j++){
            if (this[j]==v) return (!i ? true : j);
        }
        return false;
    }

    // get rid of all non-numbers (space etc)
    val = val.replace(/[^0-9]/g, "");

    // now get digits
    var d = new Array();
    var a = 0;
    var len = 0;
    var cval = val;
    while (cval != 0) {
        d[a] = cval%10;
        cval -= d[a];
        cval /= 10;
        a++;
        len++;
    }

    if (len < 13)
        return -1;

    var cType = -1;

    // mastercard
    if (val.startsWith("5")) {
        if (len != 16)
            return -1;
        cType = 1;
    } else
    // visa
    if (val.startsWith("4")) {
        if (len != 16 && len != 13)
            return -1;
        cType = 2;
    } else
    // amex
    if (val.startsWith("34") || val.startsWith("37")) {
        if (len != 15)
            return -1;
        cType = 3;
    } else
    // diners
    if (val.startsWith("36") || val.startsWith("38") || val.startsWith("300") || val.startsWith("301") || val.startsWith("302") || val.startsWith("303") || val.startsWith("304") || val.startsWith("305")) {
        if (len != 14)
        return -1;
        cType = 4;
    } else
    // discover
    if (val.startsWith("6011")) {
        if (len != 15 && len != 16)
            return -1;
        cType = 5;
    } else
    // enRoute
    if (val.startsWith("2014") || val.startsWith("2149")) {
        if (len != 15 && len != 16)
            return -1;
        // any digit check
        return 6;
    } else
    // jcb
    if (val.startsWith("3")) {
        if (len != 16)
        return -1;
        cType = 7;
    } else
    // jcb
    if (val.startsWith("2131") || val.startsWith("1800")) {                                         

        if (len != 15)
        return -1;
        cType = 7;
    } else
    return - 1;
    // invalid cc company

    // lets do some calculation
    var sum = 0;
    var i;
    for (i = 1; i < len; i += 2) {
        var s = d[i] * 2;
        sum += s % 10;
        sum += (s - s%10) /10;
    }

    for (i = 0; i < len; i += 2)
        sum += d[i];

    // musst be %10
    if (sum%10 != 0)
        return - 1;

    return cType;
}
于 2009-08-20T19:10:35.727 回答
5

这是codeproject 上各种 CC 相关内容的完整 C# 或 VB 代码。

  • IsValidNumber
  • GetCardTypeFromNumber
  • GetCardTestNumber
  • 通过卢恩测试

这篇文章已经发布了几年,没有任何负面评论。

于 2009-11-22T23:19:00.487 回答
4

维基百科包含大多数卡片前缀的列表。您发布的链接中缺少一些卡片。您提供的链接似乎也有效。

询问卡类型的一个原因是为了进行额外验证,将用户提供的内容与号码进行比较。

于 2009-08-20T19:13:19.497 回答
4

这是第一篇文章中提到的相同算法的 php 版本

<?php
function CreditCardType($CardNo)
{
/*
'*CARD TYPES            *PREFIX           *WIDTH
'American Express       34, 37            15
'Diners Club            300 to 305, 36    14
'Carte Blanche          38                14
'Discover               6011              16
'EnRoute                2014, 2149        15
'JCB                    3                 16
'JCB                    2131, 1800        15
'Master Card            51 to 55          16
'Visa                   4                 13, 16
*/    
//Just in case nothing is found
$CreditCardType = "Unknown";

//Remove all spaces and dashes from the passed string
$CardNo = str_replace("-", "",str_replace(" ", "",$CardNo));

//Check that the minimum length of the string isn't less
//than fourteen characters and -is- numeric
If(strlen($CardNo) < 14 || !is_numeric($CardNo))
    return false;

//Check the first two digits first
switch(substr($CardNo,0, 2))
{
    Case 34: Case 37:
        $CreditCardType = "American Express";
        break;
    Case 36:
        $CreditCardType = "Diners Club";
        break;
    Case 38:
        $CreditCardType = "Carte Blanche";
        break;
    Case 51: Case 52: Case 53: Case 54: Case 55:
        $CreditCardType = "Master Card";
        break;
}

//None of the above - so check the
if($CreditCardType == "Unknown")
{
    //first four digits collectively
    switch(substr($CardNo,0, 4))
    {
        Case 2014:Case 2149:
            $CreditCardType = "EnRoute";
            break;
        Case 2131:Case  1800:
            $CreditCardType = "JCB";
            break;
        Case 6011:
            $CreditCardType = "Discover";
            break;
    }
}

//None of the above - so check the
if($CreditCardType == "Unknown")
{
    //first three digits collectively
    if(substr($CardNo,0, 3) >= 300 && substr($CardNo,0, 3) <= 305)
    {
        $CreditCardType = "American Diners Club";
    }
}

//None of the above -
if($CreditCardType == "Unknown")
{
    //So simply check the first digit
    switch(substr($CardNo,0, 1))
    {
        Case 3:
            $CreditCardType = "JCB";
            break;
        Case 4:
            $CreditCardType = "Visa";
            break;
    }
}

return $CreditCardType;
 }
 ?>
于 2011-10-14T12:12:50.383 回答
3

您链接的代码对于 Discover 有一个不完整的 BIN/范围列表,省略了 Diner's club(现在无论如何都属于 Discover),列出了不再存在且应该折叠成其他类型的卡类型(enRoute、Carte Blanche),并忽略了越来越重要的 Maestro International 推车类型。

正如@Alex 证实的那样,可以从 BIN 编号确定卡类型,许多公司都这样做,但始终如一且正确地这样做并非易事:卡品牌不断变化,当您尝试处理时,跟踪事情变得更加复杂区域借记卡(爱尔兰的激光,欧洲的 Maestro 等) - 我在任何地方都没有找到免费且维护(正确)的代码或算法。

正如@MitMaro 指出的那样,维基百科包含一个高级别的卡片标识符列表,以及一个更具体的 BIN 编号和范围列表,这是一个好的开始,正如 gbjbaanb 评论的那样,巴克莱有一个公开发布的列表(但是由于某种原因,它似乎不包括 Discover - 大概他们不在 Discover 网络上处理?)

看起来微不足道,正确的卡片识别算法/方法/功能需要维护,所以除非您的检测程序是非关键/信息性的(例如@Simon_Weaver 的建议),或者您将投入工作以保持最新,我建议您跳过自动检测。

于 2012-07-09T12:15:57.563 回答
3

Stripe为卡片方案检测提供了这个奇妙的javascript库。让我添加一些代码片段并向您展示如何使用它。

首先将其包含到您的网页中

<script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/jquery.payment/1.2.3/jquery.payment.js " ></script>

其次使用函数 cardType 来检测卡片方案。

$(document).ready(function() {              
            var type = $.payment.cardType("4242 4242 4242 4242"); //test card number
            console.log(type);                                   
}); 

以下是更多示例和演示的参考链接。

  1. jquery.payment.js 的条纹博客
  2. Github 仓库
于 2015-04-17T05:09:23.140 回答
2

这是一种自动确定卡片类型并在用户输入时将其显示给用户的快速方法。

这意味着a)用户不必选择它,b)他们不会浪费时间寻找不存在的下拉菜单。

非常简单的 jQuery 版本,适用于 Amex、Visa 和 Mastercard。如果您需要其他卡类型,您可以使用

 $('[id$=CreditCardNumber]').assertOne().keyup(function(){

        // rules taken from http://en.wikipedia.org/wiki/Credit_card_number#cite_note-GenCardFeatures-0
        var value = $(this).val();

        $('#ccCardType').removeClass("unknown");
        if ((/^4/).test(value)) {
            $('#ccCardType').html("Visa");
            return;
        }
        if ((/^5[1-5]/).test(value)) {
           $('#ccCardType').html("Mastercard");
           return;
        }
        if ((/^3[47]/).test(value)) {
           $('#ccCardType').html("Mastercard");
           return;
        }
        $('#ccCardType').html("Enter card number above");
        $('#ccCardType').addClass("unknown");
     });

这是伴随此的 jQuery(ASP.NET MVC):

  Card number: <%= Html.TextBox("PaymentDetails.CreditCardDetails.CreditCardNumber")%>
  Card Type: <span id="ccCardType" class="unknown">Enter card number above</span>

我有一个用于.unknown显示灰色文本的 CSS 规则。

于 2009-10-24T05:20:50.757 回答
1

Python 中的这个实现应该适用于 AmEx、Discover、Master Card、Visa:

def cardType(number):
    number = str(number)
    cardtype = "Invalid"
    if len(number) == 15:
        if number[:2] == "34" or number[:2] == "37":
            cardtype = "American Express"
    if len(number) == 13:
        if number[:1] == "4":
            cardtype = "Visa"
    if len(number) == 16:
        if number[:4] == "6011":
            cardtype = "Discover"
        if int(number[:2]) >= 51 and int(number[:2]) <= 55:
            cardtype = "Master Card"
        if number[:1] == "4":
            cardtype = "Visa"
    return cardtype
于 2009-08-20T19:46:45.340 回答
1

如果您接受的所有信用卡都具有相同的属性,那么只需让用户输入卡号和其他属性(到期日期、CVV 等)。但是,某些卡类型需要输入不同的字段(例如,UK Maestro 卡的开始日期或发行编号)。在这些情况下,您要么必须拥有所有字段,从而使用户感到困惑,要么使用一些 Javascript 来隐藏/显示相关字段,再次使用户体验有点奇怪(字段消失/出现,因为他们输入信用卡号) . 在这些情况下,我建议先询问卡片类型。

于 2009-09-13T07:41:42.550 回答
1

就我个人而言,我首先选择卡类型没有问题。但在我看来,信用卡号码输入有两个方面存在问题。

最糟糕的是无法在数字组之间输入空格。包括打印在物理卡上的空格将使用户更容易扫描数字以验证他们是否正确输入了信息。每次我遇到这种普遍存在的缺陷时,我都觉得自己被推回了一个石器时代,因为无法过滤用户输入以删除不必要的字符。

第二个是需要在电话下单的时候听卖家把卡号重复给你。信用卡收款人真正需要的只是一个 UI,让他们可以访问校验位方案,以验证 cc 号码是否有效。根据该算法,前 15 个(或许多)数字计算最后一个数字 - 几乎不可能“愚弄”。一个胖手指数字“通过”需要在 15 位数字中至少有两个相互抵消的错误。除非该算法存在被我怀疑的转置相邻数字(常见的输入错误)不成比例地愚弄的缺陷,否则我认为它比任何人工仔细检查都更可靠。

于 2014-10-04T18:49:26.587 回答
0

https://binlist.net/提供免费的 API。您只需输入卡号的前 6 位或 8 位数字 - 即发卡行识别号 (IIN),以前称为银行识别号 (BIN)。

curl -H "Accept-Version: 3" "https://lookup.binlist.net/45717360"

(从更具体的问题交叉发布:如何区分借记卡和信用卡

于 2019-02-09T07:40:57.153 回答