Commit 1c1bb89e authored by Patrick J Cherry's avatar Patrick J Cherry
Browse files

common: Added in available_sets / current_set caching

This makes verbose logging neater.  Also various fixups around for the
binary
parent 537b4d4a
......@@ -45,8 +45,7 @@ opts = GetoptLong.new(
manual = help = false
$VERBOSE = false
prefix = nil
provider = "letsencrypt"
prefix = "/srv"
opts.each do |opt,arg|
case opt
......@@ -69,8 +68,24 @@ if help or manual
exit 0
end
#
# The required spawn a massive stack of warnings in verbose mode. So let's
# hide them.
#
v = $VERBOSE
$VERBOSE = false
require 'symbiosis/domains'
require 'symbiosis/domain/ssl'
require 'symbiosis/ssl'
require 'symbiosis/ssl/letsencrypt'
require 'symbiosis/ssl/selfsigned'
#
# And unhide. Ugh.
#
$VERBOSE = v
domains = []
......@@ -95,41 +110,40 @@ threshold = 14
domains.each do |domain|
puts "* Examining certificates for #{domain.name}" if $VERBOSE
#
# Stage 0: verify and check expiriy
#
cert_fn, key_fn = domain.ssl_find_matching_certificate_and_key
expires_in = nil
set = domain.ssl_current_set
set = domain.ssl_available_sets.last unless set.is_a?(Symbiosis::SSL::Set)
if cert_fn and key_fn
domain.ssl_verify(cert_fn, key_fn)
expires_in = nil
expires_in = ((domain.ssl_certificate.not_after - now)/86400.0).round
if set.is_a?(Symbiosis::SSL::Set)
expires_in = ((set.certificate.not_after - now)/86400.0).round
if expires_in < 14
puts "\t* The certificate is due to expire in #{expires_in} days"
puts "\tThe certificate is due to expire in #{expires_in} days" if $VERBOSE
end
else
puts "\t* No valid certificates found."
puts "\tNo valid certificates found." if $VERBOSE
end
#
# Stage 1: Generate
#
if false == domain.ssl_provider
puts "\t * Skipping because the ssl-provider has been set to false."
elsif (expires_in.is_a?(Integer) and expires_in < threshold) or cert_fn.nil?
puts "\tSkipping because the ssl-provider has been set to false." if $VERBOSE
elsif (expires_in.is_a?(Integer) and expires_in < threshold) or set.nil?
#
# Default to letsencrypt
#
domain.ssl_provider = "letsencrypt" if domain.ssl_provider.nil?
puts "\t * Fetching a new certificate from #{domain.ssl_provider}."
puts "\tFetching a new certificate from #{domain.ssl_provider}." if $VERBOSE
set = domain.ssl_fetch_certificate
set = domain.ssl_fetch_new_certificate
domain.ssl_write_set(set)
end
......@@ -137,8 +151,6 @@ domains.each do |domain|
# Stage 2: Roll over
#
domain.ssl_rollover
end
......
......@@ -110,22 +110,24 @@ module Symbiosis
def ssl_provider
provider = get_param("ssl-provider", self.config_dir)
return false if false == provider
return provider unless provider.is_a?(String)
if provider.nil?
if Symbiosis::SSL::PROVIDERS.first.to_s =~ /.*::([^:]+)$/
provider = $1.downcase
end
unless provider =~ /^[a-z0-9_]+$/
warn "\tBad ssl-provider for #{self.name}" if $VERBOSE
return false
end
return false unless provider.is_a?(String)
provider.chomp
end
def ssl_provider=(provider)
unless provider =~ /^[a-z0-9_]+$/
warn "\tBad ssl-provider for #{self.name}" if $VERBOSE
return false
return nil
end
provider.chomp
set_param("ssl-provider", provider, self.config_dir)
end
#
......@@ -141,8 +143,6 @@ module Symbiosis
if provider_name.is_a?(String)
provider = Symbiosis::SSL::PROVIDERS.find{|k| k.to_s =~ /::#{provider_name}$/i}
else
provider = Symbiosis::SSL::PROVIDERS.first
end
provider
......@@ -211,6 +211,11 @@ module Symbiosis
Process.euid = 0 if Process.uid == 0
Process.egid = 0 if Process.gid == 0
#
# Clear the cache of what is available
#
@ssl_available_sets = nil
return next_set_dir
end
......@@ -241,46 +246,53 @@ module Symbiosis
end
end
this_set = nil
begin
this_set = Symbiosis::SSL::Set.new(self, current_dir)
rescue StandardError => err
warn "\t#{err.to_s} -- ignoring SSL set in #{current_dir} for #{self.name}" if $VERBOSE
return self.ssl_legacy_set
this_set = self.ssl_available_sets.find{|s| s.directory == current_dir}
if this_set.nil?
begin
this_set = Symbiosis::SSL::Set.new(self, current_dir)
this_set = nil unless this_set.verify
rescue Errno::ENOENT, Errno::ENODIR
# do nothing
this_set = nil
rescue StandardError => err
this_set = nil
warn "\t#{err.to_s} -- ignoring SSL set in #{current_dir} for #{self.name}" if $VERBOSE
end
end
begin
this_set.verify(this_set.certificate, this_set.key, this_set.certificate_store, true)
rescue OpenSSL::OpenSSLError => err
warn "\tUnable to verfity set in #{current_dir} for #{self.name}" if $VERBOSE
return self.ssl_legacy_set
end
this_set = self.ssl_legacy_set if this_set.nil?
return self.ssl_legacy_set if this_set.nil?
if this_set.is_a?(Symbiosis::SSL::Set)
puts "\tCurrent set is #{this_set.name}" if $VERBOSE
end
this_set
@ssl_current_set = this_set
end
def ssl_legacy_set
this_set = Symbiosis::SSL::Set.new(self, self.config_dir)
this_set.verify(this_set.certificate, this_set.key, this_set.certificate_store, true)
this_set = nil unless this_set.verify
this_set
rescue OpenSSL::OpenSSLError => err
warn "\t#{err.to_s}" if $VERBOSE
nil
end
#
# Returns the directory
#
def ssl_available_sets
sets = []
@ssl_available_sets ||= []
return @ssl_available_sets unless @ssl_available_sets.empty?
Dir.glob(File.join(self.config_dir, 'ssl' ,'*')).each do |cert_dir|
Dir.glob(File.join(self.config_dir, 'ssl' ,'*')).sort.each do |cert_dir|
this_set = Symbiosis::SSL::Set.new(self, cert_dir)
begin
this_set = Symbiosis::SSL::Set.new(self, cert_dir)
rescue Errno::ENOENT, Errno::ENOTDIR
next
end
#
# Always miss out the "current" set
......@@ -290,17 +302,12 @@ module Symbiosis
#
# If this certificate verifies, add it to our list
#
begin
this_set.verify(this_set.certificate, this_set.key, this_set.certificate_store, true)
rescue OpenSSL::OpenSSLError => err
warn "\t#{err.to_s}" if $VERBOSE
next
end
next unless this_set.verify
sets << this_set
@ssl_available_sets << this_set
end
return sets.sort
return @ssl_available_sets.sort!
end
#
......@@ -310,7 +317,7 @@ module Symbiosis
#
def ssl_rollover
current = self.ssl_current_set
latest = self.ssl_available_sets.last
latest = self.ssl_available_sets.sort.last
if latest.nil?
warn "\tNo valid sets of certificates found." if $VERBOSE
......@@ -320,7 +327,7 @@ module Symbiosis
#
# If the current certificate is current, do nothing.
#
return false if current.name == latest.name
return false if current and current.name == latest.name
current_dir = File.join(self.config_dir, "ssl", "current")
......@@ -348,6 +355,11 @@ module Symbiosis
Process.euid = 0 if Process.uid == 0
Process.egid = 0 if Process.gid == 0
#
# Update our latest
#
@ssl_current_set = latest
return true
end
......
......@@ -20,7 +20,7 @@ module Symbiosis
raise Errno::ENOENT.new directory unless File.exist?(directory)
raise Errno::ENOTDIR.new directory unless File.directory?(directory)
@directory = directory
@directory = File.expand_path(directory)
@domain = domain
if @directory == @domain.config_dir
......@@ -71,7 +71,7 @@ module Symbiosis
return OpenSSL::X509::Certificate.new(data)
rescue OpenSSL::OpenSSLError => err
warn "\tCould not parse data in #{self.certificate_file}: #{err}"
warn "\tSSL set #{name}: Could not parse data in #{self.certificate_file}: #{err}"
return nil
end
......@@ -109,7 +109,7 @@ module Symbiosis
return OpenSSL::PKey::RSA.new(data)
rescue OpenSSL::OpenSSLError => err
warn "\tCould not parse data in #{self.key_file}: #{err}"
warn "\tSSL set #{name}: Could not parse data in #{self.key_file}: #{err}"
return nil
end
......@@ -156,7 +156,7 @@ module Symbiosis
begin
certificate_store.add_file(chain_file) unless chain_file.nil?
rescue OpenSSL::X509::StoreError
warn "\tUnable to add chain file to the store."
warn "\tSSL set #{name}: Unable to add chain file to the store."
end
certificate_store
end
......@@ -324,7 +324,6 @@ module Symbiosis
return false
end
#
# Firstly check that the certificate is valid for the domain or one of its aliases.
#
......@@ -333,7 +332,7 @@ module Symbiosis
if strict_checking
raise OpenSSL::X509::CertificateError, msg
else
warn "\t#{msg}" if $VERBOSE
warn "\tSSL set #{name}: #{msg}" if $VERBOSE
end
end
......@@ -345,7 +344,7 @@ module Symbiosis
if strict_checking
raise OpenSSL::X509::CertificateError, msg
else
warn "\t#{msg}" if $VERBOSE
warn "\tSSL set #{name}: #{msg}" if $VERBOSE
end
end
......@@ -354,7 +353,7 @@ module Symbiosis
if strict_checking
raise OpenSSL::X509::CertificateError, msg
else
warn "\t#{msg}" if $VERBOSE
warn "\tSSL set #{name}: #{msg}" if $VERBOSE
end
end
......@@ -372,14 +371,14 @@ module Symbiosis
# certificate is self-signed.
#
if certificate.verify(key)
puts "\tUsing a self-signed certificate for #{@domain.name}." if $VERBOSE
puts "\tSSL set #{name}: self-signed certificate for #{@domain.name}." if $VERBOSE
#
# Otherwise see if we can verify it using the certificate store,
# including any bundle that has been uploaded.
#
elsif store.is_a?(OpenSSL::X509::Store) and store.verify(certificate)
puts "\tUsing certificate signed by #{certificate.issuer.to_s} for #{@domain.name}" if $VERBOSE
puts "\tSSL set #{name}: certificate signed by \"#{certificate.issuer.to_s}\" for #{@domain.name}" if $VERBOSE
#
# If we can't verify -- raise an error if strict_checking is enabled
......@@ -389,7 +388,7 @@ module Symbiosis
if strict_checking
raise OpenSSL::X509::CertificateError, msg
else
warn "\t#{msg}" if $VERBOSE
warn "\tSSL set #{name}: #{msg}" if $VERBOSE
end
end
......
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment