From d7b2cfd808169624c9208c664b064abc8ee19e3f Mon Sep 17 00:00:00 2001 From: Ricky Smith Date: Tue, 26 Feb 2019 17:52:28 -0500 Subject: [PATCH] Introduce a new pattern for passing querystring values as a hash This refactors the gem to no longer build querystrings with string concatenation and, instead, passes a hash to the underlying request library. This commit only implements the new pattern in the list_servers request to be used as a guideline --- lib/fog/aliyun/compute.rb | 25 ++++++++++++++++--- lib/fog/aliyun/models/compute/server.rb | 2 +- .../requests/compute/list_server_types.rb | 2 +- .../aliyun/requests/compute/list_servers.rb | 18 ++++++------- 4 files changed, 33 insertions(+), 14 deletions(-) diff --git a/lib/fog/aliyun/compute.rb b/lib/fog/aliyun/compute.rb index eefae11..3fe11d9 100644 --- a/lib/fog/aliyun/compute.rb +++ b/lib/fog/aliyun/compute.rb @@ -351,6 +351,20 @@ def defaultAliyunUri(action, sigNonce, time) '?Format=JSON&AccessKeyId=' + @aliyun_accesskey_id + '&Action=' + action + '&SignatureMethod=HMAC-SHA1&RegionId=' + @aliyun_region_id + '&SignatureNonce=' + sigNonce + '&SignatureVersion=1.0&Version=2014-05-26&Timestamp=' + urlTimeFormat end + def defaultAliyunQueryParameters(action, sigNonce, time) + { + Format: 'JSON', + AccessKeyId: @aliyun_accesskey_id, + Action: action, + SignatureMethod: 'HMAC-SHA1', + RegionId: @aliyun_region_id, + SignatureNonce: sigNonce, + SignatureVersion: '1.0', + Version: '2014-05-26', + Timestamp: time.strftime('%Y-%m-%dT%H:%M:%SZ') + } + end + def defaultAliyunVPCUri(action, sigNonce, time) parTimeFormat = time.strftime('%Y-%m-%dT%H:%M:%SZ') urlTimeFormat = URI.encode(parTimeFormat, ':') @@ -399,7 +413,14 @@ def defalutVPCParameters(action, sigNonce, time) end # compute signature + # This method should be considered deprecated and replaced with sign_without_encoding, which is better for using querystring hashes and not + # building querystrings with string concatination. def sign(accessKeySecret, parameters) + signature = sign_without_encoding(accessKeySecret, parameters) + URI.encode(signature, '/[^!*\'()\;?:@#&%=+$,{}[]<>`" ') + end + + def sign_without_encoding(accessKeySecret, parameters) sortedParameters = parameters.sort canonicalizedQueryString = '' sortedParameters.each do |k, v| @@ -414,9 +435,7 @@ def sign(accessKeySecret, parameters) digest = OpenSSL::HMAC.digest(digVer, key, stringToSign) signature = Base64.encode64(digest) signature[-1] = '' - encodedSig = URI.encode(signature, '/[^!*\'()\;?:@#&%=+$,{}[]<>`" ') - - encodedSig + signature end end end diff --git a/lib/fog/aliyun/models/compute/server.rb b/lib/fog/aliyun/models/compute/server.rb index 157c046..9200bbb 100644 --- a/lib/fog/aliyun/models/compute/server.rb +++ b/lib/fog/aliyun/models/compute/server.rb @@ -36,7 +36,7 @@ class Server < Fog::Compute::Server attribute :expired_at, aliases: 'ExpiredTime' def image - requires image_id + requires :image_id Fog::Compute::Aliyun::Image.new(service: service).all(imageId: image_id)[0] end diff --git a/lib/fog/aliyun/requests/compute/list_server_types.rb b/lib/fog/aliyun/requests/compute/list_server_types.rb index 2f50d4d..5b35cb4 100644 --- a/lib/fog/aliyun/requests/compute/list_server_types.rb +++ b/lib/fog/aliyun/requests/compute/list_server_types.rb @@ -41,7 +41,7 @@ def get_instance_type(cpuCount, memorySize) ) _InstanceTypeId = nil - _InstanceTypeList = Fog::JSON.decode(response.body)['InstanceTypes']['InstanceType'] + _InstanceTypeList = response.body['InstanceTypes']['InstanceType'] _InstanceTypeList.each do |instance_type| next unless (instance_type['CpuCoreCount'] == cpuCount) && (instance_type['MemorySize'] == memorySize) _InstanceTypeId = instance_type['InstanceTypeId'] diff --git a/lib/fog/aliyun/requests/compute/list_servers.rb b/lib/fog/aliyun/requests/compute/list_servers.rb index 529f4c2..76b2ce9 100644 --- a/lib/fog/aliyun/requests/compute/list_servers.rb +++ b/lib/fog/aliyun/requests/compute/list_servers.rb @@ -11,7 +11,7 @@ def list_servers(options = {}) _time = Time.new.utc _parameters = defalutParameters(_action, _sigNonce, _time) - _pathURL = defaultAliyunUri(_action, _sigNonce, _time) + _query_parameters = defaultAliyunQueryParameters(_action, _sigNonce, _time) _InstanceId = options[:instanceId] _VpcId = options[:vpcId] @@ -22,35 +22,35 @@ def list_servers(options = {}) unless _InstanceId.nil? _InstanceStr = "[\"#{_InstanceId}\"]" _parameters['InstanceIds'] = _InstanceStr - _pathURL += '&InstanceIds=' + _InstanceStr + _query_parameters[:InstanceIds] = _InstanceStr end unless _VpcId.nil? _parameters['VpcId'] = _VpcId - _pathURL += '&VpcId=' + _VpcId + _query_parameters[:VpcId] = _VpcId end unless _SecurityGroupId.nil? _parameters['SecurityGroupId'] = _SecurityGroupId - _pathURL += '&SecurityGroupId=' + _SecurityGroupId + _query_parameters[:SecurityGroupId] = _SecurityGroupId end unless _PageNumber.nil? _parameters['PageNumber'] = _PageNumber - _pathURL += '&PageNumber=' + _PageNumber + _query_parameters[:PageNumber] = _PageNumber end _PageSize ||= '50' _parameters['PageSize'] = _PageSize - _pathURL += '&PageSize=' + _PageSize + _query_parameters[:PageSize] = _PageSize - _signature = sign(@aliyun_accesskey_secret, _parameters) - _pathURL += '&Signature=' + _signature + _signature = sign_without_encoding(@aliyun_accesskey_secret, _parameters) + _query_parameters[:Signature] = _signature request( expects: [200, 203], method: 'GET', - path: _pathURL + query: _query_parameters ) end end