facebook-graphclient 0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
data/README ADDED
File without changes
@@ -0,0 +1,24 @@
1
+ spec = Gem::Specification.new do |s|
2
+ s.name = 'facebook-graphclient'
3
+ s.version = '0.1'
4
+ s.date = '2010-04-24'
5
+ s.summary = "A simple library for Facebook's new Graph API"
6
+ s.description = "A bare-bones implementation of Facebook's new Graph API"
7
+
8
+ s.homepage = "http://github.com/jessefarmer/facebook-graphclient"
9
+
10
+ s.authors = ["Jesse Farmer"]
11
+ s.email = "jesse@20bits.com"
12
+
13
+ s.add_dependency('yajl-ruby')
14
+ s.add_dependency('patron')
15
+
16
+ # TODO Remove this dependency
17
+ s.add_dependency('rack')
18
+ s.has_rdoc = false
19
+
20
+ s.files = ["README",
21
+ "facebook-graphclient.gemspec",
22
+ "lib/facebook-graphclient.rb",
23
+ "lib/facebook-graphclient/rails.rb"]
24
+ end
@@ -0,0 +1,132 @@
1
+ class FacebookError < StandardError
2
+ attr_accessor :data
3
+ end
4
+
5
+ require 'digest/md5'
6
+ require 'yajl'
7
+ require 'patron'
8
+ require 'rack'
9
+
10
+ module Facebook
11
+ GRAPH_URL = 'https://graph.facebook.com'
12
+
13
+ class GraphClient
14
+
15
+ attr_reader :secret, :app_id, :api_key
16
+ attr_accessor :access_token
17
+
18
+ def initialize facebook_settings = {}
19
+ @app_id = facebook_settings[:app_id]
20
+ @api_key = facebook_settings[:api_key]
21
+ @secret = facebook_settings[:secret]
22
+
23
+ @cookie = get_user_cookie facebook_settings[:cookies]
24
+
25
+ @access_token = facebook_settings[:access_token] || @cookie['access_token']
26
+
27
+ @session = Patron::Session.new
28
+ end
29
+
30
+ def get_user_cookie cookies
31
+ if cookies and cookie = cookies["fbs_#{@app_id}"]
32
+ Rack::Utils.parse_nested_query(cookie)
33
+ else
34
+ {}
35
+ end
36
+ end
37
+
38
+ %w[get post delete].each do |action|
39
+ class_eval %[
40
+ def #{action} method, params = {}
41
+ self.api '#{action}', method, params
42
+ end
43
+ ]
44
+ end
45
+
46
+ def api action, method, query_params = nil
47
+ query_params[:access_token] ||= @access_token
48
+
49
+ query_string = '?' + query_params.map { |k,v| "#{k}=#{v}" }.join("&") unless query_params.empty?
50
+
51
+ tries = 0
52
+ begin
53
+ raw_response = @session.send(action, GRAPH_URL + method + query_string)
54
+ rescue Patron::HostResolutionError, Patron::ConnectionFailed
55
+ retry if tries < 5
56
+ tries += 1
57
+ end
58
+
59
+ # TODO: Handle photo requests, which return photo data and not JSON
60
+
61
+ if raw_response.headers['Content-Type'] =~ /text\/javascript/
62
+ # We have JSON
63
+ json = ["false", '', nil].include?(raw_response.body) ? '{}' : raw_response.body
64
+ response = Yajl::Parser.parse(json)
65
+
66
+ if e = response['error']
67
+ error = FacebookError.new(e['message'])
68
+ error.data = e
69
+ raise error
70
+ else
71
+ response
72
+ end
73
+ end
74
+ end
75
+
76
+ def fql query
77
+ query_params = {
78
+ :access_token => @access_token,
79
+ :format => 'json',
80
+ :query => Rack::Utils.escape(query)
81
+ }
82
+
83
+ query_string = '?' + query_params.map { |k,v| "#{k}=#{v}" }.join("&") unless query_params.empty?
84
+
85
+ tries = 0
86
+ begin
87
+ raw_response = @session.get("https://api.facebook.com/method/fql.query" + query_string)
88
+ rescue Patron::HostResolutionError, Patron::ConnectionFailed
89
+ retry if tries < 5
90
+ tries += 1
91
+ end
92
+
93
+ json = ["false", '', nil].include?(raw_response.body) ? '{}' : raw_response.body
94
+ response = Yajl::Parser.parse(json)
95
+
96
+ if e = response.first['error']
97
+ error = FacebookError.new(e['message'])
98
+ error.data = e
99
+ raise error
100
+ else
101
+ response
102
+ end
103
+ end
104
+
105
+ def valid?
106
+ return false if @cookie.nil?
107
+
108
+ unless @is_valid
109
+ vars = @cookie.dup
110
+
111
+ good_sig = vars.delete 'sig'
112
+ sig = Digest::MD5.hexdigest(vars.sort.map { |k,v| "#{k}=#{v}" }.compact.join + @secret)
113
+
114
+ if @is_valid = (sig == good_sig)
115
+ @params = vars
116
+ else
117
+ @params = {}
118
+ end
119
+ end
120
+
121
+ @is_valid
122
+ end
123
+
124
+ def [] k
125
+ params[k]
126
+ end
127
+
128
+ def params
129
+ valid? ? @params : {}
130
+ end
131
+ end
132
+ end
@@ -0,0 +1,47 @@
1
+ begin
2
+ require 'action_controller'
3
+ rescue LoadError
4
+ retry if require 'rubygems'
5
+ raise
6
+ end
7
+
8
+ require 'facebook-graphclient'
9
+
10
+ module Facebook
11
+ module RailsFacebookSettings
12
+ def self.extended(klass)
13
+ klass.cattr_accessor :facebook_settings
14
+ klass.facebook_settings = {}
15
+ end
16
+ def facebook(&blk)
17
+ instance_eval(&blk)
18
+ include Facebook::Rails
19
+ end
20
+ %w[ secret app_id api_key access_token ].each do |param|
21
+ class_eval %[
22
+ def #{param} val, &blk
23
+ facebook_settings[:#{param}] = val
24
+ end
25
+ ]
26
+ end
27
+ end
28
+
29
+ module Rails
30
+ def self.included(controller)
31
+ if controller.respond_to?(:helper_method)
32
+ controller.helper_method :fb, :facebook
33
+ end
34
+ end
35
+ def facebook
36
+ unless request.env['facebook.helper']
37
+ fb = Facebook::GraphClient.new(self.class.facebook_settings.merge(:cookies => cookies))
38
+ env['facebook.helper'] = fb
39
+ end
40
+
41
+ env['facebook.helper']
42
+ end
43
+ alias fb facebook
44
+ end
45
+ end
46
+
47
+ ActionController::Base.extend Facebook::RailsFacebookSettings
metadata ADDED
@@ -0,0 +1,99 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: facebook-graphclient
3
+ version: !ruby/object:Gem::Version
4
+ prerelease: false
5
+ segments:
6
+ - 0
7
+ - 1
8
+ version: "0.1"
9
+ platform: ruby
10
+ authors:
11
+ - Jesse Farmer
12
+ autorequire:
13
+ bindir: bin
14
+ cert_chain: []
15
+
16
+ date: 2010-04-24 00:00:00 -07:00
17
+ default_executable:
18
+ dependencies:
19
+ - !ruby/object:Gem::Dependency
20
+ name: yajl-ruby
21
+ prerelease: false
22
+ requirement: &id001 !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - ">="
25
+ - !ruby/object:Gem::Version
26
+ segments:
27
+ - 0
28
+ version: "0"
29
+ type: :runtime
30
+ version_requirements: *id001
31
+ - !ruby/object:Gem::Dependency
32
+ name: patron
33
+ prerelease: false
34
+ requirement: &id002 !ruby/object:Gem::Requirement
35
+ requirements:
36
+ - - ">="
37
+ - !ruby/object:Gem::Version
38
+ segments:
39
+ - 0
40
+ version: "0"
41
+ type: :runtime
42
+ version_requirements: *id002
43
+ - !ruby/object:Gem::Dependency
44
+ name: rack
45
+ prerelease: false
46
+ requirement: &id003 !ruby/object:Gem::Requirement
47
+ requirements:
48
+ - - ">="
49
+ - !ruby/object:Gem::Version
50
+ segments:
51
+ - 0
52
+ version: "0"
53
+ type: :runtime
54
+ version_requirements: *id003
55
+ description: A bare-bones implementation of Facebook's new Graph API
56
+ email: jesse@20bits.com
57
+ executables: []
58
+
59
+ extensions: []
60
+
61
+ extra_rdoc_files: []
62
+
63
+ files:
64
+ - README
65
+ - facebook-graphclient.gemspec
66
+ - lib/facebook-graphclient.rb
67
+ - lib/facebook-graphclient/rails.rb
68
+ has_rdoc: true
69
+ homepage: http://github.com/jessefarmer/facebook-graphclient
70
+ licenses: []
71
+
72
+ post_install_message:
73
+ rdoc_options: []
74
+
75
+ require_paths:
76
+ - lib
77
+ required_ruby_version: !ruby/object:Gem::Requirement
78
+ requirements:
79
+ - - ">="
80
+ - !ruby/object:Gem::Version
81
+ segments:
82
+ - 0
83
+ version: "0"
84
+ required_rubygems_version: !ruby/object:Gem::Requirement
85
+ requirements:
86
+ - - ">="
87
+ - !ruby/object:Gem::Version
88
+ segments:
89
+ - 0
90
+ version: "0"
91
+ requirements: []
92
+
93
+ rubyforge_project:
94
+ rubygems_version: 1.3.6
95
+ signing_key:
96
+ specification_version: 3
97
+ summary: A simple library for Facebook's new Graph API
98
+ test_files: []
99
+