読者です 読者をやめる 読者になる 読者になる

手取り足取りプログラミング

cloud9、railsについて自分がつまずいた所を詳しく説明します。なぜなら一番読み返すのは自分だから。

【Rails】twitter認証の実装方法(omniouth)

Rails

omniauthを利用してtwitter認証行うサンプルを作成します。

バージョン

ruby 2.3.0
Rails 4.2.5

twitter managementでキーを発行

twitter management に登録

Twitter Application Management から登録します。
f:id:yonayonaru:20170110233423p:plain

新しいアプリの作成

f:id:yonayonaru:20170110233600p:plain

情報の入力

  • Name:アプリケーション名。お好きな名前でどうぞ。
  • Description:アプリケーションの説明。10文字以上で。
  • Website:websiteのURLを入力します。
  • callback URL:Websiteと同じURLを設定します。必須ではないけど入力しないとWebアプリでエラーが出ます。

以上を入力し、同意のチェックをつけてボタンを押します。
f:id:yonayonaru:20170121213708p:plain

キーを確認

Keys and Access Tokens タブをクリックする。
Consumer Key (API Key)とConsumer Secret (API Secret)を後で使用します。
f:id:yonayonaru:20170110233910p:plain

omniauth

omniauthをGemfileに追加

Gemfileに下記内容を追加します。

Gemfile

gem 'omniauth'
gem 'omniauth-twitter'

twitter認証キー入力ファイルの作成

twitter認証のキーなどを入力するファイルを作成します。

touch config/initializers/omniauth.rb

config/initializers/omniauth.rb

Rails.application.config.middleware.use OmniAuth::Builder do
  provider :twitter, 'KEY', 'SECRET'
end

KEY、SECRETの部分はtwitter managementで確認したConsumer Key (API Key)とConsumer Secret (API Secret)を入力してください。

Model作成

Userモデル作成

rails g model user provider:string uid:string nickname:string image_url:string

twitterから渡ってきたデータが入ります。
provider:"twitter"という文字列
uid:id
nickname:twitterのアカウント名(@〜のやつ)
image_url:twitterのアイコン

app/model/hotpepper.rb

class User < ActiveRecord::Base
  def self.find_or_create_from_auth(auth)
    provider = auth[:provider]
    uid = auth[:uid]
    nickname = auth[:info][:nickname]
    image_url = auth[:info][:image]

    self.find_or_create_by(provider: provider, uid: uid) do |user|
      user.nickname = nickname
      user.image_url = image_url
    end
  end
end

コントローラー

sessionsコントローラーの作成

touch app/controllers/sessions_controller.rb

app/controllers/sessions_controller.rb

class SessionsController < ApplicationController
  def create
    user = User.find_or_create_from_auth(request.env['omniauth.auth'])
    session[:user_id] = user.id
    redirect_to root_path
  end

  def destroy
    reset_session
    redirect_to root_path
  end
end

applicationコントローラーにヘルパーメソッド追加

current_user:現在ログイン中のユーザを取得
logged_in?:ログイン状態を取得

app/controllers/application_controller.rb

class ApplicationController < ActionController::Base

  protect_from_forgery with: :exception

  helper_method :current_user, :logged_in?

  private

  def current_user
    return unless session[:user_id]
    @current_user ||= User.find(session[:user_id])
  end

  def logged_in?
    !!session[:user_id]
  end
end

Viewの作成

rails g controller homes top
ログインしていたら、アイコン、アカウント名、ログアウトを表示します。
ログインしていなかったら、ログインを表示します。
app/views/home/top.html.slim

- if logged_in?
  = image_tag current_user.image_url
  = label_tag current_user.nickname
  br
  = link_to 'ログアウト', logout_path
- else
  = link_to 'Twitterでログイン', 'auth/twitter'

Routeの設定

ログイン画面をルートにしておきます。

config/routes.rb

  get 'auth/:provider/callback', to: 'sessions#create'
  get '/logout', to: 'sessions#destroy'

  root 'homes#top'

完成

ログイン画面

起動するとログイン画面が表示されます。
f:id:yonayonaru:20170121223519p:plain

認証中

認証中の画面が表示されます。
f:id:yonayonaru:20170121223557p:plain

ログイン済み

ログインが完了しtwitterアカウント名と画像が表示されれば成功です。
f:id:yonayonaru:20170121223708p:plain

cloud9の公開リンク

実装済みのソースを公開します。
今回は取りあえずslim版のみ
https://ide.c9.io/yonayonaru/sample-omniauth-twitter-slim