]> git.openstreetmap.org Git - chef.git/blob - cookbooks/letsencrypt/files/default/bin/check-certificate
planet: only rate limit files else apache segfault
[chef.git] / cookbooks / letsencrypt / files / default / bin / check-certificate
1 #!/usr/bin/ruby
2
3 require "socket"
4 require "openssl"
5
6 host = ARGV.shift
7 address = ARGV.shift
8 domains = ARGV
9
10 context = OpenSSL::SSL::SSLContext.new
11 context.verify_mode = OpenSSL::SSL::VERIFY_NONE
12
13 begin
14   socket = TCPSocket.new(address, 443)
15
16   ssl = OpenSSL::SSL::SSLSocket.new(socket, context)
17   ssl.sync_close = true
18   ssl.hostname = domains.first
19   ssl.connect
20 rescue StandardError => e
21   puts "Error connecting to #{host}: #{e.message}"
22 end
23
24 if ssl
25   certificate = ssl.peer_cert
26
27   if Time.now < certificate.not_before
28     puts "Certificate #{domains.first} on #{host} not valid until #{certificate.not_before}"
29   elsif certificate.not_after - Time.now < 21 * 86400
30     puts "Certificate #{domains.first} on #{host} expires at #{certificate.not_after}"
31   end
32
33   subject_alt_name = certificate.extensions.find { |ext| ext.oid == "subjectAltName" }
34
35   if subject_alt_name.nil?
36     puts "Certificate #{domains.first} on #{host} has no subjectAltName"
37   else
38     alt_names = subject_alt_name.value.split(/\s*,\s*/).map { |n| n.sub(/^DNS:/, "") }
39
40     domains.each do |domain|
41       if alt_names.include?(domain)
42         alt_names.delete(domain)
43       else
44         puts "Certificate #{domains.first} on #{host} is missing subjectAltName #{domain}"
45       end
46     end
47
48     alt_names.each do |name|
49       puts "Certificate #{domains.first} on #{host} has unexpected subjectAltName #{name}"
50     end
51   end
52
53   ssl.close
54 end