Skip to content

Commit

Permalink
Mergig sprout's change to support OAuth, cleaning up the code.
Browse files Browse the repository at this point in the history
  • Loading branch information
gimite committed Jan 17, 2010
2 parents 688ad2d + 5357a74 commit 63ac4c1
Show file tree
Hide file tree
Showing 3 changed files with 87 additions and 34 deletions.
1 change: 1 addition & 0 deletions README.rdoc
Expand Up @@ -17,6 +17,7 @@ Example:
require "google_spreadsheet"

# Logs in.
# You can also use OAuth. See document of GoogleSpreadsheet.login_with_oauth for details.
session = GoogleSpreadsheet.login("username@gmail.com", "mypassword")

# First worksheet of http://spreadsheets.google.com/ccc?key=pz7XtlQC-PYx-jrVMJErTcg&hl=en
Expand Down
7 changes: 5 additions & 2 deletions google-spreadsheet-ruby.gemspec
@@ -1,8 +1,8 @@
Gem::Specification.new do |s|
s.name = %q{google-spreadsheet-ruby}
s.version = "0.0.9"
s.version = "0.1.0"
s.authors = ["Hiroshi Ichikawa"]
s.date = %q{2010-01-11}
s.date = %q{2010-01-17}
s.description = %q{This is a library to read/write Google Spreadsheet.}
s.email = ["gimite+github@gmail.com"]
s.extra_rdoc_files = ["README.rdoc"]
Expand All @@ -20,10 +20,13 @@ Gem::Specification.new do |s|

if Gem::Version.new(Gem::RubyGemsVersion) >= Gem::Version.new('1.2.0')
s.add_development_dependency(%q<hpricot>, [">= 0.3"])
s.add_development_dependency(%q<oauth>, [">= 0.3.6"])
else
s.add_dependency(%q<hpricot>, [">= 0.3"])
s.add_dependency(%q<oauth>, [">= 0.3.6"])
end
else
s.add_dependency(%q<hpricot>, [">= 0.3"])
s.add_dependency(%q<oauth>, [">= 0.3.6"])
end
end
113 changes: 81 additions & 32 deletions lib/google_spreadsheet.rb
Expand Up @@ -9,6 +9,7 @@
require "uri"
require "rubygems"
require "hpricot"
require "oauth"
Net::HTTP.version_1_2

module GoogleSpreadsheet
Expand All @@ -19,7 +20,29 @@ module GoogleSpreadsheet
def self.login(mail, password)
return Session.login(mail, password)
end


# Authenticates with given OAuth token.
#
# For generating oauth_token, you can proceed as follow:
#
# 1) First generate OAuth consumer object with key and secret for your site by registering site with google
# @consumer = OAuth::Consumer.new( "key","secret", {:site=>"https://agree2"})
# 2) Request token with OAuth
# @request_token = @consumer.get_request_token
# session[:request_token] = @request_token
# redirect_to @request_token.authorize_url
# 3) Create an oauth access token
# @oauth_access_token = @request_token.get_access_token
# @access_token = OAuth::AccessToken.new(@consumer, @oauth_access_token.token, @oauth_access_token.secret)
#
# See these documents for details:
#
# - http://oauth.rubyforge.org/
# - http://code.google.com/apis/accounts/docs/OAuth.html
def self.login_with_oauth(oauth_token)
return Session.login_with_oauth(oauth_token)
end

# Restores GoogleSpreadsheet::Session from +path+ and returns it.
# If +path+ doesn't exist or authentication has failed, prompts mail and password on console,
# authenticates with them, stores the session to +path+ and returns it.
Expand Down Expand Up @@ -111,12 +134,21 @@ def self.login(mail, password)
session.login(mail, password)
return session
end


# The same as GoogleSpreadsheet.login_with_oauth.
def self.login_with_oauth(oauth_token)
session = Session.new(nil, oauth_token)
end

# Restores session using return value of auth_tokens method of previous session.
def initialize(auth_tokens = {})
@auth_tokens = auth_tokens
def initialize(auth_tokens, oauth_token = nil)
if oauth_token
@oauth_token = oauth_token
else
@auth_tokens = auth_tokens
end
end

# Authenticates with given +mail+ and +password+, and updates current session object
# if succeeds. Raises GoogleSpreadsheet::AuthenticationError if fails.
# Google Apps account is supported.
Expand Down Expand Up @@ -244,41 +276,58 @@ def request(method, url, params = {}) #:nodoc:
end
response_type = params[:response_type] || :xml

http = Net::HTTP.new(uri.host, uri.port)
http.use_ssl = uri.scheme == "https"
http.verify_mode = OpenSSL::SSL::VERIFY_NONE
http.start() do
while true
path = uri.path + (uri.query ? "?#{uri.query}" : "")
header = auth_header(auth).merge(add_header)
if method == :delete || method == :get
response = http.__send__(method, path, header)
else
response = http.__send__(method, path, data, header)
end
if response.code == "401" && @on_auth_fail && @on_auth_fail.call()
next
end
if !(response.code =~ /^2/)
raise(
response.code == "401" ? AuthenticationError : GoogleSpreadsheet::Error,
"Response code #{response.code} for #{method} #{url}: " +
CGI.unescapeHTML(response.body))
end
case response_type
when :xml
return Hpricot.XML(response.body)
when :raw
return response.body
if @oauth_token

if method == :delete || method == :get
response = @oauth_token.__send__(method, url)
else
response = @oauth_token.__send__(method, url, data)
end
return convert_response(response, response_type)

else

http = Net::HTTP.new(uri.host, uri.port)
http.use_ssl = uri.scheme == "https"
http.verify_mode = OpenSSL::SSL::VERIFY_NONE
http.start() do
while true
path = uri.path + (uri.query ? "?#{uri.query}" : "")
header = auth_header(auth).merge(add_header)
if method == :delete || method == :get
response = http.__send__(method, path, header)
else
raise("unknown params[:response_type]: %s" % response_type)
response = http.__send__(method, path, data, header)
end
if response.code == "401" && @on_auth_fail && @on_auth_fail.call()
next
end
if !(response.code =~ /^2/)
raise(
response.code == "401" ? AuthenticationError : GoogleSpreadsheet::Error,
"Response code #{response.code} for #{method} #{url}: " +
CGI.unescapeHTML(response.body))
end
return convert_response(response, response_type)
end
end

end
end

private

def convert_response(response, response_type)
case response_type
when :xml
return Hpricot.XML(response.body)
when :raw
return response.body
else
raise("unknown params[:response_type]: %s" % response_type)
end
end

def authenticate(mail, password, auth)
params = {
"accountType" => "HOSTED_OR_GOOGLE",
Expand Down

0 comments on commit 63ac4c1

Please sign in to comment.