Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Rails EOF Error when using HTTP.get_response to retrieve Facebook access token

I trying to implement a Login with Facebook feature on my site, and hitting a roadblock trying to get the access token back from Facebook. Here is my code:

if params[:error_reason] == "user_denied" then
  flash[:error] = "To login with Facebook, you must click 'Allow' to let the site access your information"
  redirect_to :login
elsif params[:code] then
  token_uri = URI.parse("https://graph.facebook.com/oauth/access_token?client_id=****************&redirect_uri=http://localhost:3000/auth/fblogin&client_secret=***************&code="+URI.escape(params[:code]))
  response = Net::HTTP.get_response(token_uri)
  session[:response] = response
  data = ActiveSupport::JSON.decode(response)
  access_token = data[:access_token]
  flash[:error] = access_token
  redirect_to :register
end

This is inside a fblogin controller function that is the target of the initial redirect to get an authorization code (the params[:code]).

But when I run through this, I get the following error:

EOFError in AuthController#fblogin

on the Net::HTTP.get_response(token_uri) line. I've searched all over, and can't find anything to indicate what this means. Could it be the obscure characters Facebook uses in their access tokens? I'm totally lost!

like image 864
Dave W. Avatar asked Feb 22 '11 18:02

Dave W.


1 Answers

You are receiving an EOFError because you are trying to connect to an https URL using code that only works with http. See the section entitled "SSL/HTTPS request" at this Net::HTTP Cheat Sheet for the basics.

However, I would recommend using a third-party library to manage this for you, such as OAuth2 for utilizing Facebook's OAuth2 API, where you'd write code like this:

def client
  OAuth2::Client.new('app_id', 'app_secret', :site => 'https://graph.facebook.com')
end

# in your callback code:
access_token = client.web_server.get_access_token(params[:code], :redirect_uri => 'http://localhost:3000/auth/fblogin')
user = JSON.parse(access_token.get('/me'))

If you really want to make the requests yourself, you can look at libraries like Faraday to execute the HTTPS requests for you.

like image 194
Michelle Tilley Avatar answered Sep 23 '22 08:09

Michelle Tilley