Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

using omniauth for facebook login with only access token

I am creating an api in rails for mobile application. Now the user will login using facebook and i will recieve the access token post facebook authentication. I have to take this access token and check if the access token exists in applications database. If it does then allow user access, if not then check for email and update the access token and allow user access.

How do i accomplish this with omniauth-facebook and devise , as far as i can see omniauth-facebook does everything from ground up, can't find a way to provide only access token to omniauth-facebook.

Any kinda help would be great.

like image 592
abhilash Avatar asked Feb 11 '13 12:02

abhilash


1 Answers

You don't need omniauth-facebook. This gem's purpose is only to obtain an access token (and query the user's informations). Here's how things happen in a standard setup (with Devise and omniauth-facebook):

  • Omniauth obtains an access token
  • Omniauth fetches the user's informations through through Facebook's API and stores it in the request's environment
  • Omniauth calls a custom callback method in your application that you need to write
  • This callback method retrieves or creates the user in the database, then uses a few helpers provided by Devise to sign the user in.

(see Devise's documentation about Omniauth for more details)

Now, given that you already have an access token, and that fetching the user's informations from Facebook's API is very simple, you don't actually need omniauth-facebook.

All you need to do is to write an action to:

  • receive the access token (as a parameter)
  • fetch the users informations (a Graph API request to /me)
  • find or create the user in database (using the user's Facebook id)
  • sign the user in using Devise's helpers

This code is based on the example given in Devise's documentation.

class Users::FacebookCallbacksController
  def facebook
    # You should test if params[:access_token] is present
    # and if this request fails
    facebook_data = HTTParty.get("https://graph.facebook.com/me", query: {
      access_token: params[:access_token]
    }).parsed_response

    # You need to implement the method below in your model (e.g. app/models/user.rb)
    @user = User.find_for_facebook_oauth(facebook_data)

    if @user.persisted?
      sign_in_and_redirect @user, :event => :authentication #this will throw if @user is not activated
      set_flash_message(:notice, :success, :kind => "Facebook") if is_navigational_format?
    else
      session["devise.facebook_data"] = facebook_data
      redirect_to new_user_registration_url
    end
  end
end

Notes:

  • I'm using the HTTParty gem here to call the Facebook API but there are other possibilities, including Koala
  • sign_in_and_redirect, set_flash_message and is_navigational_format? are helpers provided by Devise
  • Refer to Devise's documentation for implementation of User.find_for_facebook_oauth
  • A gem called devise_facebook_open_graph does the same thing in a slightly different way. It is not really used or maintained, but you might be interested by the implementation.
like image 68
user1003545 Avatar answered Sep 28 '22 18:09

user1003545