[JavaScript] クレジットカード番号から国際ブランドを特定する

  • このエントリーをはてなブックマークに追加
  • LINEで送る

前回に引き続きクレジットカードがテーマです。今回は決済画面などで入力されたクレジットカード番号がどの国際ブランであるかを調べるコードです。

ブランドを検出するロジックは前回と同じですので、ここではユーザーの入力と検出部分のつなぎ込みがメインテーマとなります。

- Sponsored Link -

クレジットカード番号の仕様

開始番号と桁数

前回と同じ表です。カード番号の冒頭数桁でカード会社を判定できるようになっています。例えば「4」でカード番号が始まっていればVISAであることがわかります。

国際ブランド開始番号桁数セキュリティコード
VISA413, 16CVV(3桁)
MASTER Card510000〜559999, 222100〜27209916CVC(3桁)
JCB3528〜358916CVV(3桁)
American Express34, 3715CID(4桁)
Diners Club300〜303574, 3095, 36, 38〜3914CVV(3桁)
  • この情報は主にWikipediaを参考にしています。誤りや古くなっている箇所などあればご指摘ください。

ブランドの検出方法

では前述のロジックを利用してブランドを検出してみます。単純にカード番号の先頭を取り出して比較するだけですね。

ちょっとだけ厄介なのは「aからbの間」の判定です。正規表現を利用しても良いのですが少し複雑になるのでここではbetween()という関数を用意しました。

const n = '4111111111111111'
const between = (value, min, max) => ((min <= Number(value)) && (Number(value) <= max))

if( n.substr(0,1) === '4' ){
  console.log('Visa')
}
else if( n.match(/^5[1-5]/) || between(n.substr(0,6), 222100, 272099) ){
  console.log('Master')
}
else if( between(n.substr(0,4), 3528, 3589) ){
  console.log('JCB')
}
else if( n.match(/^3[47]/) ){
  console.log('AMEX')
}
else if( between(n.substr(0,6), 300000, 303574) || n.substr(0,4) === '3095' || n.match(/^3[689]/) ){
  console.log('Diners Club')
}

ライブラリを利用して判定

手前味噌ですが先ほどのロジックをそのまま利用したライブラリ「creditcard-checkerjs」を使うともっとシンプルに記述できます。

Webブラウザ上で動かしたい場合はcreditcard-checker.min.jsをダウンロードして保存しておきます。あとは先ほどのライブラリをscriptタグで読み込んでおきcreditcard.cardtype()で判定するだけです。

<script src="creditcard-checker.min.js"></script>
<script>
  const number = '4111111111111111'
  switch( creditcard.cardtype(number) ){
    case creditcard.type.VISA:
      console.log('Visa')
      break
    case creditcard.type.MASTER:
      console.log('Master Card')
      break
    case creditcard.type.JCB:
      console.log('JCB')
      break
    case creditcard.type.AMEX:
      console.log('American Express')
      break
    case creditcard.type.DINERS:
      console.log('Diners Club')
      break

    case creditcard.type.UNKNOWN:
    default:
      console.log('?????')
      break
  }
</script>

サンプル「ほぼリアルタイムに国際ブランドを判定する」

動作サンプル

最初の表を参考にしながらカード番号を入力してみてください。特定できた時点でテキストボックスの右側にアイコンが表示されます。

コード

<!DOCTYPE html>
<html>
<head>
  <meta charset="utf-8">
  <title>creditcard-checker.js example</title>
  <link rel="stylesheet" href="https://use.fontawesome.com/releases/v5.7.2/css/all.css" integrity="sha384-fnmOCqbTlWIlj8LyTjo7mOUStjsKC4pOpQbqyi7RrhN7udi9RwhKkMHpvLbHG9Sr" crossorigin="anonymous">
  <style>
    #brand{ font-size: 20pt; }
    #number{ width:200px; padding:5px; }
  </style>
</html>
<body>

<form>
  <span id="brand"></span>
  <input type="text" id="number" placeholder="XXXX-XXXX-XXXX-XXXX">
</form>

<script src="creditcard-checker.min.js"></script>
<script>
//---------------------------------------
// ブランドを特定する
//---------------------------------------
document.querySelector('#number').addEventListener('keyup', (e)=>{
  const number = document.querySelector('#number').value
  const brand  = document.querySelector('#brand')

  switch( creditcard.cardtype(number) ){
    case creditcard.type.VISA:
      brand.innerHTML = '<i class="fab fa-cc-visa"></i>'
      break
    case creditcard.type.MASTER:
      brand.innerHTML = '<i class="fab fa-cc-mastercard"></i>'
      break
    case creditcard.type.JCB:
      brand.innerHTML = '<i class="fab fa-cc-jcb"></i>'
      break
    case creditcard.type.AMEX:
      brand.innerHTML = '<i class="fab fa-cc-amex"></i>'
      break
    case creditcard.type.DINERS:
      brand.innerHTML = '<i class="fab fa-cc-diners-club"></i>'
      break

    case creditcard.type.UNKNOWN:
    default:
      brand.innerHTML = ''
      break
  }
})

//---------------------------------------
// submitイベントをキャンセル
//---------------------------------------
document.querySelector('form').addEventListener('submit', (e)=>{
  e.preventDefault()
})
</script>
</body>
</html>

参考ページ

コメント

コメント欄は休止中です。お問い合わせはこちらからどうぞ。ご質問はTwitterにリプを投げてください。

このブログを応援する

お寄せいただいたお気持ちは全額サーバ代や次の記事を執筆するための原資として活用させていただいております。この記事が参考になった場合などぜひご検討ください。

PayPal(ペイパル)
PayPalで300円支払う
※金額は任意で変更できます。
※100円でも泣いて喜びますw
※住所の入力欄が現れた場合は「no needed」を選択ください
これまでのご協力者さま
- Sponsored Link -