mojodna-oauth 0.3.1.6 → 0.3.1.7

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/History.txt CHANGED
@@ -1,11 +1,16 @@
1
1
  == 0.3.2
2
2
 
3
+ * 2xx statuses should be treated as success (Anders Conbere)
4
+ * Support applications using the MethodOverride Rack middleware (László Bácsi)
5
+ * `authorize` command for `oauth` CLI (Seth)
6
+ * Initial support for Problem Reporting extension (Seth)
7
+ * Verify SSL certificates if CA certificates are available (Seth)
3
8
  * Fixed ActionController parameter escaping behavior (Thiago Arrais, László
4
9
  Bácsi, Brett Gibson, et al)
5
10
  * Fixed signature calculation when both options and a block were provided to
6
- OAuth::Signature::Base#initialize. (Seth)
7
- * Added help to the 'oauth' CLI. (Seth)
8
- * Fixed a problem when attempting to normalize MockRequest URIs. (Seth)
11
+ OAuth::Signature::Base#initialize (Seth)
12
+ * Added help to the 'oauth' CLI (Seth)
13
+ * Fixed a problem when attempting to normalize MockRequest URIs (Seth)
9
14
 
10
15
  == 0.3.1 2009-1-26
11
16
 
data/Manifest.txt CHANGED
@@ -14,6 +14,10 @@ lib/oauth/client/action_controller_request.rb
14
14
  lib/oauth/client/helper.rb
15
15
  lib/oauth/client/net_http.rb
16
16
  lib/oauth/consumer.rb
17
+ lib/oauth/errors.rb
18
+ lib/oauth/errors/error.rb
19
+ lib/oauth/errors/problem.rb
20
+ lib/oauth/errors/unauthorized.rb
17
21
  lib/oauth/helper.rb
18
22
  lib/oauth/oauth_test_helper.rb
19
23
  lib/oauth/request_proxy.rb
data/bin/oauth CHANGED
@@ -2,4 +2,4 @@
2
2
 
3
3
  require "oauth/cli"
4
4
 
5
- OAuth::CLI.execute(STDOUT, ARGV)
5
+ OAuth::CLI.execute(STDOUT, STDIN, STDERR, ARGV)
data/lib/oauth/cli.rb CHANGED
@@ -4,24 +4,32 @@ require 'oauth'
4
4
  module OAuth
5
5
  class CLI
6
6
  SUPPORTED_COMMANDS = {
7
- "debug" => "Verbosely generate an OAuth signature",
8
- "sign" => "Generate an OAuth signature"
7
+ "authorize" => "Obtain an access token and secret for a user",
8
+ "debug" => "Verbosely generate an OAuth signature",
9
+ "sign" => "Generate an OAuth signature"
9
10
  }
10
11
 
11
12
  attr_reader :command
12
13
  attr_reader :options
13
- attr_reader :stdout
14
+ attr_reader :stdout, :stdin
14
15
 
15
- def self.execute(stdout, arguments = [])
16
- self.new.execute(stdout, arguments)
16
+ def self.execute(stdout, stdin, stderr, arguments = [])
17
+ self.new.execute(stdout, stdin, stderr, arguments)
17
18
  end
18
19
 
19
20
  def initialize
20
21
  @options = {}
22
+
23
+ # don't dump a backtrace on a ^C
24
+ trap(:INT) {
25
+ exit
26
+ }
21
27
  end
22
28
 
23
- def execute(stdout, arguments = [])
29
+ def execute(stdout, stdin, stderr, arguments = [])
24
30
  @stdout = stdout
31
+ @stdin = stdin
32
+ @stderr = stderr
25
33
  extract_command_and_parse_options(arguments)
26
34
 
27
35
  if sufficient_options? && valid_command?
@@ -31,6 +39,40 @@ module OAuth
31
39
  end
32
40
 
33
41
  case command
