filiptepper-oauth-plugin 0.3.11

Sign up to get free protection for your applications and to get access to all the features.
Files changed (74) hide show
  1. data/.gitignore +5 -0
  2. data/CHANGELOG +101 -0
  3. data/MIT-LICENSE +20 -0
  4. data/README.rdoc +376 -0
  5. data/Rakefile +38 -0
  6. data/VERSION +1 -0
  7. data/generators/oauth_consumer/USAGE +10 -0
  8. data/generators/oauth_consumer/oauth_consumer_generator.rb +50 -0
  9. data/generators/oauth_consumer/templates/consumer_token.rb +5 -0
  10. data/generators/oauth_consumer/templates/controller.rb +19 -0
  11. data/generators/oauth_consumer/templates/index.html.erb +29 -0
  12. data/generators/oauth_consumer/templates/index.html.haml +18 -0
  13. data/generators/oauth_consumer/templates/migration.rb +20 -0
  14. data/generators/oauth_consumer/templates/oauth_config.rb +41 -0
  15. data/generators/oauth_consumer/templates/show.html.erb +7 -0
  16. data/generators/oauth_consumer/templates/show.html.haml +8 -0
  17. data/generators/oauth_provider/USAGE +20 -0
  18. data/generators/oauth_provider/lib/insert_routes.rb +67 -0
  19. data/generators/oauth_provider/oauth_provider_generator.rb +125 -0
  20. data/generators/oauth_provider/templates/_form.html.erb +17 -0
  21. data/generators/oauth_provider/templates/_form.html.haml +21 -0
  22. data/generators/oauth_provider/templates/access_token.rb +16 -0
  23. data/generators/oauth_provider/templates/authorize.html.erb +14 -0
  24. data/generators/oauth_provider/templates/authorize.html.haml +16 -0
  25. data/generators/oauth_provider/templates/authorize_failure.html.erb +1 -0
  26. data/generators/oauth_provider/templates/authorize_failure.html.haml +1 -0
  27. data/generators/oauth_provider/templates/authorize_success.html.erb +1 -0
  28. data/generators/oauth_provider/templates/authorize_success.html.haml +1 -0
  29. data/generators/oauth_provider/templates/client_application.rb +55 -0
  30. data/generators/oauth_provider/templates/client_application_spec.rb +29 -0
  31. data/generators/oauth_provider/templates/client_application_test.rb +42 -0
  32. data/generators/oauth_provider/templates/client_applications.yml +23 -0
  33. data/generators/oauth_provider/templates/clients_controller.rb +52 -0
  34. data/generators/oauth_provider/templates/clients_controller_spec.rb +239 -0
  35. data/generators/oauth_provider/templates/clients_controller_test.rb +280 -0
  36. data/generators/oauth_provider/templates/controller.rb +11 -0
  37. data/generators/oauth_provider/templates/controller_spec.rb +367 -0
  38. data/generators/oauth_provider/templates/controller_spec_helper.rb +80 -0
  39. data/generators/oauth_provider/templates/controller_test.rb +310 -0
  40. data/generators/oauth_provider/templates/controller_test_helper.rb +115 -0
  41. data/generators/oauth_provider/templates/edit.html.erb +7 -0
  42. data/generators/oauth_provider/templates/edit.html.haml +4 -0
  43. data/generators/oauth_provider/templates/index.html.erb +43 -0
  44. data/generators/oauth_provider/templates/index.html.haml +39 -0
  45. data/generators/oauth_provider/templates/migration.rb +46 -0
  46. data/generators/oauth_provider/templates/new.html.erb +5 -0
  47. data/generators/oauth_provider/templates/new.html.haml +5 -0
  48. data/generators/oauth_provider/templates/oauth_nonce.rb +13 -0
  49. data/generators/oauth_provider/templates/oauth_nonce_spec.rb +24 -0
  50. data/generators/oauth_provider/templates/oauth_nonce_test.rb +26 -0
  51. data/generators/oauth_provider/templates/oauth_nonces.yml +13 -0
  52. data/generators/oauth_provider/templates/oauth_token.rb +31 -0
  53. data/generators/oauth_provider/templates/oauth_token_spec.rb +309 -0
  54. data/generators/oauth_provider/templates/oauth_token_test.rb +57 -0
  55. data/generators/oauth_provider/templates/oauth_tokens.yml +17 -0
  56. data/generators/oauth_provider/templates/request_token.rb +40 -0
  57. data/generators/oauth_provider/templates/show.html.erb +27 -0
  58. data/generators/oauth_provider/templates/show.html.haml +30 -0
  59. data/init.rb +1 -0
  60. data/install.rb +2 -0
  61. data/lib/oauth-plugin.rb +1 -0
  62. data/lib/oauth/controllers/application_controller_methods.rb +110 -0
  63. data/lib/oauth/controllers/consumer_controller.rb +76 -0
  64. data/lib/oauth/controllers/provider_controller.rb +111 -0
  65. data/lib/oauth/models/consumers/service_loader.rb +18 -0
  66. data/lib/oauth/models/consumers/services/agree2_token.rb +15 -0
  67. data/lib/oauth/models/consumers/services/fireeagle_token.rb +39 -0
  68. data/lib/oauth/models/consumers/services/twitter_token.rb +18 -0
  69. data/lib/oauth/models/consumers/token.rb +60 -0
  70. data/oauth-plugin.gemspec +112 -0
  71. data/rails/init.rb +7 -0
  72. data/tasks/oauth_tasks.rake +4 -0
  73. data/uninstall.rb +1 -0
  74. metadata +136 -0
