Railsのアプリでもっとも重要な認証機能、その中のfacebookでのSNS認証を
導入します。
今回はomniauth-facebookというgemの導入手順についての記事です。
目的
簡単にomniauth-facebookを導入する
(前提、環境)
mac
macOS Mojave 10.14.5
ruby 2.5.1
rails 5.2.3
gem ‘devise’ 4.7.1
はじめに
omniauthについて
そもそものomniauthについてはこちらにまとめてあります。
facebook以外でのSNS認証がしたい場合、参考にしてみてください!
RailsにSNS認証を分かりやすく導入する方法 Omniauthの導入
https://hirocorpblog.com/rails%e3%81%absns%e8%aa%8d%e8%a8%bc%e3%82%92%e5%88%86%e3%81%8b%e3%82%8a%e3%82%84%e3%81%99%e3%81%8f%e5%b0%8e%e5%85%a5%e3%81%99%e3%82%8b%e6%96%b9%e6%b3%95omniauth%e3%81%ae%e5%b0%8e%e5%85%a5/
公式
いつも通りまずは一次ソースのgithubを見に行きます。
omniauth-facebook
https://github.com/mkdynamic/omniauth-facebook
omniauth-facebookとは
facebookのAPIを利用して認証を行うgemです。
導入
facebook APIの取得
まずはfacebook APIを取得しに行きます!
facebook API Console
http://developers.facebook.com/docs/authentication
クリックしたら以下のような感じになります。
①アプリを作成
ヘッダーメニューの「アプリを作成」をクリックしてください。
②表示名を入力
表示名の欄のところにアプリ名を入れて、「アプリを作成してください」を選択してクリックしてください。
③reCAPTCHAを突破
④Facebookログインを選択
左側のサイドバーから「ダッシュボード」を選択し、「 Facebookログイン」を探してください。
そして設定を押しましょう!
⑤Facebookログインを設定
有効なOAuthリダイレクトURIの部分を必要なパスに設定しておきます。
今回はログインした後、トップページに戻りたいので、作成しているアプリのroot_pathを設定しておきましょう。
ローカル環境下だけで起動するのであれば、以下のような形ですね。
localhost::3000
⑤facebookのアプリIDとapp secretを取得
左側のサイドバーから「設定」を選択し、「ベーシック」をクリックしてください。
下記のアプリIDとapp secretは後ほど使用するので控えておきましょう!
こちらでfacebookのAPIの設定は完了です!
Railsにシークレットキーをセット
Railsに外部ツールのキーを設定する方法は様々ありますが、今回僕はRails5.2系を利用しているので推奨されているcredentials.ymlの設定方法で実装します。
※Rails5.1以下の場合はsecrets.ymlやdotenvのgemを使うと良いでしょう!
credentials.yml
まずはアプリのディレクトリに移動して下記のコマンドを打ちましょう。
EDITOR="vim" bin/rails credentials:edit
vimでcredentials.ymlが開くのでインサートモードにして、下記のように記述をしていきます。(先ほど取得したキーを参照にxを書き換えてください。)
facebook:
app_id: 123456789123456
app_secret: xxxx12345xxxxxxxxxxxx
Railsのログイン機能に組み込む
僕はdeviseを利用しているので、deviseの組み込み方をこちらに記述します!
下の方にdeviseを使用していない場合を記述しておきます!
Gemfileに追記
gem 'omniauth-facebook'
bundle install
bundle install
config/initializers/devise.rbに追記
# in config/initializers/devise.rb
Devise.setup do |config|
# 〜〜(省略)
config.omniauth :facebook, Rails.application.credentials.google[:client_id], Rails.application.credentials.google[:client_secret], name: :google,
scope: %w(email)
end
config/routes.rbに追記
# in config/routes.rb
devise_for :users, controllers: { omniauth_callbacks: 'users/omniauth_callbacks' }
app/models/user.rbに追記
deviseで作成したUserモデルにomniauthが使えるように定義します!
後述のコントローラでfrom_authメソッドをUserモデルで使うので、ここで定義しておきましょう。
# in app/models/user.rb
devise :omniauthable, omniauth_providers: [:facebook]
def self.from_omniauth(access_token)
data = access_token.info
user = User.where(email: data['email']).first
# Uncomment the section below if you want users to be created if they don't exist
# unless user
# user = User.create(name: data['name'],
# email: data['email'],
# password: Devise.friendly_token[0,20]
# )
# end
user
end
OmniauthCallbacksControllerに追記
コントローラーにfacebookメソッドを定義します!
# in app/controllers/user/OmniauthCallbacksController.rb
class Users::OmniauthCallbacksController < Devise::OmniauthCallbacksController
def facebook
# You need to implement the method below in your model (e.g. app/models/user.rb)
@user = User.from_omniauth(request.env['omniauth.auth'])
if @user.persisted?
flash[:notice] = I18n.t 'devise.omniauth_callbacks.success', kind: 'facebook'
sign_in_and_redirect @user, event: :authentication
else
session['devise.google_data'] = request.env['omniauth.auth'].except(:extra) # Removing extra as it can overflow some session stores
redirect_to new_user_registration_url, alert: @user.errors.full_messages.join("\n")
end
end
end
viewファイルに記述
facebook認証に飛ばしたいviewファイルに記述します。
<%= link_to "Sign in with facebook", user_facebook_omniauth_authorize_path %>
# Deviseのバージョンが4.1.0以下の場合
<%= link_to "Sign in with facebook", user_omniauth_authorize_path(:facebook) %>
【番外編】config/initializers/omniauth.rbに追記
deviseを使わずに認証機能を実装している方はこちらを
Rails.application.config.middleware.use OmniAuth::Builder do
provider :facebook, Rails.application.credentials.facebook[:app_id], Rails.application.credentials.facebook[:app_secret]
end
終わりに
facebookのAPI取得からdeviseに実装するまでの流れは相当長くなってしまいました汗
facebook先生APIありがとう!!