42
+ # TODO move command logic elsewhere
43
+ when "authorize"
44
+ # Y! token authority requires realm=yahoo.com when headers are in use
45
+ # TODO remove :scheme when that's been fixed
46
+ # TODO determine endpoints w/ X-RDS-Simple
47
+ consumer = OAuth::Consumer.new \
48
+ options[:oauth_consumer_key],
49
+ options[:oauth_consumer_secret],
50
+ :access_token_url => options[:access_token_url],
51
+ :authorize_url => options[:authorize_url],
52
+ :request_token_url => options[:request_token_url],
53
+ :scheme => :query_string
54
+
55
+ # get a request token
56
+ request_token = consumer.get_request_token
57
+
58
+ stdout.puts "Please visit this url to authorize:"
59
+ stdout.puts request_token.authorize_url
60
+
61
+ stdout.puts "Press return to continue..."
62
+ stdin.gets
63
+
64
+ begin
65
+ # get an access token
66
+ access_token = request_token.get_access_token
67
+
68
+ stdout.puts "Response:"
69
+ access_token.params.each do |k,v|
70
+ stdout.puts " #{k}: #{v}"
71
+ end
72
+ rescue OAuth::Unauthorized => e
73
+ stderr.puts "A problem occurred while attempting to obtain an access token:"
74
+ stderr.puts e
75
+ end
34
76
  when "sign"
35
77
  parameters = prepare_parameters
36
78
 
@@ -116,6 +158,8 @@ module OAuth
116
158
  options[:oauth_version] = "1.0"
117
159
  options[:params] = []
118
160
 
161
+ ## Common Options
162
+
119
163
  opts.on("--consumer-key KEY", "Specifies the consumer key to use.") do |v|
120
164
  options[:oauth_consumer_key] = v
121
165
  end
@@ -124,6 +168,8 @@ module OAuth
124
168
  options[:oauth_consumer_secret] = v
125
169
  end
126
170
 
171
+ ## Options for signing
172
+
127
173
  opts.on("--method METHOD", "Specifies the method (e.g. GET) to use when signing.") do |v|
128
174
  options[:method] = v
129
175
  end
@@ -176,6 +222,20 @@ module OAuth
176
222
  opts.on("-v", "--verbose", "Be verbose.") do
177
223
  options[:verbose] = true
178
224
  end
225
+
226
+ ## Options for authorization
227
+
228
+ opts.on("--access-token-url URL", "Specifies the access token URL.") do |v|
229
+ options[:access_token_url] = v
230
+ end
231
+
232
+ opts.on("--authorize-url URL", "Specifies the authorization URL.") do |v|
233
+ options[:authorize_url] = v
234
+ end
235
+
236
+ opts.on("--request-token-url URL", "Specifies the request token URL.") do |v|
237
+ options[:request_token_url] = v
238
+ end
179
239
  end
180
240
  end
181
241
 
@@ -208,7 +268,16 @@ module OAuth
208
268
  end
209
269
 
210
270
  def sufficient_options?
211
- options[:oauth_consumer_key] && options[:oauth_consumer_secret] && options[:method] && options[:uri]
271
+ case command
272
+ # TODO move command logic elsewhere
273
+ when "authorize"
274
+ options[:oauth_consumer_key] && options[:oauth_consumer_secret] &&
275
+ options[:access_token_url] && options[:authorize_url] &&
276
+ options[:request_token_url]
277
+ else
278
+ options[:oauth_consumer_key] && options[:oauth_consumer_secret] &&
279
+ options[:method] && options[:uri]
280
+ end
212
281
  end
213
282
 
214
283
  def usage
@@ -5,6 +5,8 @@ require 'oauth/request_proxy/net_http'
5
5
  class Net::HTTPRequest
6
6
  include OAuth::Helper
7
7
 
8
+ attr_reader :oauth_helper
9
+
8
10
  def oauth!(http, consumer = nil, token = nil, options = {})