@@ -0,0 +1,5 @@
1
+ doc
2
+ pkg
3
+ *.log
4
+ .DS_Store
5
+ .svn
@@ -0,0 +1,101 @@
1
+ 7/29/2009
2
+ 0.3.10
3
+ - Closed blocks in erb template (jcrosby) while pelle is hiding under his desk
4
+ - Handled error case on authorize with non existent token
5
+ - Fixed Agree2 token
6
+ - Security Fix: Only skip verify_authenticity_token for specific oauth token requests in provider controller
7
+ 7/25/2009
8
+ 0.3.9
9
+ - Added an Index to oauth consumers controller. Rerun generator to create index template
10
+ - Added invalidate action to provider, which allows a token to invalidate itself /oauth/invalidate
11
+ - Added capabilities action to provider. Lets you expand to allow auto discovery of permissions and services that token provides.
12
+ - Can override how authorize form indicates an authorization. To get around ugly checkbox
13
+
14
+ def user_authorizes_token?
15
+ params[:commit] == 'Authorize'
16
+ end
17
+
18
+ 7/23/2009
19
+ 0.3.8
20
+ - Fixed Gem Plugins Loading
21
+ 7/21/2009
22
+ 0.3.7
23
+ - A blushing Pelle adds a missing file
24
+ 0.3.6
25
+ - Twitter, Agree2 and FireEagle tokens are working in consumer.
26
+ 0.3.5
27
+ - made it a gem
28
+ - more thorough tests of OAuth 1.0 consumer
29
+ - Add support for a OAUTH_10_SUPPORT constant to switch on support for OAuth 1.0 in provider
30
+ 7/19/2009
31
+ - Added support for OAuth 1.0 consumers (nov)
32
+ 7/17/2009
33
+ - Added back support for OAuth 1.0 for providers (nov)
34
+ 7/14/2009
35
+ - Added OAuth Consumer generator
36
+ - Moved oauth controller code to a module to make it easier to upgrade in the future
37
+ 7/11/2009
38
+ - Added support for OAuth version 1.0a
39
+ - Added haml support
40
+ - Improved OAuth Client Controller gui (alec-c4)
41
+ 2/11/2009
42
+ - Fixed escaping error and file path error in the generator simultaneously reported and fixed by Ivan Valdes and Mike Demers thanks
43
+
44
+ 2/9/2009
45
+ - Fixed compatibility issue with OAuth Gem 3.1 (wr0ngway and aeden)
46
+ - Added Test:Unit tests to generator (Ed Hickey)
47
+ - added missing oauth_clients/edit.html.erb view template (Ed Hickey)
48
+ - added missing :oauth_clients resource route in USAGE (Ed Hickey)
49
+ - Don't throw NPE it token is not in db (Haruska)
50
+ - Cleaned up whitespace (bricolage, Nicholas Nam)
51
+ - Fixed bug in default verify_oauth_signature (igrigorik)
52
+ - Doc fixes (skippy)
53
+
54
+ 6/23/2008
55
+
56
+ - Split OAuth controller into two parts: OAuth and OAuth clients. [jcrosby]
57
+
58
+ revision 31
59
+
60
+ - patch that fixes a problem in oauth_required from Hannes Tyden and Sean Treadway from SoundCloud. Thanks.
61
+
62
+ revision 30
63
+
64
+ - updated to use oauth gem 0.2.1
65
+
66
+
67
+ revision 23
68
+
69
+ - removed all core libraries from plugin. They are now in the oauth gem.
70
+
71
+ # oauth-plugin-pre-gem Branch created
72
+
73
+ revision 18
74
+ - added a generator for creation oauth_providers
75
+
76
+ revision 12
77
+ - the bug with post and put has now been fixed.
78
+ - better documentation
79
+
80
+ revision 9
81
+ - added a test helper. Include OAuth::TestHelper in your tests or specs to mock incoming requests
82
+
83
+ revision: 8
84
+ - moved tests into oauth folder and renamed them to make them work with autotest by default
85
+ - Refactored the request methods to make them more flexible and ready for integrating with ActiveResource
86
+ - There are a few tests that fail. All of them to do with put and post requests with payload data. I decided to commit anyway, to get the new api out.
87
+
88
+ revision: 7
89
+
90
+ - Done a lot of work on the Server side of things. The Server class has changed a lot and is likely to be incompatible with previous versions
91
+
92
+ revision: 6
93
+
94
+ - Throws InsecureSignatureMethod exception if attempting to use straight sha1 or md5.
95
+ - Disables plaintext signature over http (throws an InsecureSignatureMethod)
96
+ - Better testing of signature methods - the prior tests were seriously flawed.
97
+
98
+ revision: 5
99
+
100
+ - Removed support for sha1 and md5
101
+ - Implemented draft 6 support of OAuth removing secrets from base string
@@ -0,0 +1,20 @@
1
+ Copyright (c) 2007 Pelle Braendgaard
2
+
3
+ Permission is hereby granted, free of charge, to any person obtaining
4
+ a copy of this software and associated documentation files (the
5
+ "Software"), to deal in the Software without restriction, including
6
+ without limitation the rights to use, copy, modify, merge, publish,
7
+ distribute, sublicense, and/or sell copies of the Software, and to
8
+ permit persons to whom the Software is furnished to do so, subject to
9
+ the following conditions:
10
+
11
+ The above copyright notice and this permission notice shall be
12
+ included in all copies or substantial portions of the Software.
13
+
14
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
@@ -0,0 +1,376 @@
1
+ = OAuth Plugin
2
+
3
+ This is a plugin for implementing OAuth Providers and Consumers in Rails applications.
4
+
5
+ We support the revised OAuth 1.0a specs at:
6
+
7
+ http://oauth.net/core/1.0a
8
+
9
+ and the OAuth site at:
10
+
11
+ http://oauth.net
12
+
13
+ For more about the changes made to OAuth1.0a please see Seth's Idiot's Guide to OAuth 1.0a.
14
+
15
+ http://mojodna.net/2009/05/20/an-idiots-guide-to-oauth-10a.html
16
+
17
+ == Requirements
18
+
19
+ You need to install the oauth gem (0.3.5) which is the core OAuth ruby library. It will NOT work on any previous version of the gem.
20
+
21
+ sudo gem install oauth
22
+
23
+ == Installation
24
+
25
+ The plugin can now be installed as an gem from github, which is the easiest way to keep it up to date.
26
+
27
+ sudo gem install oauth-plugin
28
+
29
+ You should add the following in the gem dependency section of environment.rb
30
+
31
+ config.gem "oauth"
32
+ config.gem "oauth-plugin"
33
+
34
+ Alternatively you can install it in vendors/plugin:
35
+
36
+ script/plugin install git://github.com/pelle/oauth-plugin.git
37
+
38
+ The Generator currently creates code (in particular views) that only work in Rails 2.
39
+
40
+ It should not be difficult to manually modify the code to work on Rails 1.2.x
41
+
42
+ I think the only real issue is that the views have .html.erb extensions. So these could theoretically just be renamed to .rhtml.
43
+
44
+ Please let me know if this works and I will see if I can make the generator conditionally create .rhtml for pre 2.0 versions of RAILS.
45
+
46
+ == OAuth Provider generator
47
+
48
+ While it isn't very flexible at the moment there is an oauth_provider generator which you can use like this:
49
+
50
+ ./script/generate oauth_provider
51
+
52
+ This generates OAuth and OAuth client controllers as well as the required models.
53
+
54
+ It requires an authentication framework such as acts_as_authenticated, restful_authentication or restful_open_id_authentication. It also requires Rails 2.0.
55
+
56
+ === Generator Options
57
+
58
+ By default the generator generates RSpec and ERB templates. The generator can instead create Test::Unit and/or HAML templates. To do this use the following options:
59
+
60
+ ./script/generate oauth_provider --test-unit --haml
61
+
62
+ These can of course be used individually as well.
63
+
64
+ === User Model
65
+
66
+ Add the following lines to your user model:
67
+
68
+ has_many :client_applications
69
+ has_many :tokens, :class_name=>"OauthToken",:order=>"authorized_at desc",:include=>[:client_application]
70
+
71
+ === Migrate database
72
+
73
+ The database is defined in:
74
+
75
+ db/migrate/XXX_create_oauth_tables.rb
76
+
77
+ Run them as any other normal migration in rails with:
78
+
79
+ rake db:migrate
80
+
81
+ == Upgrading from OAuth 1.0 to OAuth 1.0a
82
+
83
+ As the flow has changed slightly and there are a couple of database changes it isn't as simple as just updating the plugin. Please follow these steps closely:
84
+
85
+ === Add a migration
86
+
87
+ You need to add a migration:
88
+
89
+ script/generate migration upgrade_oauth
90
+
91
+ Make it look like this:
92
+
93
+ class UpgradeOauth < ActiveRecord::Migration
94
+ def self.up
95
+ add_column :oauth_tokens,:callback_url,:string
96
+ add_column :oauth_tokens,:verifier,:string,:limit => 20
97
+ end
98
+
99
+ def self.down
100
+ remove_column :oauth_tokens,:callback_url
101
+ remove_column :oauth_tokens,:verifier
102
+ end
103
+ end
104
+
105
+ === Change code
106
+
107
+ There are changes to the following files:
108
+
109
+ app/models/client_application.rb
110
+ app/models/request_token.rb
111
+ app/controllers/oauth_controller.rb
112
+
113
+ === Changes in client_application.rb
114
+
115
+ Add the following towards the top of the model class
116
+
117
+ attr_accessor :token_callback_url
118
+
119
+ Then change the create_request_token method to the following:
120
+
121
+ def create_request_token
122
+ RequestToken.create :client_application =>self,:callback_url=>token_callback_url
123
+ end
124
+
125
+ === Changes in request_token.rb
126
+
127
+ The RequestToken contains the bulk of the changes so it's easiest to list it in it's entirety. Mainly we need to add support for the oauth_verifier parameter and also tell the client that we support OAuth 1.0a.
128
+
129
+ Make sure it looks like this:
130
+
131
+ class RequestToken < OauthToken
132
+
133
+ attr_accessor :provided_oauth_verifier
134
+
135
+ def authorize!(user)
136
+ return false if authorized?
137
+ self.user = user
138
+ self.authorized_at = Time.now
139
+ self.verifier=OAuth::Helper.generate_key(16)[0,20] unless oauth10?
140
+ self.save
141
+ end
142
+
143
+ def exchange!
144
+ return false unless authorized?
145
+ return false unless oauth10? || verifier==provided_oauth_verifier
146
+
147
+ RequestToken.transaction do
148
+ access_token = AccessToken.create(:user => user, :client_application => client_application)
149
+ invalidate!
150
+ access_token
151
+ end
152
+ end
153
+
154
+ def to_query
155
+ if oauth10?
156
+ super
157
+ else
158
+ "#{super}&oauth_callback_confirmed=true"
159
+ end
160
+ end
161
+
162
+ def oob?
163
+ self.callback_url=='oob'
164
+ end
165
+
166
+ def oauth10?
167
+ (defined? OAUTH_10_SUPPORT) && OAUTH_10_SUPPORT && self.callback_url.blank?
168
+ end
169
+
170
+ end
171
+
172
+ === Changes in oauth_controller
173
+
174
+ All you need to do here is the change the authorize action to use the request_token callback url and add the oauth_verifier to the callback url.
175
+
176
+ def authorize
177
+ @token = ::RequestToken.find_by_token params[:oauth_token]
178
+ unless @token.invalidated?
179
+ if request.post?
180
+ if params[:authorize] == '1'
181
+ @token.authorize!(current_user)
182
+ if @token.oauth10?
183
+ @redirect_url = params[:oauth_callback] || @token.client_application.callback_url
184
+ else
185
+ @redirect_url = @token.oob? ? @token.client_application.callback_url : @token.callback_url
186
+ end
187
+
188
+ if @redirect_url
189
+ if @token.oauth10?
190
+ redirect_to "#{@redirect_url}?oauth_token=#{@token.token}"
191
+ else
192
+ redirect_to "#{@redirect_url}?oauth_token=#{@token.token}&oauth_verifier=#{@token.verifier}"
193
+ end
194
+ else
195
+ render :action => "authorize_success"
196
+ end
197
+ elsif params[:authorize] == "0"
198
+ @token.invalidate!
199
+ render :action => "authorize_failure"
200
+ end
201
+ end
202
+ else
203
+ render :action => "authorize_failure"
204
+ end
205
+ end
206
+
207
+ Alternatively if you haven't customized your controller you can replace the full controller with this:
208
+
209
+ require 'oauth/controllers/provider_controller'
210
+ class OauthController < ApplicationController
211
+ include OAuth::Controllers::ProviderController
212
+ end
213
+
214
+ This way the controller will automatically include bug fixes in future versions of the plugin.
215
+
216
+ The rest of the changes are in the plugin and will be automatically be included.
217
+
218
+ *Note* OAuth 1.0a removes support for callback url's passed to the authorize page, clients must either define a callback url in their client application or pass one on the token request page.
219
+
220
+ === Supporting old OAuth 1.0 clients
221
+
222
+ If you absolutely have to support older OAuth 1.0 clients on an optional basis, we now include a switch to turn it back on.
223
+
224
+ For legacy OAUTH 1.0 support add the following constant in your environment.rb
225
+
226
+ OAUTH_10_SUPPORT = true
227
+
228
+ Note, you should only do this if you really positively require to support old OAuth1.0 clients. There is a serious security issue with this.
229
+
230
+ == Protecting your actions
231
+
232
+ I recommend that you think about what your users would want to provide access to and limit oauth for those only. For example in a CRUD controller you may think about if you want to let consumer applications do the create, update or delete actions. For your application this might make sense, but for others maybe not.
233
+
234
+ If you want to give oauth access to everything a registered user can do, just replace the filter you have in your controllers with:
235
+
236
+ before_filter :login_or_oauth_required
237
+
238
+ If you want to restrict consumers to the index and show methods of your controller do the following:
239
+
240
+ before_filter :login_required,:except=>[:show,:index]
241
+ before_filter :login_or_oauth_required,:only=>[:show,:index]
242
+
243
+ If you have an action you only want used via oauth:
244
+
245
+ before_filter :oauth_required
246
+
247
+ All of these places the tokens user in current_user as you would expect. It also exposes the following methods:
248
+
249
+ * current_token - for accessing the token used to authorize the current request
250
+ * current_client_application - for accessing information about which consumer is currently accessing your request
251
+
252
+ You could add application specific information to the OauthToken and ClientApplication model for such things as object level access control, billing, expiry etc. Be creative and you can create some really cool applications here.
253
+
254
+ == OAuth Consumer generator
255
+
256
+ The oauth_consumer generator creates a controller to manage the authentication flow between your application and any number of external OAuth secured applications that you wish to connect to.
257
+
258
+ To run it simply run:
259
+
260
+ ./script/generate oauth_consumer
261
+
262
+ This generates the OauthConsumerController as well as the ConsumerToken model.
263
+
264
+ === Generator Options
265
+
266
+ By default the generator generates ERB templates. The generator can instead create HAML templates. To do this use the following options:
267
+
268
+ ./script/generate oauth_consumer --haml
269
+
270
+ === Configuration
271
+
272
+ All configuration of applications is done in
273
+
274
+ config/initializers/oauth_consumers.rb
275
+
276
+ Add entries to OAUTH_CREDENTIALS for all OAuth Applications you wish to connect to. Get this information by registering your application at the particular applications developer page.
277
+
278
+ OAUTH_CREDENTIALS={
279
+ :twitter=>{
280
+ :key=>"key",
281
+ :secret=>"secret"
282
+ },
283
+ :agree2=>{
284
+ :key=>"key",
285
+ :secret=>"secret"
286
+ },
287
+ :hour_feed=>{
288
+ :key=>"",
289
+ :secret=>"",
290
+ :options={
291
+ :site=>"http://hourfeed.com"
292
+ }
293
+ },
294
+ :nu_bux=>{
295
+ :key=>"",
296
+ :secret=>"",
297
+ :super_class=>"OpenTransactToken", # if a OAuth service follows a particular standard
298
+ # with a token implementation you can set the superclass
299
+ # to use
300
+ :options=>{
301
+ :site=>"http://nubux.heroku.com"
302
+ }
303
+ }
304
+ }
305
+
306
+ You can add any of the options that the OAuth::Consumer.new accepts to the options hash: http://oauth.rubyforge.org/rdoc/classes/OAuth/Consumer.html
307
+
308
+ :key, :secret are required as well as :options[:site] etc. for non custom ConsumerToken services.
309
+
310
+ === ConsumerToken models
311
+
312
+ For each site setup in the OAUTH_CREDENTIALS hash the plugin goes through and loads or creates a new model class that subclasses ConsumerToken.
313
+
314
+ eg. If you connect to Yahoo's FireEagle you would add the :fire_eagle entry to OAUTH_CREDENTIALS and a new FireEagleToken model class will be created on the fly.
315
+
316
+ This allows you to add a has_one association in your user model:
317
+
318
+ has_one :fire_eagle,:class_name=>"FireEagleToken", :dependent=>:destroy
319
+
320
+ And you could do:
321
+
322
+ @location=@user.fire_eagle.client.location
323
+
324
+ The client method gives you a OAuth::AccessToken which you can use to perform rest operations on the client site - see http://oauth.rubyforge.org/rdoc/classes/OAuth/AccessToken.html
325
+
326
+ === Custom ConsumerToken models
327
+
328
+ Before creating the FireEagleToken model the plugin checks if a class already exists by that name or if we provide an api wrapper for it. This allows you to create a better token model that uses an existing ruby gem.
329
+
330
+ Currently we provide the following semi tested tokens wrappers:
331
+
332
+ * FireEagle
333
+ * Twitter (requires Paul Singh's version of twitter gem until main gem is updated to 0.3.5 - sudo gem install paulsingh-twitter)
334
+ * Agree2
335
+
336
+ These can be found in lib/oauth/models/consulers/services. Contributions will be warmly accepted for your favorite OAuth service.
337
+
338
+ === The OauthConsumerController
339
+
340
+ To connect a user to an external service link or redirect them to:
341
+
342
+ /oauth_consumers/[SERVICE_NAME]
343
+
344
+ Where SERVICE_NAME is the name you set in the OAUTH_CREDENTIALS hash. This will request the request token and redirect the user to the services authorization screen. When the user accepts the get redirected back to:
345
+
346
+ /oauth_consumers/[SERVICE_NAME]/callback
347
+
348
+ You can specify this url to the service you're calling when you register, but it will automatically be sent along anyway.
349
+
350
+ === Migrate database
351
+
352
+ The database is defined in:
353
+
354
+ db/migrate/XXX_create_oauth_consumer_tokens.rb
355
+
356
+ Run them as any other normal migration in rails with:
357
+
358
+ rake db:migrate
359
+
360
+ == More
361
+
362
+ The Google Code project is http://code.google.com/p/oauth-plugin/
363
+
364
+ The Mailing List for all things OAuth in Ruby is:
365
+
366
+ http://groups.google.com/group/oauth-ruby
367
+
368
+ The Mailing list for everything else OAuth is:
369
+
370
+ http://groups.google.com/group/oauth
371
+
372
+ The OAuth Ruby Gem home page is http://oauth.rubyforge.org
373
+
374
+ Please help documentation, patches and testing.
375
+
376
+ Copyright (c) 2007-2009 Pelle Braendgaard, released under the MIT license