Help us understand the problem. What is going on with this article?

クレジットカード番号を保有せずクレジットカード番号を保存するCard on Fileの使い方

More than 1 year has passed since last update.

Eコマースサイトなどでよくある「クレジットカード番号を保存する」チェックボックスですが、これをチェックしておくとクレジットカード番号がそのまま保存されそうで何となく避けてしまう人も多いでしょう。とは言え、毎回の決済時にカード番号を入力するのも面倒です。

そこでSquareで提供しているのがCard on Fileと呼ばれる機能です。これはカード番号を保有せず、サービス提供事業者がカード決済を繰り返し使えるようにする機能です。

今回はRuby on Railsで簡易的に実装したデモを元に紹介します。

認証について

カード情報を保存するので、認証はあった方が良いでしょう。今回はDeviseを使って簡単に実装してあります。

カード番号の保存

認証後、カード番号を保存できるようになります。

Screenshot_ 2017-11-23 14.40.03.png

クレジットカード番号の入力フォームです。Bootstrapベースになっています。ちなみにここで表示されているテキストボックスはすべてSquare側のiframe内で提供されており、Webサービス提供側からは触れないようになっています。ユーザからの見た目はWebサービス側そのままですし、デザインの自由度も高いのですがセキュリティ的に安全な仕組みになっています。

カード番号を入力してカード番号を保存するボタンを押すと、まずカード番号や有効期限、CVVといった情報がSquareのサーバに送られます。その結果、一時的に決済に使えるトークン(nonce)が発行されます。このトークンと決済金額を合わせて決済ができますが、これは一度しか使えません。

カード情報を永続化する

そこでこのトークンを映像化します。そのためにはまずSquareの顧客APIを使って、顧客を作ります。これはカード番号をまとめて管理するためのもので、メールアドレスや名前などだけで作れます。パスワードは不要です。

Rubyの場合は次のように実装します。

api = SquareConnect::CustomersApi.new

if current_user.square_customer_id.nil?
  customer = api.create_customer({
    email_address: current_user.email
  }).to_hash[:customer]
  current_user.update_attribute :square_customer_id, customer[:id]
end

次にこの情報とカードのトークン(nonce)とを結びつけてカードを作成します。

card = api.create_customer_card(
  current_user.square_customer_id, {
  card_nonce: card_nonce
}).to_hash[:card]

後はこの結果をもとに、IDをデータベースに保存します。

current_user.cards.create(
  nonce: card[:id],
  last4: params[:last_4],
  brand: params[:card_brand],
  exp_month: params[:exp_month],
  exp_year: params[:exp_year]
)

決済を行う

では決済を行う場合です。処理時には店舗ID(location_id)や処理ID(ユニークな文字列)が必要です。そして前述の顧客ID(current_user.square_customer_id)とカードIDを使って決済が行えます。

Screenshot_ 2017-11-24 9.14.15.png

idempotency_key = SecureRandom.uuid
card = current_user.cards.find(params[:checkout][:card])
amount = params[:checkout][:amount].to_i # 決済額

api = SquareConnect::TransactionsApi.new
transaction = api.charge(load_config['location_id'], {
  idempotency_key: idempotency_key,
  amount_money: {
    amount: amount, currency: 'JPY'
  },
  customer_id: current_user.square_customer_id,
  customer_card_id: card.nonce
}).to_hash[:transaction]

このIDの組み合わせであれば繰り返し決済処理が行えます。

Screenshot_ 2017-11-24 9.22.15.png


こちらのコードは goofmint/Square_Card_on_File_Demo: SquareのCard on Fileを使ったデモです。 にアップロードしてあります。実装時の参考にしてください。また、質問がある場合には Teratail にてお願いします!

Build with Square

Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
Comments
No comments
Sign up for free and join this conversation.
If you already have a Qiita account
Why do not you register as a user and use Qiita more conveniently?
You need to log in to use this function. Qiita can be used more conveniently after logging in.
You seem to be reading articles frequently this month. Qiita can be used more conveniently after logging in.
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
ユーザーは見つかりませんでした