hyper-graph 0.2 → 0.3

Sign up to get free protection for your applications and to get access to all the features.
data/README.md CHANGED
@@ -35,44 +35,51 @@ Usage
35
35
  Supports 'ID' and 'ID/CONNECTION_TYPE' API requests using GET, POST and DELETE. HyperGraph parses the API's JSON response into a Ruby-friendly format.
36
36
  [Read up on the API](http://developers.facebook.com/docs/api) to learn what that means.
37
37
 
38
- Create a graph to store the session key:
38
+ Version 0.3 introduces a new, friendlier HyperGraph API. If you're familiar with previous versions, review the updated API but don't worry: the new API 100% backward compatible.
39
+
40
+ Create a HyperGraph to store your access token:
39
41
  irb > graph = HyperGraph.new('my-access-token')
40
42
  => #<HyperGraph:0x1943b98 @access_token="my-access-token">
41
- irb > graph.get('me')
42
- => {:updated_time=>Wed Mar 17 16:19:03 -0400 2010, :first_name=>"Chris", :last_name=>"Dinn", :name=>"Chris Dinn",
43
- :link=>"http://www.facebook.com/chrisdinn", :timezone=>-4, :birthday=>"05/28/1983", :id=>518018845, :verified=>true}
44
-
45
- Or, make requests directly from HyperGraph, though you'll need an access token for most requests:
46
- irb > HyperGraph.get('518018845')
47
- => {:first_name=>"Chris", :last_name=>"Dinn", :name=>"Chris Dinn", :link=>"http://www.facebook.com/chrisdinn", :id=>518018845}
48
- irb > HyperGraph.get('518018845', :access_token => 'my-access-token')
49
- => {:updated_time=>Wed Mar 17 16:19:03 -0400 2010, :first_name=>"Chris", :last_name=>"Dinn", :name=>"Chris Dinn",
50
- :link=>"http://www.facebook.com/chrisdinn", :timezone=>-4, :birthday=>"05/28/1983", :id=>518018845, :verified=>true}
43
+
44
+ You can load an object and make requests against it:
45
+ irb > me = graph.object(518018845)
46
+ => #<HyperGraphObject:0x1945934 @id="518018845" @access_token="my-access-token">
47
+ You can make connection requests, too:
48
+ irb > me.get(:likes)
49
+ => [{:category=>"Websites", :name=>"Slate.com", :id=>21516776437}]
50
+ irb > graph.object('514569082_115714061789461').post(:comments, :message => 'durian is disgustingly delicious')
51
+ => true
52
+ irb > graph.object('514569082_115714061789461').delete(:likes)
53
+ => true
51
54
 
52
- You can also request connections:
55
+ Or, you can request from the graph directly:
56
+ irb > graph.get('me')
57
+ => {:updated_time=>Wed Mar 17 16:19:03 -0400 2010, :first_name=>"Chris", :last_name=>"Dinn", ...
53
58
  irb > graph.get('me/photos', :limit => 1)
54
- => [{:source=>"http://sphotos.ak.fbcdn.net/hphotos-ak-snc3/hs239.snc3/22675_248026512444_511872444_3217612_4249159_n.jpg",
55
- :picture=>"http://photos-b.ak.fbcdn.net/hphotos-ak-snc3/hs239.snc3/22675_248026512444_511872444_3217612_4249159_s.jpg",
56
- :updated_time=>Sun Jan 10 18:06:36 -0500 2010, :from=>{:name=>"Jennifer Byrne", :id=>511872444},
57
- :name=>"Finally a day off....xmas dinner, a few days late", :link=>"http://www.facebook.com/photo.php?pid=3217612&id=511872444",
58
- :icon=>"http://static.ak.fbcdn.net/rsrc.php/z2E5Y/hash/8as8iqdm.gif", :tags=>[{:name=>"Chris Dinn", :y=>15.3846,
59
- :created_time=>Sun Jan 10 18:06:41 -0500 2010, :id=>518018845, :x=>83.8889}], :created_time=>Sun Jan 10 18:00:10 -0500 2010,
60
- :id=>248026512444, :width=>604, :height=>483}]
61
-
62
- Similarly, make a post or delete request:
63
- irb > graph.post('514569082_115714061789461/likes')
59
+ => [{:source=>"http://sphotos.ak.fbcdn.net/hphotos-a...
60
+
61
+ Similarly, make a post or delete request directly from the graph:
62
+ irb > graph.post('514569082_115714061789461/likes')
64
63
  => true
65
- irb > graph.post('514569082_115714061789461/comments', :message => 'durian is disgustingly delicious')
64
+ irb > graph.post('514569082_115714061789461/comments', :message => 'durian is disgustingly delicious')
66
65
  => true
67
- irb > graph.delete('514569082_115714061789461/likes')
66
+ irb > graph.delete('514569082_115714061789461/likes')
68
67
  => true
68
+
69
+ As well, you can make requests directly from HyperGraph, with or without an access token (though you'll need an access token for most requests):
70
+ irb > HyperGraph.get('518018845')
71
+ => {:first_name=>"Chris", :last_name=>"Dinn", :name=>"Chris Dinn", ...
72
+ irb > HyperGraph.get('518018845', :access_token => 'my-access-token')
73
+ => {:updated_time=>Wed Mar 17 16:19:03 -0400 2010, :first_name=>"Chris", :last_name=>"Dinn", ...
74
+
75
+ HyperGraph tries to convert `id` values into integers when possible, for easy database storage. When that's not possible, the `id` will be returned as a string. Values representing a date are converted into Time objects.
69
76
 
70
- When parsing the response, time variables are converted into Time objects and IDs are converted to integers. Note that paging information is discarded from requests that return an array, so be sure to manage paging manually.
77
+ Note that paging information is discarded from requests that return an array, so be sure to manage paging manually.
71
78
 
72
79
  Problems/Bugs/Requests
73
80
  -----------------------------
74
81
 
75
- Please, file an issue.
82
+ Please, file an issue.
76
83
 
77
84
  Note on Patches/Pull Requests
78
85
  -----------------------------
data/lib/hyper_graph.rb CHANGED
@@ -2,6 +2,7 @@ require 'net/http'
2
2
  require 'net/https'
3
3
  require 'time'
4
4
  require 'json'
5
+ require 'hyper_graph_object'
5
6
 
6
7
  # Wrapper for errors generated by the Facebook Graph API server
7
8
  class FacebookError<StandardError;end
@@ -92,7 +93,11 @@ class HyperGraph
92
93
  when "error"
93
94
  raise FacebookError.new("#{v['type']} - #{v['message']}")
94
95
  when "id"
95
- normalized_hash[k.to_sym] = v.to_i
96
+ if (v.to_i == v.to_s.to_i)
97
+ normalized_hash[k.to_sym] = v.to_i
98
+ else
99
+ normalized_hash[k.to_sym] = v
100
+ end
96
101
  when /_time$/
97
102
  normalized_hash[k.to_sym] = Time.parse(v)
98
103
  else
@@ -111,7 +116,13 @@ class HyperGraph
111
116
  end
112
117
 
113
118
  def normalize_array(array)
114
- array.collect{ |item| normalize_response(item) }.sort{ |a, b| a[:id] <=> b[:id] }
119
+ array.collect{ |item| normalize_response(item) }.sort do |a, b|
120
+ if a[:id] && b[:id]
121
+ a[:id] <=> b[:id]
122
+ elsif a[:name]&&b[:name]
123
+ a[:name] <=> b[:name]
124
+ end
125
+ end
115
126
  end
116
127
 
117
128
  # Extracts data from "data" key in Hash, if present
@@ -129,6 +140,10 @@ class HyperGraph
129
140
  @access_token = access_token
130
141
  end
131
142
 
143
+ def object(id)
144
+ HyperGraphObject.new(self, id)
145
+ end
146
+
132
147
  def get(requested_object_id, options = {})
133
148
  self.class.get(requested_object_id, options.merge(:access_token => @access_token))
134
149
  end
@@ -0,0 +1,25 @@
1
+ class HyperGraphObject
2
+
3
+ def initialize(graph, id)
4
+ @graph = graph
5
+ @id = id
6
+ end
7
+
8
+ def get(connection=nil, options={})
9
+ request = @id.to_s
10
+ request += "/#{connection.to_s}" if connection
11
+ @graph.get(request, options)
12
+ end
13
+
14
+ def post(connection=nil, options={})
15
+ request = @id.to_s
16
+ request += "/#{connection.to_s}" if connection
17
+ @graph.post(request, options)
18
+ end
19
+
20
+ def delete(connection=nil, options={})
21
+ request = @id.to_s
22
+ request += "/#{connection.to_s}" if connection
23
+ @graph.delete(request, options)
24
+ end
25
+ end
@@ -0,0 +1,89 @@
1
+ require 'test_helper'
2
+
3
+ class HyperGraphObjectTest < Test::Unit::TestCase
4
+
5
+ def setup
6
+ @mock_connection = mock('api-connection')
7
+ @mock_connection.stubs(:verify_mode=)
8
+ Net::HTTP.stubs(:new).returns(@mock_connection)
9
+ end
10
+
11
+ def test_get_object
12
+ json_api_response = '{"id":"518018845","name":"Chris Dinn","first_name":"Chris","last_name":"Dinn","link":"http://www.facebook.com/chrisdinn","birthday":"05/28/1983","email":"expected-app-specific-email@proxymail.facebook.com","timezone":-4,"verified":true,"updated_time":"2010-03-17T20:19:03+0000"}'
13
+ expected_parsed_response = { :id => 518018845,
14
+ :name => "Chris Dinn",
15
+ :first_name => "Chris",
16
+ :last_name => "Dinn",
17
+ :link => "http://www.facebook.com/chrisdinn",
18
+ :birthday => "05/28/1983",
19
+ :email => "expected-app-specific-email@proxymail.facebook.com",
20
+ :timezone => -4,
21
+ :verified => true,
22
+ :updated_time => Time.parse("2010-03-17T20:19:03+0000")}
23
+
24
+ access_token = "test-access-token"
25
+ mock_response = stub(:body => json_api_response)
26
+ @mock_connection.expects(:use_ssl=).with(true)
27
+ @mock_connection.stubs(:get).with("/518018845?access_token=#{access_token}").returns(mock_response)
28
+
29
+ graph = HyperGraph.new(access_token)
30
+ graph_object = graph.object(518018845)
31
+
32
+ assert_equal expected_parsed_response, graph_object.get
33
+ end
34
+
35
+ def test_get_object_connection
36
+ json_api_response = '{ "data":[{"name": "Andrew Louis", "id": "28103622"},{"name": "Joey Coleman","id": "72600429"},{"name": "Kathryn Kinley","id": "28125421"},{"name": "Vanessa Larkey", "id": "28112600"}] }'
37
+ expected_sorted_array = [{:name => "Andrew Louis", :id => 28103622},{:name => "Vanessa Larkey", :id => 28112600},{:name => "Kathryn Kinley", :id => 28125421}, {:name => "Joey Coleman", :id => 72600429}]
38
+
39
+ access_token = "test-access-token"
40
+ mock_response = stub(:body => json_api_response)
41
+ @mock_connection.expects(:use_ssl=).with(true)
42
+ @mock_connection.stubs(:get).with("/518018845/friends?access_token=#{access_token}").returns(mock_response)
43
+
44
+ graph = HyperGraph.new(access_token)
45
+ graph_object = graph.object('518018845')
46
+
47
+ assert_equal expected_sorted_array, graph_object.get(:friends)
48
+ end
49
+
50
+ def test_post_request_returning_true
51
+ json_api_response = 'true'
52
+ access_token = "test-access-token"
53
+ mock_response = stub(:body => json_api_response)
54
+ @mock_connection.expects(:use_ssl=).with(true)
55
+ @mock_connection.stubs(:post).with("/115934485101003/maybe", "access_token=#{access_token}").returns(mock_response)
56
+
57
+ graph = HyperGraph.new(access_token)
58
+ object = graph.object(115934485101003)
59
+ assert_equal true, object.post(:maybe)
60
+ end
61
+
62
+ def test_post_request_raising_error
63
+ json_api_response = '{"error":{"type":"Exception","message":"(#210) User not visible"}}'
64
+ access_token = "test-access-token"
65
+ mock_response = stub(:body => json_api_response)
66
+ @mock_connection.expects(:use_ssl=).with(true)
67
+ @mock_connection.stubs(:post).with('/514569082_115714061789461/comments', "access_token=#{access_token}").returns(mock_response)
68
+
69
+ graph = HyperGraph.new(access_token)
70
+ object = graph.object('514569082_115714061789461')
71
+
72
+ assert_raise FacebookError do
73
+ object.post(:comments)
74
+ end
75
+ end
76
+
77
+ def test_delete_request
78
+ json_api_response = 'true'
79
+ access_token = "test-access-token"
80
+ mock_response = stub(:body => json_api_response)
81
+ @mock_connection.expects(:use_ssl=).with(true)
82
+ @mock_connection.stubs(:post).with("/514569082_115714061789461/likes", "access_token=#{access_token}&method=delete").returns(mock_response)
83
+
84
+ graph = HyperGraph.new(access_token)
85
+ object = graph.object('514569082_115714061789461')
86
+
87
+ assert_equal true, object.delete(:likes)
88
+ end
89
+ end
metadata CHANGED
@@ -4,8 +4,8 @@ version: !ruby/object:Gem::Version
4
4
  prerelease: false
5
5
  segments:
6
6
  - 0
7
- - 2
8
- version: "0.2"
7
+ - 3
8
+ version: "0.3"
9
9
  platform: ruby
10
10
  authors:
11
11
  - Chris Dinn
@@ -13,7 +13,7 @@ autorequire:
13
13
  bindir: bin
14
14
  cert_chain: []
15
15
 
16
- date: 2010-04-25 00:00:00 -04:00
16
+ date: 2010-04-29 00:00:00 -04:00
17
17
  default_executable:
18
18
  dependencies:
19
19
  - !ruby/object:Gem::Dependency
@@ -39,6 +39,8 @@ extra_rdoc_files: []
39
39
 
40
40
  files:
41
41
  - lib/hyper_graph.rb
42
+ - lib/hyper_graph_object.rb
43
+ - test/hyper_graph_object_test.rb
42
44
  - test/hyper_graph_test.rb
43
45
  - test/test_helper.rb
44
46
  - LICENSE