話題の決済サービス Stripe を使ってみた
ども、どもども。
ここ数年、話題の決済サービスStripeを使ってみました。
これまで、クレジットカード決済代行サービスはいくつか利用してきましたが、ちょっとした「かゆいところ」がありました。
- 決済手数料の問題(月額維持費的なものも含む)
- 購入者アカウント登録の必要性
- アカウント審査時間(利用開始までの時間)の問題
- ダウンロード販売への対応可否(ドキュメント不足あるいは難読問題含む)
- テスト環境の利用しやすさ
- 別ウィンドウ問題( https://www.ni4.jp/2018/02/post_97.html )
これらを一挙に解決できそうなサービスがStripeでした。
決済手数料などを他の決済サービスと比較した結果などは他のブログ記事さんでも紹介されているのでそちらにお任せします(笑)
アカウント登録も無料ですし、利用開始までの流れなども特にマニュアルなどなくてもサクサクと進められると思うので、まずは触ってみると良いんじゃないでしょうか。
最初、私も英語のドキュメントがとっつきにくいと思ったのですが、わかりやすい英語でしたし、難しいところはGoogle翻訳などを使用してもクリアできる感じだったので大丈夫と思います。
というわけでこのブログでは、プログラマーではない私の目線で「うまく行ったところ/うまく行かなかったところ」など、これまでの経緯をまとめてみようと思います。
Stripeを導入してみる
さっそく決済フローを作っていきます。
Stripeでのクレジットカード決済を実現するにはいくつか方法がありますが、私は「Checkout.js」と「PHP」で構築することにしました。
PHPのライブラリは以下からダウンロードできます。
https://github.com/stripe/stripe-php/releases
大まかな流れは以下のような感じです。
- Checkout.jsで決済ボタンを作成
トークンを発行してカード情報をStripeに登録 - PHPでクレジットカード決済を実行
トークンから顧客情報を作成、その情報から決済(チャージ)を実行
Checkout.jsを利用して決済ボタンを作成
まずは決済ボタン(今すぐ購入!的なボタン)を作成します。
これはホントに簡単で、以下のコードサンプルを決済ボタンを表示したい場所に設置するだけです。
なお、住所などの入力を要する場合はStripeのドキュメントを参考に、data-shippingAddress="true"のオプションを付与してください。(最初、これがわからなかった...)
https://stripe.com/docs/checkout
<form action="stripe-php/charge.php" method="POST">
<input type="hidden" name="productId" value="iuu">
<script src="https://checkout.stripe.com/checkout.js" class="stripe-button"
data-key="公開APIキー(テスト用 or 本番用)"
data-amount="決済金額"
data-name="支払先の名前"
data-description="購入内容の詳細"
data-image="アイコン(ダイアログに表示)"
data-locale="auto"
data-currency="jpy">
</script>
</form>
上記を設置すると、その場所に購入ボタンが表示されます。(JSで表示)
私が公開しているサイトではその見た目をさらにJSで置き換えたりしていますが、それについてはもっと良い方法があるかもしれません(苦笑)
ともあれ上記をHTMLに設置して、購入ボタンをクリックすると以下のようなダイアログが表示されます。
右上に「TEST MODE」とあるのでこれがテスト環境であることがわかります。
この状態でメールアドレスとカード情報を入力し「支払う」をクリックすることで、Stripe側でトークンが発行されます。
そのトークンをformで stripe-php/charge.php で受け取るわけです。
PHPを利用して顧客情報と決済情報をStripeに送信する
Checkout.jsで発行されたトークンをcharge.phpで受け取り、以降の動作(顧客作成、チャージほか)を行います。
さきほどダウンロードしたPHPのライブラリを任意の場所にインストール(アップロード)して、同じ場所にcharge.phpを作ります。
最小構成としてはチャージ(決済)だけでOKですが、私は以下のように書いています。(一部省略)
<?php
// 他のライブラリを読み込み
require_once('init.php');
// APIキー登録
$stripe = array(
"secret_key" => "sk_********************",
"publishable_key" => "pk_********************"
);
\Stripe\Stripe::setApiKey($stripe['secret_key']);
// Checkput.jsからPOSTされたトークンとメールアドレスを代入
$token = $_POST['stripeToken'];
$email = $_POST['stripeEmail'];
// 決済額を設定
$price = '決済金額';
// 顧客を作成
$customer = \Stripe\Customer::create(array(
'email' => $email,
'source' => $token
));
// チャージを作成
$charge = \Stripe\Charge::create(array(
'description' => $product,
'customer' => $customer->id,
'amount' => $price,
'currency' => 'jpy'
));
// 処理が完了したら完了ページへリダイレクト
header('Location: https://www.juxtaposition.jp/image-upload-utility/thanks.html');
?>
上記以外にも価格を複数設定している部分があったり、製品購入時のライセンス番号を発行したり、メールを送信したりしていますが、その部分は省略しています。
実際にはチャージが失敗した場合などの処理を入れておくと良さそうですが、その辺りは追々設置していきますね(汗)
secret_key と publishable_key をテスト環境用のAPIキーにしておくと、ダッシュボードのテスト環境で決済完了が確認できます。
また、「開発者」メニューの「ログ」で、トークン発行(tokens)/顧客作成(customers)/チャージ作成(charges)までが確認できます。
本番環境への切り替え
本番環境への切り替えと実際にチャージされた代金が口座振替されるまでには以下のことを実施することになります。
- 本番環境利用の申請を行う(事業の所在地や口座情報などを入力)
- APIキーを本番環境のものに置き換える
- 最初の支払いがあった際、本人確認を行う(免許証コピーなどの送信)
いずれもダッシュボードがわかりやすいし、申請方法などは検索するといろいろと情報が出てくるので困ることはなさそうです。
ダウンロード販売に挑戦してみる
さてさて、ここまでで一般的なクレジットカード決済は完成したわけですが、今回私がStripeを導入するもう1つの目的、ダウンロード販売にも挑戦してみようと思います。
かつてPayPalで挑戦するも失敗してしまったダウンロード販売、Stripeでは意外に簡単に完成しました。
とはいえ、今回は販売商品も限定的なものなのでこれでいいかもしれませんが、もっと大規模になると違うのでしょうね(汗)
先程のcharge.phpに以下を書き足します。
echo <<<eof
<form method="post" action="/thanks.html">
<input type="hidden" name="email" value="{$email}" />
<input type="hidden" name="product" value="{$product}" />
<input type="hidden" name="name" value="{$name}" />
<input type="hidden" name="productid" value="{$productid}" />
</form>
<script>
document.forms[0].submit();
</script>
eof;
// 処理が完了したら完了ページへリダイレクト
// header('Location: https://www.juxtaposition.jp/image-upload-utility/thanks.html');
※先ほどまで記載していたリダイレクト部分は不要になります。
上記は一連の処理(顧客作成、チャージ作成)が完了した後に、購入完了ページ(thanks.html)へ購入者情報などをPOSTして移動する内容になります。
購入完了ページ(thanks.html)では、上記のほかいくつかの情報を確認して、それらが正しいものであれば製品ダウンロードURLへのリンクを設置するようにしています。
なので、購入手続きを踏まないまま購入完了ページのURLを表示しても、それらのリンクは表示されません。
非常に簡易なものではありますが、これでダウンロード販売を実現できました!
長年の希望が実現した瞬間です(笑)
ユーザーグループに参加してみた
さて、ちょっと話は変わりますが、私が急に思い立ってここまで順調に進むことができたのは、今年の7月26日に開催されたStripeユーザーグループのイベント「JP_Stripes (Stripe ユーザーグループ)in サッポロ Vol.2」での事例発表が間近に迫っていたからでした(笑)
プログラマーでもない私が事例発表なんてと思ったのですが、せっかくの機会をいただいたので、Stripeを選んだ理由やダウンロード販売実現までのことなどを発表させてもらいました。
その際のスライドが以下になります。
3月に開催された第1回に参加した際に、7月の発表を予告されてしまい正直焦った部分はあるのですが、これがなければ自分で構築することもなかったな...と(笑)
それに、仕組みを覚えることができたので、自分が構築せずにプログラマーさんやエンジニアさんに相談する際にも役立つだろうなということで、結果オーライです!
それにユーザーグループに参加すると、同じようにStripeを利用している方たちとも知り合いになれるので、つまづきポイントなども相談できたりしてよかったと思っています。
問題発生...!でもサポートに問い合わせて解決できた
順調かにみえた矢先、ちょっとした(いやそれどころなじゃないかもw)なミスが発覚しました。
いずれも凡ミスなんですが、1つは購入があった際のメール通知部分がうまく行っていなく、自身宛に購入があった通知メールが送信されてこなかったこと。
そしてもう1つは肝心のチャージがうまく行っていなかったことでした。
1つめはホントに凡ミス(テスト中は自分のメールアドレスで申し込むので気がついていなかった)だったので、すぐに解決できたのですが、2つめの理由がわからない。
テスト環境では確かにチャージできていて、それは今でも確認できているのに、なぜか本番切り替え後にそのチャージがうまくいっていませんでした。
ダッシュボードのログには200OKでリクエストが成功したと残っているのに売上として上がってこない...。
そこでサポートに連絡してみることにしました。
(Stripeのサポートは迅速でかつ、日本語でやり取りできるとのことだったので一度試してみたかった)
得られた回答はこちら。
トークンは作成されていますが、チャージが作成されていないため、支払いが完了しておりません。
APIにて取得されたトークンを利用されますと、チャージすることができます。
チャージを作成するパラメータにつきましては、こちらをご参照ください:https://stripe.com/docs/api#create_charge
サポートとの連絡は非常にスムースでしたが、やはり私は悲しきノンプログラマー。
連絡いただいた上記の意味がピンときませんでした。(今読むと当たり前のようにわかりやすい...)
これってつまり、購入者のクレジットカードに請求できていないってことだよね?
ってことは、もう1回購入手続きをやり直してもらう必要があるのかな?というわけで再度問い合わせ。
お客さまのクレジットカード情報がすでにトークンとして取得されている状態です。そのため、お客さまから再度決済をお願いされなくてもよいかと存じます。トークンは作成されていますので、トークンを利用してチャージを作成していただけますと支払いが完了します。
ふむ...。
トークンが取得されているからチャージを作成すると。
なるほど(わかっていない)
ただ、「チャージが作成できていない」ことはハッキリしたので、もう一度charge.phpを確認してみると...
// 顧客を作成
$customer = \Stripe\Customer::create(array(
'email' => $email,
'source' => $token
));
// チャージを作成
$charge = \Stripe\Charge::create(array(
'description' => $product,
'customer' => $customer->id,
'amount' => $price,
'currency' => 'jpy'
));
なぜか上記の部分がごっそりと抜け落ちていることが判明!
おそらく最終的に不要なコードを整理している中で、上記を誤って削除してしまったものと...
失敗だったのはこの段階までGitを使っていなく、最終的に完成したところからしか残っていなくて、差分も確認できなかったという...
いやはや参りました...。
原因はわかったけれど、途中まで進んだ状態で引き続き「顧客作成/チャージ作成」をどう進めると良いんだ?という問題に。
そこで、なにかドキュメントで参考になるところがないかと再度連絡することにしました。(いやホントすみません汗)
その後も丁寧にドキュメントの該当箇所を教えてくれたサポートさん。
その結果、charge.phpの一部を変更して、そのPHPをブラウザから叩くことでチャージが無事に成功したのでした。
テスト環境で何度も試してから本番で実施したのですが、テスト環境で試しやすいってのがここでも活きました。
実施した手順はこちら
- ダッシュボードの「開発者」メニューの「ログ」から該当のtokensを開く
- Checkout.jsからのPOSTに対し応答した内容にある「"id": "tok_hogehoge",」を見つけ、tok_hogehoge部分をコピー
- charge.phpの「顧客を作成」にあるsourceにそれを直接記入(POST内容にあるメールアドレスもemailに記入)
- 「チャージを作成」のdescriptionとamountにも直接記入
- メール送信などの部分は不要なので削除
- charge.phpをcharge_fuga.phpなどとリネームしてアップロード
- ブラウザからcharge_fuga.phpにアクセス(私はここで完了画面へリダイレクトするようにしました)
以上を行って、ダッシュボードを確認すると無事にチャージが成功(ログにcustomersとchargesが記録される)し、売上が正常に登録されましたー!
良かった!
いろいろ教えてくれたサポートさん、ありがとうございました!
まとめ:ウェブディレクターがStripeを使ってみた感想
先のスライドにもありましたが、まず思ったのは「いろいろ試しやすい!」ということ。
PayPalでもいろいろと試したことはあったのですが、そのテスト環境の使いやすさでは圧倒的にStripeが良かったです。
あと、私はPHPを使用しましたが、他にもライブラリが揃っていることと、そのドキュメントがわかりやすかったことも良いと思います。
Stripeの情報を得ようと検索してみると、WordPressでプラグインを利用する際の情報ばかりが出てきたり、あるいはCheckout.jsの部分までで説明が終わっていて、肝心のチャージ部分に触れられていなかったり、そこまで説明があったとしてもPHP以外の言語だったりとなかなか困ったものでしたが、結果的には公式ドキュメントをゆっくり読むのが一番わかりやすかったんじゃないか、と。
そしてワタシですらここまで自力でできたんだから、プログラマーさんやエンジニアさんにとってはもっと使いやすいのではないかという気がしました。
この記事の冒頭で挙げたこれまでの決済サービスのかゆいところをすべてフォローして余りある感じ、個人的には大満足な決済サービスで、今後は弊社の案件でも利用頻度が増えると思います!
この記事に書いてあるコードはまだまだ改善の余地があるのかもですが、そこは少し大目に見ていただいて、まずは皆さんも試してみては?
以上、Stripeを試してみた話でした!