开发者

Does OmniAuth provide simple hooks to the Facebook Graph API?

I am working on integrating Omniauth with my new Facebook application, and I am looking through the rather sparse documentation to understand if it gives simple ways to access the graph API... I am moving from Koala which was pretty simple.

Has anyone out there used Omniauth for this yet? I want to get photos fr开发者_运维问答om the users' albums, and sort and get the unique URLs for them.


I finally found out:

1) include this gem

2) use the gem:

user = FbGraph::User.new('me', :access_token => session[:omniauth]["credentials"]["token"])

user.fetch

3) retrieve your information user.name

Remember you can get anything from here ttp://developers.facebook.com/docs/reference/api/user


Another good option is Koala: https://github.com/arsduo/koala

If you're just using Facebook, Koala has its own OAuth support. It also works fine with OmniAuth. To use them together, set up OmniAuth per this Railscast: http://railscasts.com/episodes/235-omniauth-part-1

Then add a 'token' column to 'authentications' table, and any supporting methods for retrieving tokens. When the app needs to interact with Facebook, let Koala grab the token and do its thing. In a controller:

if @token = current_user.facebook_token
  @graph = Koala::Facebook::GraphAPI.new(@token)
  @friends = @graph.get_connections("me", "friends")
end


First, I would go for fb_graph, just compare:

with koala:

graph = Koala::Facebook::GraphAPI.new OAUTH_ACCESS_TOKEN
friends = graph.get_connections("me", "friends")
graph.put_object("me", "feed", :message => "I am writing on my wall!")

with fb_graph:

me = FbGraph::User.me OAUTH_ACCESS_TOKEN
my_friends = me.friends
me.feed! :message => "I am writing on my wall!"

When using omniauth, every user has many authorizations (facebook, twitter, ...)

For each user authorization, you should store the oauth token that is returned in your oauth callback hash.

auth = Authorization.create!(:user => user,
                             :uid =>      hash['uid'],
                             :provider => hash['provider'],
                             :token =>    hash['credentials']['token'])

Then wherever you want to access albums and photos, do something like this:

class User
  ...
  has_many :authorizations
  ...
  def grap_facebook_albums
    facebook = authorizations.where(:provider => :facebook).first
    fb_user = ::FbGraph::User.fetch facebook.uid, :access_token => facebook.token
    fb_albums = fb_user.albums
  end
  ...
end


So I wasn't able to get fb_graph to work properly - I am still a noob having been a Ruby On Rails developer for a total of about 8-10 weeks, and therefore don't have an instinct for what must be obvious problems to other folks.

However I found this great little blog post which outlines a simple facebook client and shows clearly how it all plugs together. I found an issue with it picking up the me/picture object as Facebook returns an http302 not http200 but that was easily worked around with the help of the author. Check it out: http://bnerd.de/misc/ruby-write-basic-client-for-facebook-graph-api/

I am now using Omniauth for the simplicity of the login/signup interaction based on this walkthrough here: blog.railsrumble.com/blog/2010/10/08/intridea-omniauth and with the token I get from that I am using this simple FBClient from the bnerd reference above to access the Graph API. Hope what I found helps others.

...here's my version of bnerd's code and it worked for me:

    class FBClient

      def initialize(app, access_token = nil)
        @app = app
        @access_token = access_token
      end

      # request permission(s) from user
      def request(perms)
        #create a random verifier to identify user on fb callback
        verifier = (0...10).map{65.+(rand(25)).chr}.join
        uri = "https://graph.facebook.com/oauth/authorize?client_id=#{@app.app_id}&redirect_uri=#{@app.connect_url}?verifier=#{verifier}&scope=#{perms}"

        request = { :verifier => verifier, :uri => uri }
        return request

      end

      def connect(code, verifier)

        uri = URI.parse("https://graph.facebook.com/oauth/access_token?client_id=#{@app.app_id}&redirect_uri=#{@app.connect_url}?verifier=#{verifier}&client_secret=#{@app.secret}&code=#{CGI::escape(code)}")
        http = Net::HTTP.new(uri.host, uri.port)
        http.use_ssl = true

        request = Net::HTTP::Get.new(uri.path + "?" + uri.query)
        response = http.request(request)     
        data = response.body

        return data.split("=")[1]
      end

      # get, post
      def get(path, params = nil)
        uri = URI.parse("https://graph.facebook.com/" + path)
        http = Net::HTTP.new(uri.host, uri.port)
        http.use_ssl = true

        if params.nil?
          params = Hash.new
        end

        if params["access_token"].nil? 
          params["access_token"] = @access_token unless @access_token.nil?
        end

        request = Net::HTTP::Get.new(uri.path) 
        request.set_form_data( params )
        request = Net::HTTP::Get.new(uri.path + "?" + request.body)

        return response = http.request(request)
      end

      def post(path, params = nil)
        uri = URI.parse("https://graph.facebook.com/" + path)
        http = Net::HTTP.new(uri.host, uri.port)
        http.use_ssl = true        

        if params.nil?
          params = Hash.new
        end

        if params[:access_token].nil?
          params[:access_token] = @access_token unless @access_token.nil?
        end

        request = Net::HTTP::Post.new(uri.path) 
        request.set_form_data( params )
        request = Net::HTTP::Post.new(uri.path + "?" + request.body)

        response = http.request(request)
        response.code == "200" ? feed = JSON.parse(response.body) : raise("Sorry, an error occured. #{response.body}")
        return feed
      end
    end

I am sure someone more experienced than I could improve this - I was about 10 weeks into learning Ruby (and my first programming since Fortran and Pascal at university in the early 90s!).


I also had problems getting the devise+Omniauth solution to work. I had to problems:

  1. The session cookie did not store the facebook authentication token that is necessary to initialize fb_graph and koala.
  2. I was unable to initialize fb_graph after getting the facebook authentication token in place (but got Koala to work after some work).

I solved #1 by inserting 'session[:omniauth] = omniauth' into the create method of the authentications_controller.rb.

I solved #2 by using Koala. Seem like fb_graph requires oauth2, and the devise omniauth integration use oauth. Koala works with perfectly with the facebook authentication token stored by session[:omniauth]["credentials"]["token"].

You initialize koala like this:
- @fbprofile = Koala::Facebook::GraphAPI.new( session[:omniauth]["credentials"]["token"] )


I made sure oauth and oauth2 were uninstalled, and then I installed oauth2. It appears that now omniauth and fb_graph are working ... but probably need to test it more.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