Rails5.2でStripeを使う

[Rails5.2で色々やってみる](https://qiita.com/lumbermill/items/5a94264eb3888bf0c133) という記事で作成したRailsプロジェクトに付け足して[Stripe](https://stripe.com/jp)によるクレジットカード決済を実装しています。普通に新規プロジェクトを作った続きとして読んで頂いても大体OKなはずです。

![stripe-flow.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/50780/d43aa113-e552-e288-10fd-4a573c57f282.png)

まずはGemfileにgemを追加して、`bundle install`を実行します(gemのバージョンは5.11でした)。

```ruby:Gemfile
gem 'stripe'
```

Stripeのダッシュボード Developers -> API Keys にアクセスして「Publishable key」と「Secret Key」を取得しておいてください。

定額の商品を１つ購入するサンプルとして、購入ページ(payment1)と購入完了ページ(payment2)を作成します。

```ruby:config/routes.rb
  get '/payment1', to: 'pages#payment1'
  post '/payment2', to: 'pages#payment2'
```

pages_controller.rbが無い場合は以下のコマンドで作成してください。[前回の記事](https://qiita.com/lumbermill/items/5a94264eb3888bf0c133)でコントローラを作成している場合は不要です。

```bash
rails g controller Pages payment1 payment2
```

コントローラのコードは以下のようになります。payment1はボタン(JavaScript)を置くだけでpayment2では、postされてきたメールアドレスとトークンを元に Customer(顧客) を作成し、さらにそのIDを使って、500円の Charge(決済) を作成します。カードが承認されないなどのエラーが発生した場合は、そのメッセージと共に payment1 にリダイレクトさせています（TODO: メッセージを日本語で取得する方法はあるのかな？）。

```ruby:app/controllers/pages_controller.rb
  def payment1
  end

  def payment2
    customer = Stripe::Customer.create(
      :email => params[:stripeEmail],
      :source  => params[:stripeToken]
    )

    charge = Stripe::Charge.create(
      :customer    => customer.id,
      :amount      => 500,
      :description => 'From Rails Demo',
      :currency    => 'jpy'
    )
  rescue Stripe::CardError => e
    flash[:error] = e.message
    redirect_to payment1_path
  end
```

対応するビューの方は以下のような感じ。なるべくシンプルに書いています。先程取得したキーのうち「Publishable」の方をボタンの属性としてセットしています。

```erb:app/views/pages/payment1.html.erb
<%= form_tag payment2_path do %>
  <% if flash[:error].present? %>
    <div id="error_explanation">
      <p><%= flash[:error] %></p>
    </div>
  <% end %>
  <p>Total(tax included): ¥500 </p>
  <script src="https://checkout.stripe.com/checkout.js" class="stripe-button"
          data-key="pk_test_DfoKFBIrAGKhxBbDgP0G954e"
          data-description="テスト"
          data-amount="500"
          data-currency="jpy"
          data-locale="auto"></script>
<% end %>
```

```erb:app/views/pages/payment2.html.erb
<p>Thank you for purchasing!</p>
<p><%= link_to 'Back', payment1_path %></p>
```

「Secret」の方のAPI KeyはRailsのcredentialsの中に保管することにします。以下のコマンドでファイルを開き、

```bash
EDITOR=vim rails credentials:edit
```

最下行に以下のように定義します。

```yml
stripe_secret_key: sk_test_xxxxxx
```

（おまけ）docker-composerを使っている場合は、エディタのインストールが必要です。

```bash
docker-compose exec web apt install vim
docker-compose exec -e EDITOR=vim web rails credentials:edit
```

以下のようにinitializersの中に記述して、credentialsに保存したキーの値をStripeのフレームワークにセットします。

```ruby:config/initializers/stripe.rb
Stripe.api_key = Rails.application.credentials.stripe_secret_key
```

以上でローカル環境では動作するようになるはずです。Stripeのダッシュボード Paymentsの一覧に決済が登録されていることを確認してみてください。

--- 
（おまけ）Railsのcredentialsを参照するためには、`config/master.key`というファイルが必要ですが、Herokuにはアップロードできない（= `git add`したくない）ので、代わりにmaster.keyの中に書かれたハッシュ値を環境変数としてセットします。

```
heroku config:set RAILS_MASTER_KEY=xxxxx
```

これで、ローカル環境と同様にAPI Keyが読み込まれるようになります。

## 参考リンク
- [StripeがRailsで動く仕組み]
(https://qiita.com/100010/items/c09fb08dd555b32a2652)  
ほとんどこちらの記事をベースにさせて頂きました。Rails5.2以降の仕様に合わせて鍵の持ち方を変更しています。