Skip to content

Commit

Permalink
first pass at kms sign request and mocks
Browse files Browse the repository at this point in the history
  • Loading branch information
geemus committed Dec 10, 2024
1 parent a1390b5 commit 192f8a6
Show file tree
Hide file tree
Showing 6 changed files with 101 additions and 14 deletions.
1 change: 1 addition & 0 deletions lib/fog/aws/kms.rb
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ class KMS < Fog::Service
request :describe_key
request :get_public_key
request :schedule_key_deletion
request :sign

model_path 'fog/aws/models/kms'
model :key
Expand Down
24 changes: 24 additions & 0 deletions lib/fog/aws/parsers/kms/sign.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
module Fog
module Parsers
module AWS
module KMS
class Sign < Fog::Parsers::Base
def reset
@response = {}
end

def start_element(name, attrs = [])
super
end

def end_element(name)
case name
when 'KeyId', 'Signature', 'SigningAlgorithm'
@response[name] = value
end
end
end
end
end
end
end
26 changes: 12 additions & 14 deletions lib/fog/aws/requests/kms/create_key.rb
Original file line number Diff line number Diff line change
Expand Up @@ -52,20 +52,18 @@ def create_key(*args)

self.data[:keys][key_id] = key

size = key['KeySpec'].split('_').last
type = key['KeySpec'].split('_').first
case type
when 'ECC'
curve = {
'ECC_NIST_P256' => 'secp256k1',
'ECC_NIST_P384' => 'secp384r1',
'ECC_NIST_P521' => 'secp521r1',
'ECC_SECG_P256K1' => 'prime256v1'
}[key['KeySpec']]
self.data[:pkeys][key_id] = OpenSSL::PKey::EC.generate(curve)
when 'RSA'
self.data[:pkeys][key_id] = OpenSSL::PKey::RSA.generate(size.to_i)
end
klass, arg = {
'ECC_NIST_P256' => [OpenSSL::PKey::EC, 'secp256k1'],
'ECC_NIST_P384' => [OpenSSL::PKey::EC, 'secp384r1'],
'ECC_NIST_P521' => [OpenSSL::PKey::EC, 'secp521r1'],
'ECC_SECG_P256K1' => [OpenSSL::PKey::EC, 'prime256v1'],
'RSA_2048' => [OpenSSL::PKey::RSA, 2048],
'RSA_3072' => [OpenSSL::PKey::RSA, 3072],
'RSA_4096' => [OpenSSL::PKey::RSA, 4096]
}[key['KeySpec']]
raise "Unknown or not-yet-implemented #{key['KeySpec']} KeySpec for kms create_key mocks" unless klass

self.data[:pkeys][key_id] = klass.generate(arg)

response.body = { 'KeyMetadata' => key }
response
Expand Down
54 changes: 54 additions & 0 deletions lib/fog/aws/requests/kms/sign.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
module Fog
module AWS
class KMS
class Real
require 'fog/aws/parsers/kms/sign'

# Sign
#
# ==== Parameters
#
# === Returns
#
# ==== See Also
# https://docs.aws.amazon.com/kms/latest/APIReference/API_Sign.html
def sign(identifier, message, algorithm, options = {})
request({
'Action' => 'Sign',
'KeyId' => identifier,
'Message' => message,
'SigningAlgorithm' => algorithm,
:parser => Fog::Parsers::AWS::KMS::Sign.new
}.merge!(options))
end
end

class Mock
def sign(identifier, message, algorithm, _options = {})
response = Excon::Response.new
pkey = self.data[:pkeys][identifier]
unless pkey
response.status = 404
raise(Excon::Errors.status_error({ expects: 200 }, response))
end

# FIXME: SM2 support?
sha = "SHA#{algorithm.split('_SHA_').last}"
hash = OpenSSL::Digest.digest(sha, message)

signopts = {}
signopts[:rsa_padding_mode] = 'pss' if algorithm.start_with?('RSASSA_PSS')

signature = pkey.sign_raw(sha, hash, signopts)

response.body = {
'KeyId' => identifier,
'Signature' => Base64.strict_encode64(signature),
'SigningAlgorithm' => algorithm
}
response
end
end
end
end
end
6 changes: 6 additions & 0 deletions tests/requests/kms/helper.rb
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,12 @@ module Formats
'KeyState' => String,
'PendingWindowInDays' => Integer
}.freeze

SIGN = {
'KeyId' => String,
'Signature' => String,
'SigningAlgorithm' => String
}.freeze
end
end
end
4 changes: 4 additions & 0 deletions tests/requests/kms/key_tests.rb
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,10 @@
Fog::AWS[:kms].list_keys.body
end

tests('#sign').data_matches_schema(AWS::KMS::Formats::SIGN) do
Fog::AWS[:kms].sign(key_id, 'sign me', 'RSASSA_PSS_SHA_256').body
end

tests('#schedule_key_deletion').data_matches_schema(AWS::KMS::Formats::SCHEDULE_KEY_DELETION) do
Fog::AWS[:kms].schedule_key_deletion(key_id, 7).body
end
Expand Down

0 comments on commit 192f8a6

Please sign in to comment.