summaryrefslogtreecommitdiff
path: root/test
diff options
context:
space:
mode:
authorJenny Shen <jenny.shen@shopify.com>2021-10-06 17:39:23 -0400
committerHiroshi SHIBATA <hsbt@ruby-lang.org>2021-10-26 08:01:55 +0900
commit92ec010595bed29567fc08dd4d52d4c4518f0fd4 (patch)
treedd979fbf6aba6d5638153c54ca03f3363e9a8827 /test
parent10fe8495cd9568be79b4c254742eb0f667e84988 (diff)
[rubygems/rubygems] Add support to build and sign certificates with multiple key algorithms
https://github.com/rubygems/rubygems/commit/967876f15d Co-Authored-By: Frederik Dudzik <frederik.dudzik@shopify.com>
Diffstat (limited to 'test')
-rw-r--r--test/rubygems/helper.rb4
-rw-r--r--test/rubygems/private_ec_key.pem9
-rw-r--r--test/rubygems/test_gem_commands_cert_command.rb67
-rw-r--r--test/rubygems/test_gem_security.rb36
4 files changed, 106 insertions, 10 deletions
diff --git a/test/rubygems/helper.rb b/test/rubygems/helper.rb
index 17f7350f13..504e25ea52 100644
--- a/test/rubygems/helper.rb
+++ b/test/rubygems/helper.rb
@@ -1519,14 +1519,14 @@ Also, a list:
end
##
- # Loads an RSA private key named +key_name+ with +passphrase+ in <tt>test/rubygems/</tt>
+ # Loads a private key named +key_name+ with +passphrase+ in <tt>test/rubygems/</tt>
def self.load_key(key_name, passphrase = nil)
key_file = key_path key_name
key = File.read key_file
- OpenSSL::PKey::RSA.new key, passphrase
+ OpenSSL::PKey.read key, passphrase
end
##
diff --git a/test/rubygems/private_ec_key.pem b/test/rubygems/private_ec_key.pem
new file mode 100644
index 0000000000..5d855d0dfc
--- /dev/null
+++ b/test/rubygems/private_ec_key.pem
@@ -0,0 +1,9 @@
+-----BEGIN EC PRIVATE KEY-----
+Proc-Type: 4,ENCRYPTED
+DEK-Info: AES-256-CBC,4107F98A374CB8EC18F1AA4EA4B6A0DB
+
+BRklFxJGcz7gqQYxek8TZkt8qbPhB0FSR6nyw3SYuio/2tlT9ohs74mlK3EbG9Lt
+Y4OquJbksBFmoB7fIoM4vnuIZ0Eoz2ooxn9tjhBtqJ3mVscYXwZmA3UDUWDMlviQ
+Fu37OpikQv4TFA1jlmUK0LM8xmUCfUeLl0kHD17lFsz2gkO2kwg8mn/YUMOIaDOu
+EnnmxbAwnZBpemQkQfpTt2mYL9gu3CcMt5gokBuGDxY=
+-----END EC PRIVATE KEY-----
diff --git a/test/rubygems/test_gem_commands_cert_command.rb b/test/rubygems/test_gem_commands_cert_command.rb
index f722678a19..077be11d55 100644
--- a/test/rubygems/test_gem_commands_cert_command.rb
+++ b/test/rubygems/test_gem_commands_cert_command.rb
@@ -14,9 +14,10 @@ class TestGemCommandsCertCommand < Gem::TestCase
ALTERNATE_CERT = load_cert 'alternate'
EXPIRED_PUBLIC_CERT = load_cert 'expired'
- ALTERNATE_KEY_FILE = key_path 'alternate'
- PRIVATE_KEY_FILE = key_path 'private'
- PUBLIC_KEY_FILE = key_path 'public'
+ ALTERNATE_KEY_FILE = key_path 'alternate'
+ PRIVATE_KEY_FILE = key_path 'private'
+ PRIVATE_EC_KEY_FILE = key_path 'private_ec'
+ PUBLIC_KEY_FILE = key_path 'public'
ALTERNATE_CERT_FILE = cert_path 'alternate'
CHILD_CERT_FILE = cert_path 'child'
@@ -142,6 +143,42 @@ Added '/CN=alternate/DC=example'
assert_path_exist File.join(@tempdir, 'gem-public_cert.pem')
end
+ def test_execute_build_key_algorithm_ec_key
+ passphrase = 'Foo bar'
+
+ @cmd.handle_options %W[--build nobody@example.com --key-algorithm ec]
+
+ @build_ui = Gem::MockGemUi.new "#{passphrase}\n#{passphrase}"
+
+ use_ui @build_ui do
+ @cmd.execute
+ end
+
+ output = @build_ui.output.squeeze("\n").split "\n"
+
+ assert_equal "Passphrase for your Private Key: ",
+ output.shift
+ assert_equal "Please repeat the passphrase for your Private Key: ",
+ output.shift
+ assert_equal "Certificate: #{File.join @tempdir, 'gem-public_cert.pem'}",
+ output.shift
+ assert_equal "Private Key: #{File.join @tempdir, 'gem-private_key.pem'}",
+ output.shift
+
+ assert_equal "Don't forget to move the key file to somewhere private!",
+ output.shift
+
+ assert_empty output
+ assert_empty @build_ui.error
+
+ assert_path_exist File.join(@tempdir, 'gem-private_key.pem')
+
+ cert_path = File.join(@tempdir, 'gem-public_cert.pem')
+ assert_path_exist cert_path
+ cert = OpenSSL::X509::Certificate.new(File.read(cert_path))
+ assert cert.public_key.is_a? OpenSSL::PKey::EC
+ end
+
def test_execute_build_bad_email_address
passphrase = 'Foo bar'
email = "nobody@"
@@ -279,6 +316,28 @@ Added '/CN=alternate/DC=example'
assert_path_exist File.join(@tempdir, 'gem-public_cert.pem')
end
+ def test_execute_build_ec_key
+ @cmd.handle_options %W[
+ --build nobody@example.com
+ --private-key #{PRIVATE_EC_KEY_FILE}
+ ]
+
+ use_ui @ui do
+ @cmd.execute
+ end
+
+ output = @ui.output.split "\n"
+
+ assert_equal "Certificate: #{File.join @tempdir, 'gem-public_cert.pem'}",
+ output.shift
+
+ assert_empty output
+ assert_empty @ui.error
+
+ assert_path_exist File.join(@tempdir, 'gem-public_cert.pem')
+ assert_path_not_exist File.join(@tempdir, 'gem-private_key.pem')
+ end
+
def test_execute_certificate
use_ui @ui do
@cmd.handle_options %W[--certificate #{PUBLIC_CERT_FILE}]
@@ -742,7 +801,7 @@ ERROR: --private-key not specified and ~/.gem/gem-private_key.pem does not exis
@cmd.handle_options %W[--private-key #{bad}]
end
- assert_equal "invalid argument: --private-key #{bad}: invalid RSA key",
+ assert_equal "invalid argument: --private-key #{bad}: invalid RSA, DSA, or EC key",
e.message
e = assert_raise OptionParser::InvalidArgument do
diff --git a/test/rubygems/test_gem_security.rb b/test/rubygems/test_gem_security.rb
index 2eabbea3bf..d04bd4a8bd 100644
--- a/test/rubygems/test_gem_security.rb
+++ b/test/rubygems/test_gem_security.rb
@@ -12,6 +12,7 @@ end
class TestGemSecurity < Gem::TestCase
CHILD_KEY = load_key 'child'
+ EC_KEY = load_key 'private_ec', 'Foo bar'
ALTERNATE_CERT = load_cert 'child'
CHILD_CERT = load_cert 'child'
@@ -103,11 +104,38 @@ class TestGemSecurity < Gem::TestCase
end
def test_class_create_key
- key = @SEC.create_key 1024
+ key = @SEC.create_key 'rsa'
assert_kind_of OpenSSL::PKey::RSA, key
end
+ def test_class_create_key_downcases
+ key = @SEC.create_key 'DSA'
+
+ assert_kind_of OpenSSL::PKey::DSA, key
+ end
+
+ def test_class_create_key_raises_unknown_algorithm
+ e = assert_raise Gem::Security::Exception do
+ @SEC.create_key 'NOT_RSA'
+ end
+
+ assert_equal "NOT_RSA algorithm not found. RSA, DSA, and EC algorithms are supported.",
+ e.message
+ end
+
+ def test_class_get_public_key_rsa
+ pkey_pem = PRIVATE_KEY.public_key.to_pem
+
+ assert_equal pkey_pem, @SEC.get_public_key(PRIVATE_KEY).to_pem
+ end
+
+ def test_class_get_public_key_ec
+ pkey = @SEC.get_public_key(EC_KEY)
+
+ assert_respond_to pkey, :to_pem
+ end
+
def test_class_email_to_name
assert_equal '/CN=nobody/DC=example',
@SEC.email_to_name('nobody@example').to_s
@@ -259,7 +287,7 @@ class TestGemSecurity < Gem::TestCase
end
def test_class_write
- key = @SEC.create_key 1024
+ key = @SEC.create_key 'rsa'
path = File.join @tempdir, 'test-private_key.pem'
@@ -273,7 +301,7 @@ class TestGemSecurity < Gem::TestCase
end
def test_class_write_encrypted
- key = @SEC.create_key 1024
+ key = @SEC.create_key 'rsa'
path = File.join @tempdir, 'test-private_encrypted_key.pem'
@@ -289,7 +317,7 @@ class TestGemSecurity < Gem::TestCase
end
def test_class_write_encrypted_cipher
- key = @SEC.create_key 1024
+ key = @SEC.create_key 'rsa'
path = File.join @tempdir, 'test-private_encrypted__with_non_default_cipher_key.pem'