Permalink
Browse files

Initial commit.

  • Loading branch information...
1 parent 64195c2 commit 09ca36d72d5f468907e055cc23c4598cf44535f8 @mjbellantoni mjbellantoni committed Dec 28, 2011
View
@@ -1,13 +1,16 @@
source "http://rubygems.org"
-# Add dependencies required to use your gem here.
-# Example:
-# gem "activesupport", ">= 2.3.5"
-# Add dependencies to develop your gem here.
-# Include everything needed to run rake, tests, features, etc.
+gem 'omniauth', "~> 1.0.0"
+gem 'omniauth-oauth'
+gem 'multi_json'
+
group :development do
- gem "shoulda", ">= 0"
- gem "bundler", "~> 1.0.0"
- gem "jeweler", "~> 1.6.4"
- gem "rcov", ">= 0"
+ gem "bundler"
+ gem "jeweler"
end
+
+group :development, :test do
+ gem "rack-test"
+ gem "rspec"
+ gem "webmock"
+end
View
@@ -0,0 +1,48 @@
+GEM
+ remote: http://rubygems.org/
+ specs:
+ addressable (2.2.6)
+ crack (0.3.1)
+ diff-lcs (1.1.3)
+ git (1.2.5)
+ hashie (1.2.0)
+ jeweler (1.6.4)
+ bundler (~> 1.0)
+ git (>= 1.2.5)
+ rake
+ multi_json (1.0.4)
+ oauth (0.4.5)
+ omniauth (1.0.1)
+ hashie (~> 1.2)
+ rack
+ omniauth-oauth (1.0.0)
+ oauth
+ omniauth (~> 1.0)
+ rack (1.3.5)
+ rack-test (0.6.1)
+ rack (>= 1.0)
+ rake (0.9.2.2)
+ rspec (2.7.0)
+ rspec-core (~> 2.7.0)
+ rspec-expectations (~> 2.7.0)
+ rspec-mocks (~> 2.7.0)
+ rspec-core (2.7.1)
+ rspec-expectations (2.7.0)
+ diff-lcs (~> 1.1.2)
+ rspec-mocks (2.7.0)
+ webmock (1.7.8)
+ addressable (~> 2.2, > 2.2.5)
+ crack (>= 0.1.7)
+
+PLATFORMS
+ ruby
+
+DEPENDENCIES
+ bundler
+ jeweler
+ multi_json
+ omniauth (~> 1.0.0)
+ omniauth-oauth
+ rack-test
+ rspec
+ webmock
View
@@ -1,4 +1,4 @@
-Copyright (c) 2011 mjbellantoni@yahoo.com
+Copyright (c) 2011 Yesware, Inc.
Permission is hereby granted, free of charge, to any person obtaining
a copy of this software and associated documentation files (the
@@ -1,8 +1,32 @@
-= omniauth-google
+# omniauth-google
-Description goes here.
+A Google OAuth strategy for OmniAuth 1.0.
-== Contributing to omniauth-google
+## Installing
+
+Add to your `Gemfile`:
+
+```ruby
+gem 'omniauth-google'
+```
+
+Then `bundle install`.
+
+## Usage
+
+Add the middleware to a Rails app in `config/initializers/omniauth.rb`:
+
+```ruby
+Rails.application.config.middleware.use OmniAuth::Builder do
+ provider :google, CONSUMER_KEY, CONSUMER_SECRET
+end
+```
+
+## Acknowledgments
+
+This code was extracted from OmniAuth v0.3 and is really the work of those folks!
+
+## Contributing to omniauth-google
* Check out the latest master to make sure the feature hasn't been implemented or the bug hasn't been fixed yet
* Check out the issue tracker to make sure someone already hasn't requested it and/or contributed it
@@ -12,8 +36,8 @@ Description goes here.
* Make sure to add tests for it. This is important so I don't break it in a future version unintentionally.
* Please try not to mess with the Rakefile, version, or history. If you want to have your own version, or is otherwise necessary, that is fine, but please isolate to its own commit so I can cherry-pick around it.
-== Copyright
+## Copyright
-Copyright (c) 2011 mjbellantoni@yahoo.com. See LICENSE.txt for
+Copyright (c) 2011 Yesware, Inc. See LICENSE.txt for
further details.
View
@@ -13,31 +13,21 @@ require 'rake'
require 'jeweler'
Jeweler::Tasks.new do |gem|
- # gem is a Gem::Specification... see http://docs.rubygems.org/read/chapter/20 for more options
gem.name = "omniauth-google"
- gem.homepage = "http://github.com/mjbellantoni/omniauth-google"
+ gem.homepage = "http://github.com/Yesware/omniauth-google"
gem.license = "MIT"
- gem.summary = %Q{TODO: one-line summary of your gem}
- gem.description = %Q{TODO: longer description of your gem}
- gem.email = "mjbellantoni@yahoo.com"
+ gem.summary = %Q{A Google OAuth strategy for OmniAuth 1.0}
+ gem.description = gem.summary
+ gem.email = "info@yesware.com"
gem.authors = ["mjbellantoni@yahoo.com"]
# dependencies defined in Gemfile
end
Jeweler::RubygemsDotOrgTasks.new
-require 'rake/testtask'
-Rake::TestTask.new(:test) do |test|
- test.libs << 'lib' << 'test'
- test.pattern = 'test/**/test_*.rb'
- test.verbose = true
-end
-
-require 'rcov/rcovtask'
-Rcov::RcovTask.new do |test|
- test.libs << 'test'
- test.pattern = 'test/**/test_*.rb'
- test.verbose = true
- test.rcov_opts << '--exclude "gems/*"'
+require 'rspec/core'
+require 'rspec/core/rake_task'
+RSpec::Core::RakeTask.new(:spec) do |spec|
+ spec.pattern = FileList['spec/**/*_spec.rb']
end
task :default => :test
@@ -0,0 +1,3 @@
+require "omniauth-google/version"
+require 'omniauth/strategies/google'
+
@@ -0,0 +1,5 @@
+module OmniAuth
+ module Google
+ VERSION = "1.0.0"
+ end
+end
@@ -0,0 +1,87 @@
+require 'omniauth-oauth'
+
+module OmniAuth
+ module Strategies
+ # Authenticate to Google via OAuth and retrieve basic
+ # user information.
+ #
+ # Usage:
+ # use OmniAuth::Strategies::Google, 'consumerkey', 'consumersecret'
+ class Google < OmniAuth::Strategies::OAuth
+ def initialize(app, consumer_key=nil, consumer_secret=nil, options={}, &block)
+ client_options = {
+ :access_token_path => '/accounts/OAuthGetAccessToken',
+ :authorize_path => '/accounts/OAuthAuthorizeToken',
+ :request_token_path => '/accounts/OAuthGetRequestToken',
+ :site => 'https://www.google.com',
+ }
+ google_contacts_auth = 'www.google.com/m8/feeds'
+ options[:scope] ||= "https://#{google_contacts_auth}"
+ options[:scope] << " https://#{google_contacts_auth}" unless options[:scope] =~ %r[http[s]?:\/\/#{google_contacts_auth}]
+ options[:client_options] = client_options
+
+ super(app, consumer_key, consumer_secret, options, &block)
+ end
+
+ uid do
+ user_info['uid']
+ end
+
+ info do
+ user_info
+ end
+
+ extra do
+ { 'user_hash' => user_hash }
+ end
+
+ def user_info
+ email = user_hash['feed']['id']['$t']
+
+ name = user_hash['feed']['author'].first['name']['$t']
+ name = email if name.strip == '(unknown)'
+
+ {
+ 'email' => email,
+ 'uid' => email,
+ 'name' => name,
+ }
+ end
+
+ def user_hash
+ # Google is very strict about keeping authorization and
+ # authentication separated.
+ # They give no endpoint to get a user's profile directly that I can
+ # find. We *can* get their name and email out of the contacts feed,
+ # however. It will fail in the extremely rare case of a user who has
+ # a Google Account but has never even signed up for Gmail. This has
+ # not been seen in the field.
+ @user_hash ||= MultiJson.decode(@access_token.get('https://www.google.com/m8/feeds/contacts/default/full?max-results=1&alt=json').body)
+ end
+
+ # Monkeypatch OmniAuth to pass the scope and authorize_params in the consumer.get_request_token call
+ def request_phase
+ request_options = {:scope => options[:scope]}
+ request_options.merge!(options[:authorize_params])
+
+ request_token = consumer.get_request_token({:oauth_callback => callback_url}, request_options)
+ session['oauth'] ||= {}
+ session['oauth'][name.to_s] = {'callback_confirmed' => request_token.callback_confirmed?, 'request_token' => request_token.token, 'request_secret' => request_token.secret}
+ r = Rack::Response.new
+
+ if request_token.callback_confirmed?
+ r.redirect(request_token.authorize_url)
+ else
+ r.redirect(request_token.authorize_url(:oauth_callback => callback_url))
+ end
+
+ r.finish
+
+ rescue ::Timeout::Error => e
+ fail!(:timeout, e)
+ rescue ::Net::HTTPFatalError, ::OpenSSL::SSL::SSLError => e
+ fail!(:service_unavailable, e)
+ end
+ end
+ end
+end
Oops, something went wrong.

0 comments on commit 09ca36d

Please sign in to comment.