rest-more 0.7.1 → 0.7.2
Sign up to get free protection for your applications and to get access to all the features.
- data/.travis.yml +2 -1
- data/CHANGES.md +20 -0
- data/Gemfile +5 -1
- data/README.md +26 -0
- data/bin/rib-rest-core +22 -0
- data/example/rails2/Gemfile +1 -0
- data/example/rails2/app/views/application/helper.html.erb +1 -1
- data/example/rails2/config/environment.rb +10 -0
- data/example/rails2/config/rest-core.yaml +2 -2
- data/example/rails2/test/functional/application_controller_test.rb +3 -3
- data/example/rails2/test/unit/rails_util_test.rb +12 -7
- data/example/rails3/Gemfile +1 -0
- data/example/rails3/app/views/application/helper.html.erb +1 -1
- data/example/rails3/config/rest-core.yaml +2 -2
- data/example/rails3/test/functional/application_controller_test.rb +3 -3
- data/example/rails3/test/unit/rails_util_test.rb +12 -7
- data/lib/rest-core/client/bing.rb +92 -0
- data/lib/rest-core/client/bing/rails_util.rb +13 -0
- data/lib/rest-core/client/facebook.rb +2 -2
- data/lib/rest-core/client/facebook/rails_util.rb +28 -65
- data/lib/rest-core/client/flurry.rb +3 -3
- data/lib/rest-core/client/flurry/rails_util.rb +3 -64
- data/lib/rest-core/client/github.rb +3 -0
- data/lib/rest-core/client/github/rails_util.rb +13 -0
- data/lib/rest-core/client/linkedin.rb +2 -0
- data/lib/rest-core/client/linkedin/rails_util.rb +13 -0
- data/lib/rest-core/client/mixi.rb +2 -0
- data/lib/rest-core/client/mixi/rails_util.rb +13 -0
- data/lib/rest-core/client/twitter.rb +2 -0
- data/lib/rest-core/client/twitter/rails_util.rb +13 -0
- data/lib/rest-core/util/rails_util_util.rb +112 -5
- data/lib/rest-more.rb +4 -3
- data/lib/rest-more/version.rb +1 -1
- data/lib/rib/app/rest-core.rb +15 -0
- data/rest-more.gemspec +13 -4
- data/test/client/bing/test_api.rb +34 -0
- data/test/client/facebook/test_api.rb +12 -12
- data/test/client/facebook/test_cache.rb +3 -3
- data/test/client/facebook/test_default.rb +5 -5
- data/test/client/facebook/test_error.rb +25 -25
- data/test/client/facebook/test_handler.rb +12 -12
- data/test/client/facebook/test_load_config.rb +4 -4
- data/test/client/facebook/test_misc.rb +16 -16
- data/test/client/facebook/test_oauth.rb +3 -3
- data/test/client/facebook/test_old.rb +11 -11
- data/test/client/facebook/test_page.rb +4 -4
- data/test/client/facebook/test_parse.rb +14 -14
- data/test/client/facebook/test_serialize.rb +4 -4
- data/test/client/facebook/test_timeout.rb +4 -4
- data/test/client/flurry/test_metrics.rb +1 -1
- data/test/client/twitter/test_api.rb +1 -1
- metadata +16 -7
- data/lib/rest-core/client/simple.rb +0 -2
- data/lib/rest-core/client/universal.rb +0 -18
data/.travis.yml
CHANGED
data/CHANGES.md
CHANGED
@@ -1,5 +1,25 @@
|
|
1
1
|
# CHANGES
|
2
2
|
|
3
|
+
## rest-more 0.7.2 -- 2011-11-05
|
4
|
+
|
5
|
+
### Incompatible changes
|
6
|
+
|
7
|
+
* [Flurry] renamed `api_key` to `apiKey` to better match the original name
|
8
|
+
from flurry. Also renamed `access_code` to `apiAccessCode`.
|
9
|
+
* [Facebook::RailsUtil] Some `module_function`s are changed to controller's
|
10
|
+
private methods. You aren't using it if you don't know what does this mean.
|
11
|
+
|
12
|
+
### Enhancement
|
13
|
+
|
14
|
+
* Added `rib-rest-core` command line tool, extracted from rest-core.
|
15
|
+
* [RailsUtilUtil] Introduced this to ease the pain writing RailsUtil for
|
16
|
+
various clients.
|
17
|
+
* [Bing] Added Bing client and its RailsUtil.
|
18
|
+
* [Github] Added RailsUtil for Github client.
|
19
|
+
* [Linkedin] Added RailsUtil for Linkedin client.
|
20
|
+
* [Mixi] Added RailsUtil for Mixi client.
|
21
|
+
* [Twitter] Added RailsUtil for Twitter client.
|
22
|
+
|
3
23
|
## rest-more 0.7.1 -- 2011-10-31
|
4
24
|
|
5
25
|
### Bugs fixes
|
data/Gemfile
CHANGED
@@ -1,7 +1,11 @@
|
|
1
1
|
|
2
2
|
source 'http://rubygems.org'
|
3
3
|
|
4
|
-
|
4
|
+
# this is for travis-ci
|
5
|
+
gem 'rest-core', :path => 'rest-core' if
|
6
|
+
File.exist?("#{File.dirname(File.expand_path(__FILE__))}/rest-core/Gemfile")
|
7
|
+
gem 'rest-client'
|
8
|
+
gem 'rest-more', :path => '.'
|
5
9
|
|
6
10
|
gem 'rake'
|
7
11
|
gem 'bacon'
|
data/README.md
CHANGED
@@ -48,6 +48,32 @@ See [example][] for more complex examples.
|
|
48
48
|
|
49
49
|
[example]: https://github.com/cardinalblue/rest-more/tree/master/example
|
50
50
|
|
51
|
+
## List of supported clients:
|
52
|
+
|
53
|
+
* Bing
|
54
|
+
* Facebook
|
55
|
+
* Flurry
|
56
|
+
* Github
|
57
|
+
* Linkedin
|
58
|
+
* Mixi
|
59
|
+
* Twitter
|
60
|
+
|
61
|
+
## A simple interactive shell with [rib][]:
|
62
|
+
|
63
|
+
You need to install [rib][] in order to try this interactive shell:
|
64
|
+
|
65
|
+
gem install rib
|
66
|
+
|
67
|
+
Then you can try this by running `rib rest-core`:
|
68
|
+
|
69
|
+
rest-core>> self.site = 'https://api.github.com/users/'
|
70
|
+
rest-core>> self.json_decode = true
|
71
|
+
rest-core>> get 'cardinalblue'
|
72
|
+
|
73
|
+
Which is using `RestCore::Universal` for accessing arbitrary websites.
|
74
|
+
|
75
|
+
[rib]: https://github.com/godfat/rib
|
76
|
+
|
51
77
|
## rest-more users:
|
52
78
|
|
53
79
|
* [s2sync](https://github.com/brucehsu/s2sync)
|
data/bin/rib-rest-core
ADDED
@@ -0,0 +1,22 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
begin
|
4
|
+
require 'rib/runner'
|
5
|
+
# create the shell before app to prvent your bundler (if any) kicks in
|
6
|
+
Rib.shell
|
7
|
+
# we need to require anything before loading the app,
|
8
|
+
# and both `rib auto` (true) and `rib-auto` (nil) should work
|
9
|
+
require 'rib/core' if Rib.config.delete(:mimic_irb) != false
|
10
|
+
require 'rib/app/rest-core'
|
11
|
+
# load the app
|
12
|
+
Rib::RestCore.load
|
13
|
+
Rib::Runner.run(ARGV)
|
14
|
+
rescue LoadError => e
|
15
|
+
abort("Error: #{e}\n" \
|
16
|
+
"Please install rib to use interactive rest-core:\n\n" \
|
17
|
+
" gem install rib\n\n" \
|
18
|
+
"Or add rib or rest-core to Gemfile if that's the case")
|
19
|
+
end
|
20
|
+
|
21
|
+
__END__
|
22
|
+
Run as interactive rest-core client
|
data/example/rails2/Gemfile
CHANGED
@@ -1,2 +1,2 @@
|
|
1
1
|
<%= rc_facebook.app_id %>
|
2
|
-
<%= rc_flurry .
|
2
|
+
<%= rc_flurry .apiKey %>
|
@@ -3,6 +3,16 @@
|
|
3
3
|
# Specifies gem version of Rails to use when vendor/rails is not present
|
4
4
|
RAILS_GEM_VERSION = '2.3.14' unless defined? RAILS_GEM_VERSION
|
5
5
|
|
6
|
+
# monkey patch from https://github.com/rails/rails/pull/3473
|
7
|
+
class MissingSourceFile < LoadError #:nodoc:
|
8
|
+
REGEXPS = [
|
9
|
+
[/^no such file to load -- (.+)$/i, 1],
|
10
|
+
[/^Missing \w+ (file\s*)?([^\s]+.rb)$/i, 2],
|
11
|
+
[/^Missing API definition file in (.+)$/i, 1],
|
12
|
+
[/^cannot load such file -- (.+)$/i, 1]
|
13
|
+
]
|
14
|
+
end
|
15
|
+
|
6
16
|
# Bootstrap the Rails environment, frameworks, and default configuration
|
7
17
|
require File.join(File.dirname(__FILE__), 'boot')
|
8
18
|
|
@@ -145,7 +145,7 @@ class ApplicationControllerTest < ActionController::TestCase
|
|
145
145
|
stub_request(:get, 'https://graph.facebook.com/me?access_token=wozilla').
|
146
146
|
to_return(:body => '["fireball"]')
|
147
147
|
|
148
|
-
@request.session[
|
148
|
+
@request.session[@controller.send(:rc_facebook_storage_key)] =
|
149
149
|
RestCore::Facebook.new(:access_token => 'wozilla').fbs
|
150
150
|
|
151
151
|
get(:session_)
|
@@ -158,7 +158,7 @@ class ApplicationControllerTest < ActionController::TestCase
|
|
158
158
|
stub_request(:get, 'https://graph.facebook.com/me?access_token=blizzard').
|
159
159
|
to_return(:body => '["yeti"]')
|
160
160
|
|
161
|
-
@request.cookies[
|
161
|
+
@request.cookies[@controller.send(:rc_facebook_storage_key)] =
|
162
162
|
RestCore::Facebook.new(:access_token => 'blizzard').fbs
|
163
163
|
|
164
164
|
get(:cookies_)
|
@@ -182,7 +182,7 @@ class ApplicationControllerTest < ActionController::TestCase
|
|
182
182
|
get(:helper)
|
183
183
|
assert_response :success
|
184
184
|
assert_equal "#{RestCore::Facebook.default_app_id}\n" \
|
185
|
-
"#{RestCore::Flurry .
|
185
|
+
"#{RestCore::Flurry .default_apiKey}",
|
186
186
|
@response.body.strip
|
187
187
|
end
|
188
188
|
|
@@ -6,8 +6,13 @@ class RailsUtilTest < ActiveSupport::TestCase
|
|
6
6
|
include RR::Adapters::TestUnit
|
7
7
|
|
8
8
|
def setup_mock url
|
9
|
-
|
10
|
-
|
9
|
+
@controller = Class.new do
|
10
|
+
def self.helper dummy ; end
|
11
|
+
def self.rescue_from dummy, _; end
|
12
|
+
include RestCore::Facebook::RailsUtil
|
13
|
+
end.new
|
14
|
+
mock(@controller).rc_facebook_in_canvas?{ false }
|
15
|
+
mock(@controller).request{
|
11
16
|
mock(Object.new).url{ url }
|
12
17
|
}
|
13
18
|
end
|
@@ -15,30 +20,30 @@ class RailsUtilTest < ActiveSupport::TestCase
|
|
15
20
|
def test_rest_graph_normalized_request_uri_0
|
16
21
|
setup_mock( 'http://test.com/?code=123&lang=en')
|
17
22
|
assert_equal('http://test.com/?lang=en',
|
18
|
-
|
23
|
+
@controller.send(:rc_facebook_normalized_request_uri))
|
19
24
|
end
|
20
25
|
|
21
26
|
def test_rest_graph_normalized_request_uri_1
|
22
27
|
setup_mock( 'http://test.com/?lang=en&code=123')
|
23
28
|
assert_equal('http://test.com/?lang=en',
|
24
|
-
|
29
|
+
@controller.send(:rc_facebook_normalized_request_uri))
|
25
30
|
end
|
26
31
|
|
27
32
|
def test_rest_graph_normalized_request_uri_2
|
28
33
|
setup_mock( 'http://test.com/?session=abc&lang=en&code=123')
|
29
34
|
assert_equal('http://test.com/?lang=en',
|
30
|
-
|
35
|
+
@controller.send(:rc_facebook_normalized_request_uri))
|
31
36
|
end
|
32
37
|
|
33
38
|
def test_rest_graph_normalized_request_uri_3
|
34
39
|
setup_mock( 'http://test.com/?code=123')
|
35
40
|
assert_equal('http://test.com/',
|
36
|
-
|
41
|
+
@controller.send(:rc_facebook_normalized_request_uri))
|
37
42
|
end
|
38
43
|
|
39
44
|
def test_rest_graph_normalized_request_uri_4
|
40
45
|
setup_mock( 'http://test.com/?signed_request=abc&code=123')
|
41
46
|
assert_equal('http://test.com/',
|
42
|
-
|
47
|
+
@controller.send(:rc_facebook_normalized_request_uri))
|
43
48
|
end
|
44
49
|
end
|
data/example/rails3/Gemfile
CHANGED
@@ -1,2 +1,2 @@
|
|
1
1
|
<%= rc_facebook.app_id %>
|
2
|
-
<%= rc_flurry .
|
2
|
+
<%= rc_flurry .apiKey %>
|
@@ -145,7 +145,7 @@ class ApplicationControllerTest < ActionController::TestCase
|
|
145
145
|
stub_request(:get, 'https://graph.facebook.com/me?access_token=wozilla').
|
146
146
|
to_return(:body => '["fireball"]')
|
147
147
|
|
148
|
-
@request.session[
|
148
|
+
@request.session[@controller.send(:rc_facebook_storage_key)] =
|
149
149
|
RestCore::Facebook.new(:access_token => 'wozilla').fbs
|
150
150
|
|
151
151
|
get(:session_)
|
@@ -158,7 +158,7 @@ class ApplicationControllerTest < ActionController::TestCase
|
|
158
158
|
stub_request(:get, 'https://graph.facebook.com/me?access_token=blizzard').
|
159
159
|
to_return(:body => '["yeti"]')
|
160
160
|
|
161
|
-
@request.cookies[
|
161
|
+
@request.cookies[@controller.send(:rc_facebook_storage_key)] =
|
162
162
|
RestCore::Facebook.new(:access_token => 'blizzard').fbs
|
163
163
|
|
164
164
|
get(:cookies_)
|
@@ -182,7 +182,7 @@ class ApplicationControllerTest < ActionController::TestCase
|
|
182
182
|
get(:helper)
|
183
183
|
assert_response :success
|
184
184
|
assert_equal "#{RestCore::Facebook.default_app_id}\n" \
|
185
|
-
"#{RestCore::Flurry .
|
185
|
+
"#{RestCore::Flurry .default_apiKey}",
|
186
186
|
@response.body.strip
|
187
187
|
end
|
188
188
|
|
@@ -6,8 +6,13 @@ class RailsUtilTest < ActiveSupport::TestCase
|
|
6
6
|
include RR::Adapters::TestUnit
|
7
7
|
|
8
8
|
def setup_mock url
|
9
|
-
|
10
|
-
|
9
|
+
@controller = Class.new do
|
10
|
+
def self.helper dummy ; end
|
11
|
+
def self.rescue_from dummy, _; end
|
12
|
+
include RestCore::Facebook::RailsUtil
|
13
|
+
end.new
|
14
|
+
mock(@controller).rc_facebook_in_canvas?{ false }
|
15
|
+
mock(@controller).request{
|
11
16
|
mock(Object.new).url{ url }
|
12
17
|
}
|
13
18
|
end
|
@@ -15,30 +20,30 @@ class RailsUtilTest < ActiveSupport::TestCase
|
|
15
20
|
def test_rest_graph_normalized_request_uri_0
|
16
21
|
setup_mock( 'http://test.com/?code=123&lang=en')
|
17
22
|
assert_equal('http://test.com/?lang=en',
|
18
|
-
|
23
|
+
@controller.send(:rc_facebook_normalized_request_uri))
|
19
24
|
end
|
20
25
|
|
21
26
|
def test_rest_graph_normalized_request_uri_1
|
22
27
|
setup_mock( 'http://test.com/?lang=en&code=123')
|
23
28
|
assert_equal('http://test.com/?lang=en',
|
24
|
-
|
29
|
+
@controller.send(:rc_facebook_normalized_request_uri))
|
25
30
|
end
|
26
31
|
|
27
32
|
def test_rest_graph_normalized_request_uri_2
|
28
33
|
setup_mock( 'http://test.com/?session=abc&lang=en&code=123')
|
29
34
|
assert_equal('http://test.com/?lang=en',
|
30
|
-
|
35
|
+
@controller.send(:rc_facebook_normalized_request_uri))
|
31
36
|
end
|
32
37
|
|
33
38
|
def test_rest_graph_normalized_request_uri_3
|
34
39
|
setup_mock( 'http://test.com/?code=123')
|
35
40
|
assert_equal('http://test.com/',
|
36
|
-
|
41
|
+
@controller.send(:rc_facebook_normalized_request_uri))
|
37
42
|
end
|
38
43
|
|
39
44
|
def test_rest_graph_normalized_request_uri_4
|
40
45
|
setup_mock( 'http://test.com/?signed_request=abc&code=123')
|
41
46
|
assert_equal('http://test.com/',
|
42
|
-
|
47
|
+
@controller.send(:rc_facebook_normalized_request_uri))
|
43
48
|
end
|
44
49
|
end
|
@@ -0,0 +1,92 @@
|
|
1
|
+
|
2
|
+
require 'rest-core'
|
3
|
+
|
4
|
+
RestCore::Bing = RestCore::Builder.client(:AppId) do
|
5
|
+
s = self.class # this is only for ruby 1.8!
|
6
|
+
use s::Timeout , 10
|
7
|
+
|
8
|
+
use s::DefaultSite , 'http://api.bing.net/json.aspx'
|
9
|
+
use s::DefaultHeaders, {'Accept' => 'application/json'}
|
10
|
+
use s::DefaultQuery , {}
|
11
|
+
|
12
|
+
use s::CommonLogger , nil
|
13
|
+
use s::Cache , nil, 600 do
|
14
|
+
use s::ErrorHandler, lambda{ |env|
|
15
|
+
raise ::RestCore::Bing::Error.call(env) }
|
16
|
+
use s::ErrorDetector, lambda{ |env|
|
17
|
+
if env[s::RESPONSE_BODY].kind_of?(Hash) &&
|
18
|
+
(res = env[s::RESPONSE_BODY]['SearchResponse']).kind_of?(Hash)
|
19
|
+
res['Errors']
|
20
|
+
end}
|
21
|
+
use s::JsonDecode , true
|
22
|
+
end
|
23
|
+
end
|
24
|
+
|
25
|
+
module RestCore::Bing::Client
|
26
|
+
def query
|
27
|
+
{'AppId' => self.AppId,
|
28
|
+
'JsonType' => 'raw' ,
|
29
|
+
'Version' => '2.2' }
|
30
|
+
end
|
31
|
+
|
32
|
+
def search_image term, query={}, opts={}
|
33
|
+
get('', {:Query => term, :Sources => 'Image'}.merge(query), opts)[
|
34
|
+
'SearchResponse']['Image']['Results'] || []
|
35
|
+
end
|
36
|
+
|
37
|
+
def search_image_urls term, query={}, opts={}
|
38
|
+
search_image(term, query, opts).map{ |i| i['MediaUrl'] }
|
39
|
+
end
|
40
|
+
end
|
41
|
+
|
42
|
+
class RestCore::Bing::Error < RestCore::Error
|
43
|
+
include RestCore
|
44
|
+
class MissingParameter < Bing::Error; end
|
45
|
+
class InvalidParameter < Bing::Error; end
|
46
|
+
class QueryTooLong < Bing::Error; end
|
47
|
+
class AppIdNotFunctioning < Bing::Error; end
|
48
|
+
class ExceededLimit < Bing::Error; end
|
49
|
+
class NoAccess < Bing::Error; end
|
50
|
+
class ResultsTemporarilyUnavailable < Bing::Error; end
|
51
|
+
class ServiceTemporarilyUnavailable < Bing::Error; end
|
52
|
+
class SourceTypeError < Bing::Error; end
|
53
|
+
|
54
|
+
attr_reader :error, :url
|
55
|
+
def initialize error, url=''
|
56
|
+
@error, @url = error, url
|
57
|
+
super("#{error.inspect} from #{url}")
|
58
|
+
end
|
59
|
+
|
60
|
+
def self.call env
|
61
|
+
error, url = env[RESPONSE_BODY], Middleware.request_uri(env)
|
62
|
+
code = extract_error_code(error)
|
63
|
+
|
64
|
+
return new(env[FAIL], url) unless code
|
65
|
+
|
66
|
+
case code
|
67
|
+
when 1001; MissingParameter
|
68
|
+
when 1002; InvalidParameter
|
69
|
+
when 1005; QueryTooLong
|
70
|
+
when 2001; AppIdNotFunctioning
|
71
|
+
when 2002; ExceededLimit
|
72
|
+
when 2003; NoAccess
|
73
|
+
when 3001; ResultsTemporarilyUnavailable
|
74
|
+
when 3002; ServiceTemporarilyUnavailable
|
75
|
+
when 4001; SourceTypeError
|
76
|
+
end.new(error, url)
|
77
|
+
end
|
78
|
+
|
79
|
+
def self.extract_error_code error
|
80
|
+
code = error.kind_of?(Hash) &&
|
81
|
+
(error = error['SearchResponse']).kind_of?(Hash) &&
|
82
|
+
(error = error['Errors'] ).kind_of?(Array) &&
|
83
|
+
(error = error[0] ).kind_of?(Hash) &&
|
84
|
+
(error = error['Code'] )
|
85
|
+
|
86
|
+
code && code.to_i
|
87
|
+
end
|
88
|
+
end
|
89
|
+
|
90
|
+
RestCore::Bing.send(:include, RestCore::Bing::Client)
|
91
|
+
require 'rest-core/client/bing/rails_util' if
|
92
|
+
Object.const_defined?(:Rails)
|
@@ -0,0 +1,13 @@
|
|
1
|
+
|
2
|
+
require 'rest-core/util/rails_util_util'
|
3
|
+
|
4
|
+
module RestCore::Bing::DefaultAttributes
|
5
|
+
def default_log_method; Rails.logger.method(:debug); end
|
6
|
+
def default_cache ; Rails.cache ; end
|
7
|
+
end
|
8
|
+
|
9
|
+
module RestCore::Bing::RailsUtil
|
10
|
+
include RestCore::RailsUtilUtil
|
11
|
+
end
|
12
|
+
|
13
|
+
RestCore::Bing::RailsUtil.init(Rails)
|
@@ -132,7 +132,7 @@ module RestCore::Facebook::Client
|
|
132
132
|
def parse_fbs! fbs
|
133
133
|
self.data = check_sig_and_return_data(
|
134
134
|
# take out facebook sometimes there but sometimes not quotes in cookies
|
135
|
-
|
135
|
+
ParseQuery.parse_query(fbs.to_s.sub(/^"/, '').sub(/"$/, '')))
|
136
136
|
end
|
137
137
|
|
138
138
|
def parse_fbsr! fbsr
|
@@ -180,7 +180,7 @@ module RestCore::Facebook::Client
|
|
180
180
|
|
181
181
|
def authorize! opts={}
|
182
182
|
query = {:client_id => app_id, :client_secret => secret}.merge(opts)
|
183
|
-
self.data =
|
183
|
+
self.data = ParseQuery.parse_query(
|
184
184
|
get(url('oauth/access_token'), query,
|
185
185
|
{:json_decode => false}.merge(opts)))
|
186
186
|
end
|