9
11
  options = { :request_uri => oauth_full_request_uri(http),
10
12
  :consumer => consumer,
@@ -30,10 +32,6 @@ class Net::HTTPRequest
30
32
  OAuth::Client::Helper.new(self, options).signature_base_string
31
33
  end
32
34
 
33
- def oauth_helper
34
- @oauth_helper
35
- end
36
-
37
35
  private
38
36
 
39
37
  def oauth_full_request_uri(http)
@@ -67,7 +65,7 @@ private
67
65
  oauth_params_str = @oauth_helper.oauth_parameters.map { |k,v| [escape(k), escape(v)] * "=" }.join("&")
68
66
 
69
67
  uri = URI.parse(path)
70
- if !uri.query || uri.query == ''
68
+ if uri.query.to_s == ""
71
69
  uri.query = oauth_params_str
72
70
  else
73
71
  uri.query = uri.query + "&" + oauth_params_str
@@ -75,6 +73,6 @@ private
75
73
 
76
74
  @path = uri.to_s
77
75
 
78
- @path << "&oauth_signature=#{escape(@oauth_helper.signature)}"
76
+ @path << "&oauth_signature=#{escape(oauth_helper.signature)}"
79
77
  end
80
78
  end
@@ -1,8 +1,19 @@
1
1
  require 'net/http'
2
2
  require 'net/https'
3
3
  require 'oauth/client/net_http'
4
+ require 'oauth/errors'
5
+
4
6
  module OAuth
5
7
  class Consumer
8
+ # determine the certificate authority path to verify SSL certs
9
+ CA_FILES = %w(/etc/ssl/certs/ca-certificates.crt /usr/share/curl/curl-ca-bundle.crt)
10
+ CA_FILES.each do |ca_file|
11
+ if File.exists?(ca_file)
12
+ CA_FILE = ca_file
13
+ break
14
+ end
15
+ end
16
+ CA_FILE = nil unless defined?(CA_FILE)
6
17
 
7
18
  @@default_options = {
8
19
  # Signature method used by server. Defaults to HMAC-SHA1
@@ -102,20 +113,39 @@ module OAuth
102
113
  # @consumer.request(:post, '/people', @token, {}, @person.to_xml, { 'Content-Type' => 'application/xml' })
103
114
  #
104
115
  def request(http_method, path, token = nil, request_options = {}, *arguments)
105
- if path =~ /^\//
106
- _http = http
107
- else
108
- _http = create_http(path)
116
+ if path !~ /^\//
117
+ @http = create_http(path)
109
118
  _uri = URI.parse(path)
110
119
  path = "#{_uri.path}#{_uri.query ? "?#{_uri.query}" : ""}"
111
120
  end
112
121
 
113
- _http.request(create_signed_request(http_method, path, token, request_options, *arguments))
122
+ rsp = http.request(create_signed_request(http_method, path, token, request_options, *arguments))
123
+
124
+ # check for an error reported by the Problem Reporting extension
125
+ # (http://wiki.oauth.net/ProblemReporting)
126
+ # note: a 200 may actually be an error; check for an oauth_problem key to be sure
127
+ if !(headers = rsp.to_hash["www-authenticate"]).nil? &&
128
+ (h = headers.select { |h| h =~ /^OAuth / }).any? &&
129
+ h.first =~ /oauth_problem/
130
+
131
+ # puts "Header: #{h.first}"
132
+
133
+ # TODO doesn't handle broken responses from api.login.yahoo.com
134
+ # remove debug code when done
135
+ params = OAuth::Helper.parse_header(h.first)
136
+
137
+ # puts "Params: #{params.inspect}"
138
+ # puts "Body: #{rsp.body}"
139
+
140
+ raise OAuth::Problem.new(params.delete("oauth_problem"), rsp, params)
141
+ end
142
+
143
+ rsp
114
144
  end
115
145
 
116
146
  # Creates and signs an http request.
117
147
  # It's recommended to use the Token classes to set this up correctly
118
- def create_signed_request(http_method, path, token = nil,request_options = {}, *arguments)
148
+ def create_signed_request(http_method, path, token = nil, request_options = {}, *arguments)
119
149
  request = create_http_request(http_method, path, *arguments)
120
150
  sign!(request, token, request_options)
121
151
  request
@@ -124,20 +154,28 @@ module OAuth
124
154
  # Creates a request and parses the result as url_encoded. This is used internally for the RequestToken and AccessToken requests.
125
155
  def token_request(http_method, path, token = nil, request_options = {}, *arguments)
126
156
  response = request(http_method, path, token, request_options, *arguments)
127
- if response.code == "200"
157
+
158
+ case response.code.to_i
159
+
160
+ when (200..299)
128
161
  CGI.parse(response.body).inject({}) { |h,(k,v)| h[k.to_sym] = v.first; h }
162
+ when (300..399)
163
+ # this is a redirect
164
+ response.error!
165
+ when (400..499)
166
+ raise OAuth::Unauthorized, response
129
167
  else
130
168
  response.error!
131
169
  end
132
170
  end
133
171
 
134
172
  # Sign the Request object. Use this if you have an externally generated http request object you want to sign.
135
- def sign!(request, token=nil, request_options = {})
173
+ def sign!(request, token = nil, request_options = {})
136
174
  request.oauth!(http, self, token, options.merge(request_options))
137
175
  end
138
176
 
139
177
  # Return the signature_base_string
140
- def signature_base_string(request, token=nil, request_options = {})
178
+ def signature_base_string(request, token = nil, request_options = {})
141
179
  request.signature_base_string(http, self, token, options.merge(request_options))
142
180
  end
143
181
 
@@ -167,7 +205,7 @@ module OAuth
167
205
  end
168
206
 
169
207
  def request_token_url?
170
- @options[:request_token_url]!=nil
208
+ @options.has_key?(:request_token_url)
171
209
  end
172
210
 
173
211
  def authorize_url
@@ -175,7 +213,7 @@ module OAuth
175
213
  end
176
214
 
177
215
  def authorize_url?
178
- @options[:authorize_url]!=nil
216
+ @options.has_key?(:authorize_url)
179
217
  end
180
218
 
181
219
  def access_token_url
@@ -183,7 +221,7 @@ module OAuth
183
221
  end
184
222
 
185
223
  def access_token_url?
186
- @options[:access_token_url]!=nil
224
+ @options.has_key?(:access_token_url)
187
225
  end
188
226
 
189
227
  protected
@@ -197,7 +235,16 @@ module OAuth
197
235
  end
198
236
 
199
237
  http_object = Net::HTTP.new(our_uri.host, our_uri.port)
200
- http_object.use_ssl = true if our_uri.scheme == "https"
238
+
239
+ http_object.use_ssl = (our_uri.scheme == 'https')
240
+
241
+ if CA_FILE
242
+ http_object.ca_file = CA_FILE
243
+ http_object.verify_mode = OpenSSL::SSL::VERIFY_PEER
244
+ http_object.verify_depth = 5
245
+ else
246
+ http_object.verify_mode = OpenSSL::SSL::VERIFY_NONE
247
+ end
201
248
 
202
249
  http_object
203
250
  end
@@ -1,4 +1,3 @@
1
- require 'rubygems'
2
1
  require 'active_support'
3
2
  require 'action_controller/request'
4
3
  require 'oauth/request_proxy/base'
@@ -7,7 +7,7 @@ module OAuth::RequestProxy
7
7
  proxies Rack::Request
8
8
 
9
9
  def method
10
- request.request_method
10
+ request.env["rack.methodoverride.original_method"] || request.request_method
11
11
  end
12
12
 
13
13
  def uri
@@ -37,4 +37,4 @@ module OAuth::RequestProxy
37
37
  request.params
38
38
  end
39
39
  end
40
- end
40
+ end
@@ -1,5 +1,4 @@
1
1
  require 'oauth/signature/hmac/base'
2
- require 'rubygems'
3
2
  require 'hmac-sha1'
4
3
 
5
4
  module OAuth::Signature::HMAC
data/lib/oauth/version.rb CHANGED
@@ -1,3 +1,3 @@
1
1
  module OAuth #:nodoc:
2
- VERSION = '0.3.1.6'
2
+ VERSION = '0.3.1.7'
3
3
  end
data/oauth.gemspec CHANGED
@@ -2,11 +2,11 @@
2
2
 
3
3
  Gem::Specification.new do |s|
4
4
  s.name = %q{oauth}
5
- s.version = "0.3.1.6"
5
+ s.version = "0.3.1.7"
6
6
 
7
7
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
8
8
  s.authors = ["Pelle Braendgaard", "Blaine Cook", "Larry Halff", "Jesse Clark", "Jon Crosby", "Seth Fitzsimmons"]
9
- s.date = %q{2009-02-11}
9
+ s.date = %q{2009-03-02}
10
10
  s.default_executable = %q{oauth}
11
11
  s.description = %q{OAuth Core Ruby implementation}
12
12
  s.email = %q{pelleb@gmail.com}
@@ -143,7 +143,7 @@ class ConsumerTest < Test::Unit::TestCase
143
143
 
144
144
  assert_equal 'POST', request.method
145
145
  assert_equal '/test', request.path
146
- assert_equal "key=value&oauth_consumer_key=consumer_key_86cad9&oauth_nonce=225579211881198842005988698334675835446&oauth_signature=iMZaUTbQof%2fHMFyIde%2bOIkhW5is%3d&oauth_signature_method=HMAC-SHA1&oauth_timestamp=1199645624&oauth_token=token_411a7f&oauth_version=1.0", request.body.split("&").sort.join("&")
146
+ assert_equal "key=value&oauth_consumer_key=consumer_key_86cad9&oauth_nonce=225579211881198842005988698334675835446&oauth_signature=26g7wHTtNO6ZWJaLltcueppHYiI%3d&oauth_signature_method=HMAC-SHA1&oauth_timestamp=1199645624&oauth_token=token_411a7f&oauth_version=1.0", request.body.split("&").sort.join("&")
147
147
  assert_equal nil, request['authorization']
148
148
  end
149
149
 
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: mojodna-oauth
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.3.1.6
4
+ version: 0.3.1.7
5
5
  platform: ruby
6
6
  authors:
7
7
  - Pelle Braendgaard
@@ -14,11 +14,12 @@ autorequire:
14
14
  bindir: bin
15
15
  cert_chain: []
16
16
 
17
- date: 2009-02-11 00:00:00 -08:00
17
+ date: 2009-03-02 00:00:00 -08:00
18
18
  default_executable: oauth
19
19
  dependencies:
20
20
  - !ruby/object:Gem::Dependency
21
21
  name: ruby-hmac
22
+ type: :runtime
22
23
  version_requirement:
23
24
  version_requirements: !ruby/object:Gem::Requirement
24
25
  requirements:
@@ -28,6 +29,7 @@ dependencies:
28
29
  version:
29
30
  - !ruby/object:Gem::Dependency
30
31
  name: newgem
32
+ type: :development
31
33
  version_requirement:
32
34
  version_requirements: !ruby/object:Gem::Requirement
33
35
  requirements:
@@ -37,6 +39,7 @@ dependencies:
37
39
  version:
38
40
  - !ruby/object:Gem::Dependency
39
41
  name: actionpack
42
+ type: :development
40
43
  version_requirement:
41
44
  version_requirements: !ruby/object:Gem::Requirement
42
45
  requirements:
@@ -46,6 +49,7 @@ dependencies:
46
49
  version:
47
50
  - !ruby/object:Gem::Dependency
48
51
  name: rack
52
+ type: :development
49
53
  version_requirement:
50
54
  version_requirements: !ruby/object:Gem::Requirement
51
55
  requirements:
@@ -55,6 +59,7 @@ dependencies:
55
59
  version:
56
60
  - !ruby/object:Gem::Dependency
57
61
  name: hoe
62
+ type: :development
58
63
  version_requirement:
59
64
  version_requirements: !ruby/object:Gem::Requirement
60
65
  requirements: