Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Rubocop Implemented #212

Merged
merged 1 commit into from
Jan 11, 2018
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
4 changes: 4 additions & 0 deletions .sync.yml
Original file line number Diff line number Diff line change
@@ -1,3 +1,7 @@
---
appveyor.yml:
delete: false
.travis.yml:
extras:
- rvm: 2.1.9
script: bundle exec rake rubocop
2 changes: 2 additions & 0 deletions .travis.yml
Original file line number Diff line number Diff line change
Expand Up @@ -25,5 +25,7 @@ matrix:
- rvm: 2.1.9
bundler_args: --without system_tests
env: PUPPET_GEM_VERSION="~> 4.0"
- rvm: 2.1.9
script: bundle exec rake rubocop
notifications:
email: false
199 changes: 97 additions & 102 deletions lib/puppet/provider/java_ks/keytool.rb
Original file line number Diff line number Diff line change
Expand Up @@ -14,9 +14,9 @@ def command_keytool
def to_pkcs12(path)
case private_key_type
when :rsa
pkey = OpenSSL::PKey::RSA.new File.read(private_key), get_password
pkey = OpenSSL::PKey::RSA.new File.read(private_key), password
when :ec
pkey = OpenSSL::PKey::EC.new File.read(private_key), get_password
pkey = OpenSSL::PKey::EC.new File.read(private_key), password
end

if chain
Expand All @@ -26,50 +26,48 @@ def to_pkcs12(path)
chain_certs = get_chain(certificate)
x509_cert = chain_certs.shift
end
pkcs12 = OpenSSL::PKCS12.create(get_password, @resource[:name], pkey, x509_cert, chain_certs)
File.open(path, "wb") { |f| f.print pkcs12.to_der }
pkcs12 = OpenSSL::PKCS12.create(password, @resource[:name], pkey, x509_cert, chain_certs)
File.open(path, 'wb') { |f| f.print pkcs12.to_der }
end

# Keytool can only import a jceks keystore if the format is der. Generating and
# importing a keystore is used to add private_key and certifcate pairs.
def to_der(path)
x509_cert = OpenSSL::X509::Certificate.new File.read certificate
File.open(path, "wb") { |f| f.print x509_cert.to_der }
File.open(path, 'wb') { |f| f.print x509_cert.to_der }
end

def get_chain(path)
File.read(path).scan(/-----BEGIN [^\n]*CERTIFICATE.*?-----END [^\n]*CERTIFICATE-----/m).map {|cert| OpenSSL::X509::Certificate.new cert}
File.read(path).scan(%r{-----BEGIN [^\n]*CERTIFICATE.*?-----END [^\n]*CERTIFICATE-----}m).map { |cert| OpenSSL::X509::Certificate.new cert }
end

def get_password
def password
if @resource[:password_file].nil?
@resource[:password]
else
file = File.open(@resource[:password_file], "r")
file = File.open(@resource[:password_file], 'r')
pword = file.read
file.close
pword.chomp
end
end

def password_file
pword = get_password
pword = password
source_pword = sourcepassword

tmpfile = Tempfile.new("#{@resource[:name]}.")
if File.exists?(@resource[:target]) and not File.zero?(@resource[:target])
if !source_pword.nil?
contents = "#{pword}\n#{source_pword}"
else
contents = "#{pword}\n#{pword}"
end
else
if !source_pword.nil?
contents = "#{pword}\n#{pword}\n#{source_pword}"
else
contents = "#{pword}\n#{pword}\n#{pword}"
end
end
contents = if File.exist?(@resource[:target]) && !File.zero?(@resource[:target])
if !source_pword.nil?
"#{pword}\n#{source_pword}"
else
"#{pword}\n#{pword}"
end
elsif !source_pword.nil?
"#{pword}\n#{pword}\n#{source_pword}"
else
"#{pword}\n#{pword}\n#{pword}"
end
tmpfile.write(contents)
tmpfile.flush
tmpfile
Expand All @@ -80,14 +78,14 @@ def import_ks
tmppk12 = Tempfile.new("#{@resource[:name]}.")
to_pkcs12(tmppk12.path)
cmd = [
command_keytool,
'-importkeystore', '-srcstoretype', 'PKCS12',
'-destkeystore', @resource[:target],
'-srckeystore', tmppk12.path,
'-alias', @resource[:name]
command_keytool,
'-importkeystore', '-srcstoretype', 'PKCS12',
'-destkeystore', @resource[:target],
'-srckeystore', tmppk12.path,
'-alias', @resource[:name]
]
cmd << '-trustcacerts' if @resource[:trustcacerts] == :true
cmd += [ '-destkeypass', @resource[:destkeypass] ] unless @resource[:destkeypass].nil?
cmd += ['-destkeypass', @resource[:destkeypass]] unless @resource[:destkeypass].nil?

pwfile = password_file
run_command(cmd, @resource[:target], pwfile)
Expand All @@ -97,23 +95,22 @@ def import_ks

def import_pkcs12
cmd = [
command_keytool,
'-importkeystore', '-srcstoretype', 'PKCS12',
'-destkeystore', @resource[:target],
'-srckeystore', certificate
command_keytool,
'-importkeystore', '-srcstoretype', 'PKCS12',
'-destkeystore', @resource[:target],
'-srckeystore', certificate
]

if @resource[:source_alias]
cmd.concat([
'-srcalias', @resource[:source_alias],
'-destalias', @resource[:name]
])
'-srcalias', @resource[:source_alias],
'-destalias', @resource[:name]
])
end

pwfile = password_file
run_command(cmd, @resource[:target], pwfile)
pwfile.close! if pwfile.is_a? Tempfile

end

def import_jceks
Expand All @@ -128,7 +125,7 @@ def import_jceks
'-storetype', storetype
]
cmd << '-trustcacerts' if @resource[:trustcacerts] == :true
cmd += [ '-destkeypass', @resource[:destkeypass] ] unless @resource[:destkeypass].nil?
cmd += ['-destkeypass', @resource[:destkeypass]] unless @resource[:destkeypass].nil?

pwfile = password_file
run_command(cmd, @resource[:target], pwfile)
Expand All @@ -137,19 +134,19 @@ def import_jceks

def exists?
cmd = [
command_keytool,
'-list',
'-keystore', @resource[:target],
'-alias', @resource[:name]
command_keytool,
'-list',
'-keystore', @resource[:target],
'-alias', @resource[:name]
]
cmd += [ '-storetype', storetype ] if storetype == "jceks"
cmd += ['-storetype', storetype] if storetype == 'jceks'
begin
tmpfile = password_file
run_command(cmd, false, tmpfile)
tmpfile.close!
return true
rescue => e
if e.message =~ /password was incorrect/i
if e.message =~ %r{password was incorrect}i
# we have the wrong password for the keystore. so delete it if :password_fail_reset
if @resource[:password_fail_reset] == :true
File.delete(@resource[:target])
Expand All @@ -163,71 +160,71 @@ def exists?
def latest
# The certificate file may not exist during a puppet noop run as it's managed by puppet.
# Return value must be different to provider.current to signify a possible trigger event.
if Puppet[:noop] and !File.exists?(certificate)
return 'latest'
if Puppet[:noop] && !File.exist?(certificate)
'latest'
elsif storetype == :pkcs12
cmd = [
command_keytool,
'-list', '-keystore', certificate,
'-storetype', 'PKCS12', '-storepass', sourcepassword
command_keytool,
'-list', '-keystore', certificate,
'-storetype', 'PKCS12', '-storepass', sourcepassword
]
output = run_command(cmd)
latest = output.scan(/\(SHA1\):\s+(.*)/)[0][0]
return latest
latest = output.scan(%r{\(SHA1\):\s+(.*)})[0][0]
latest
else
cmd = [
command_keytool,
'-v', '-printcert', '-file', certificate
command_keytool,
'-v', '-printcert', '-file', certificate
]
output = run_command(cmd)
latest = output.scan(/SHA1:\s+(.*)/)[0][0]
return latest
latest = output.scan(%r{SHA1:\s+(.*)})[0][0]
latest
end
end

# Reading the fingerprint of the certificate currently in the keystore.
def current
# The keystore file may not exist during a puppet noop run as it's managed by puppet.
if Puppet[:noop] and !File.exists?(@resource[:target])
return 'current'
if Puppet[:noop] && !File.exist?(@resource[:target])
'current'
else
cmd = [
command_keytool,
'-list', '-v',
'-keystore', @resource[:target],
'-alias', @resource[:name]
command_keytool,
'-list', '-v',
'-keystore', @resource[:target],
'-alias', @resource[:name]
]
cmd += [ '-storetype', storetype ] if storetype == "jceks"
cmd += ['-storetype', storetype] if storetype == 'jceks'
tmpfile = password_file
output = run_command(cmd, false, tmpfile)
tmpfile.close!
if output.include? 'MD5:'
current = output.scan(/Certificate fingerprints:\n\s+MD5: .*\n\s+SHA1: (.*)/)[0][0]
else
current = output.scan(/Certificate fingerprints:\n\s+SHA1: (.*)/)[0][0]
end
return current
current = if output.include? 'MD5:'
output.scan(%r{Certificate fingerprints:\n\s+MD5: .*\n\s+SHA1: (.*)})[0][0]
else
output.scan(%r{Certificate fingerprints:\n\s+SHA1: (.*)})[0][0]
end
current
end
end

# Determine if we need to do an import of a private_key and certificate pair
# or just add a signed certificate, then do it.
def create
if !certificate.nil? and !private_key.nil?
if !certificate.nil? && !private_key.nil?
import_ks
elsif certificate.nil? and !private_key.nil?
elsif certificate.nil? && !private_key.nil?
raise Puppet::Error, 'Keytool is not capable of importing a private key without an accomapaning certificate.'
elsif storetype == :jceks
import_jceks
elsif storetype == :pkcs12
import_pkcs12
else
cmd = [
command_keytool,
'-importcert', '-noprompt',
'-alias', @resource[:name],
'-file', certificate,
'-keystore', @resource[:target]
command_keytool,
'-importcert', '-noprompt',
'-alias', @resource[:name],
'-file', certificate,
'-keystore', @resource[:target]
]
cmd << '-trustcacerts' if @resource[:trustcacerts] == :true
tmpfile = password_file
Expand All @@ -238,10 +235,10 @@ def create

def destroy
cmd = [
command_keytool,
'-delete',
'-alias', @resource[:name],
'-keystore', @resource[:target]
command_keytool,
'-delete',
'-alias', @resource[:name],
'-keystore', @resource[:target]
]
tmpfile = password_file
run_command(cmd, false, tmpfile)
Expand Down Expand Up @@ -278,30 +275,29 @@ def storetype
@resource[:storetype]
end

def run_command(cmd, target=false, stdinfile=false, env={})

def run_command(cmd, target = false, stdinfile = false, env = {})
env[:PATH] = @resource[:path].join(File::PATH_SEPARATOR) if resource[:path]

# The Puppet::Util::Execution.execute method is deparcated in Puppet 3.x
# but we need this to work on 2.7.x too.
if Puppet::Util::Execution.respond_to?(:execute)
exec_method = Puppet::Util::Execution.method(:execute)
else
exec_method = Puppet::Util.method(:execute)
end

if Puppet::Util::Execution.respond_to?(:withenv)
withenv = Puppet::Util::Execution.method(:withenv)
else
withenv = Puppet::Util.method(:withenv)
end
exec_method = if Puppet::Util::Execution.respond_to?(:execute)
Puppet::Util::Execution.method(:execute)
else
Puppet::Util.method(:execute)
end

withenv = if Puppet::Util::Execution.respond_to?(:withenv)
Puppet::Util::Execution.method(:withenv)
else
Puppet::Util.method(:withenv)
end

# the java keytool will not correctly deal with an empty target keystore
# file. If we encounter an empty keystore target file, preserve the mode,
# owner and group, temporarily raise the umask, and delete the empty file.
if target and (File.exists?(target) and File.zero?(target))
if target && (File.exist?(target) && File.zero?(target))
stat = File.stat(target)
umask = File.umask(0077)
umask = File.umask(0o077)
File.delete(target)
end

Expand All @@ -312,22 +308,22 @@ def run_command(cmd, target=false, stdinfile=false, env={})
# From a best practice standpoint the keystore should be protected by file
# permissions and not just the passphrase so "making it work on SLES"
# trumps.
if Facter.value('osfamily') == 'Suse' and @resource[:password]
cmd_to_run = cmd.is_a?(String) ? cmd.split(/\s/).first : cmd.first
if Facter.value('osfamily') == 'Suse' && @resource[:password]
cmd_to_run = cmd.is_a?(String) ? cmd.split(%r{\s}).first : cmd.first
if cmd_to_run == command_keytool
cmd << '-srcstorepass' << @resource[:password]
cmd << '-deststorepass' << @resource[:password]
end
end

# Now run the command
options = {:failonfail => true, :combine => true}
options = { failonfail: true, combine: true }
output = nil
begin
Timeout::timeout(@resource[:keytool_timeout], Timeout::Error) do
Timeout.timeout(@resource[:keytool_timeout], Timeout::Error) do
output = if stdinfile
withenv.call(env) do
exec_method.call(cmd, options.merge(:stdinfile => stdinfile.path))
exec_method.call(cmd, options.merge(stdinfile: stdinfile.path))
end
else
withenv.call(env) do
Expand All @@ -336,21 +332,20 @@ def run_command(cmd, target=false, stdinfile=false, env={})
end
end
rescue Timeout::Error
raise Puppet::Error.new("Timed out waiting for '#{@resource[:name]}' to run keytool")
raise Puppet::Error, "Timed out waiting for '#{@resource[:name]}' to run keytool"
end

# for previously empty files, restore the umask, mode, owner and group.
# The funky double-take check is because on Suse defined? doesn't seem
# to behave quite the same as on Debian, RedHat
if target and (defined? stat and stat)
if target and (defined? stat and stat) # rubocop:disable Style/AndOr : Changing 'and' to '&&' causes test failures.
File.umask(umask)
# Need to change group ownership before mode to prevent making the file
# accessible to the wrong group.
File.chown(stat.uid, stat.gid, target)
File.chmod(stat.mode, target)
end

return output
output
end

end