From f5feadc81fa85a829b9996e8ff7e212f1467b901 Mon Sep 17 00:00:00 2001 From: Paul Thornthwaite Date: Wed, 21 Nov 2012 12:11:26 +0000 Subject: [PATCH] [Brightbox] Refactors credential code in Compute --- lib/fog/brightbox/compute.rb | 30 +++++++++++++++++----------- lib/fog/brightbox/oauth2.rb | 35 +++++++++++++++++++++++++++++++++ tests/brightbox/oauth2_tests.rb | 20 +++++++++++++++++++ 3 files changed, 73 insertions(+), 12 deletions(-) create mode 100644 lib/fog/brightbox/oauth2.rb create mode 100644 tests/brightbox/oauth2_tests.rb diff --git a/lib/fog/brightbox/compute.rb b/lib/fog/brightbox/compute.rb index 4114a2368..91d54d494 100644 --- a/lib/fog/brightbox/compute.rb +++ b/lib/fog/brightbox/compute.rb @@ -1,5 +1,6 @@ require 'fog/brightbox' require 'fog/compute' +require 'fog/brightbox/oauth2' module Fog module Compute @@ -162,6 +163,7 @@ module Fog class Real include Shared + include Fog::Brightbox::OAuth2 # Creates a new instance of the Brightbox Compute service # @@ -185,12 +187,15 @@ module Fog @connection = Fog::Connection.new(@api_url, @persistent, @connection_options) # Authentication options - @brightbox_client_id = options[:brightbox_client_id] || Fog.credentials[:brightbox_client_id] - @brightbox_secret = options[:brightbox_secret] || Fog.credentials[:brightbox_secret] + client_id = options[:brightbox_client_id] || Fog.credentials[:brightbox_client_id] + client_secret = options[:brightbox_secret] || Fog.credentials[:brightbox_secret] - @brightbox_username = options[:brightbox_username] || Fog.credentials[:brightbox_username] - @brightbox_password = options[:brightbox_password] || Fog.credentials[:brightbox_password] - @brightbox_account = options[:brightbox_account] || Fog.credentials[:brightbox_account] + username = options[:brightbox_username] || Fog.credentials[:brightbox_username] + password = options[:brightbox_password] || Fog.credentials[:brightbox_password] + @scoped_account = options[:brightbox_account] || Fog.credentials[:brightbox_account] + + credential_options = {:username => username, :password => password} + @credentials = CredentialSet.new(client_id, client_secret, credential_options) end # Makes an API request to the given path using passed options or those @@ -214,7 +219,7 @@ module Fog :path => path, :expects => expected_responses } - parameters[:account_id] = @brightbox_account if parameters[:account_id].nil? && @brightbox_account + parameters[:account_id] = @scoped_account if parameters[:account_id].nil? && @scoped_account request_options[:body] = Fog::JSON.encode(parameters) unless parameters.empty? make_request(request_options) end @@ -237,8 +242,9 @@ module Fog # Returns true if authentication is being performed as a user # @return [Boolean] def authenticating_as_user? - @brightbox_username && @brightbox_password + @credentials.user_details? end + private def get_oauth_token(options = {}) auth_url = options[:brightbox_auth_url] || @auth_url @@ -246,13 +252,13 @@ module Fog connection = Fog::Connection.new(auth_url) authentication_body_hash = if authenticating_as_user? { - 'client_id' => @brightbox_client_id, + 'client_id' => @credentials.client_id, 'grant_type' => 'password', - 'username' => @brightbox_username, - 'password' => @brightbox_password + 'username' => @credentials.username, + 'password' => @credentials.password } else - {'client_id' => @brightbox_client_id, 'grant_type' => 'none'} + {'client_id' => @credentials.client_id, 'grant_type' => 'none'} end @authentication_body = Fog::JSON.encode(authentication_body_hash) @@ -260,7 +266,7 @@ module Fog :path => "/token", :expects => 200, :headers => { - 'Authorization' => "Basic " + Base64.encode64("#{@brightbox_client_id}:#{@brightbox_secret}").chomp, + 'Authorization' => "Basic " + Base64.encode64("#{@credentials.client_id}:#{@credentials.client_secret}").chomp, 'Content-Type' => 'application/json' }, :method => 'POST', diff --git a/lib/fog/brightbox/oauth2.rb b/lib/fog/brightbox/oauth2.rb new file mode 100644 index 000000000..549d63207 --- /dev/null +++ b/lib/fog/brightbox/oauth2.rb @@ -0,0 +1,35 @@ +# This module covers Brightbox's partial implementation of OAuth 2.0 +# and enables fog clients to implement several authentictication strategies +# +# @see http://tools.ietf.org/html/draft-ietf-oauth-v2-10 +# +module Fog::Brightbox::OAuth2 + + # Encapsulates credentials required to request access tokens from the + # Brightbox authorisation servers + # + # @todo Interface to update certain credentials (after password change) + # + class CredentialSet + attr_reader :client_id, :client_secret, :username, :password + # + # @param [String] client_id + # @param [String] client_secret + # @param [Hash] options + # @option options [String] :username + # @option options [String] :password + # + def initialize(client_id, client_secret, options = {}) + @client_id = client_id + @client_secret = client_secret + @username = options[:username] + @password = options[:password] + end + + # Returns true if user details are available + # @return [Boolean] + def user_details? + !!(@username && @password) + end + end +end diff --git a/tests/brightbox/oauth2_tests.rb b/tests/brightbox/oauth2_tests.rb new file mode 100644 index 000000000..52639d84d --- /dev/null +++ b/tests/brightbox/oauth2_tests.rb @@ -0,0 +1,20 @@ +Shindo.tests("Fog::Brightbox::OAuth2", ["brightbox"]) do + + tests("CredentialSet") do + @client_id = "app-12345" + @client_secret = "__mashed_keys_123__" + @username = "usr-12345" + @password = "__mushed_keys_321__" + + tests("with client credentials") do + credentials = Fog::Brightbox::OAuth2::CredentialSet.new(@client_id, @client_secret) + tests("#user_details?").returns(false) { credentials.user_details? } + end + + tests("with user credentials") do + options = {:username => @username, :password => @password} + credentials = Fog::Brightbox::OAuth2::CredentialSet.new(@client_id, @client_secret, options) + tests("#user_details?").returns(true) { credentials.user_details? } + end + end +end