From Daniel Manser, 4 Years ago, written in Python.
Embed
  1. #!/usr/bin/python
  2.  
  3. """
  4. Usage: check_ssl_certificate -H <host> -p <port> [-m <method>]
  5.                      [-c <days>] [-w <days>]
  6.  -h show the help
  7.  -H <HOST>    host/ip to check
  8.  -p <port>    port number
  9.  -m <method>  (SSLv2|SSLv3|SSLv23|TLSv1) defaults to SSLv23
  10.  -c <days>    day threshold for critical
  11.  -w <days>    day threshold for warning
  12.  -n name      Check CN value is valid
  13. """
  14.  
  15. import getopt,sys
  16. import __main__
  17. from OpenSSL import SSL
  18. import socket
  19. import datetime
  20.  
  21. # On debian Based systems requires python-openssl
  22.  
  23. def get_options():
  24.   "get options"
  25.  
  26.   options={'host':'',
  27.            'port':'',
  28.            'method':'SSLv23',
  29.            'critical':5,
  30.            'warning':15,
  31.            'cn':''}
  32.  
  33.   try:
  34.     opts, args = getopt.getopt(sys.argv[1:], "hH:p:m:c:w:n:", ['help', "host", 'port', 'method'])
  35.   except getopt.GetoptError as err:
  36.     # print help information and exit:
  37.     print str(err) # will print something like "option -a not recognized"
  38.     usage()
  39.     sys.exit(2)
  40.   for o, a in opts:
  41.     if o in ("-h", "--help"):
  42.       print __main__.__doc__
  43.       sys.exit()
  44.     elif o in ("-H", "--host"):
  45.       options['host'] = a
  46.       pass
  47.     elif o in ("-p", "--port"):
  48.       options['port'] = a
  49.     elif o in ("-m", "--method"):
  50.       options['method'] = a
  51.     elif o == '-c':
  52.       options['critical'] = int(a)
  53.     elif o == '-w':
  54.       options['warning'] = int(a)
  55.     elif o == '-n':
  56.       options['cn'] = a
  57.     else:
  58.       assert False, "unhandled option"
  59.  
  60.   if (''==options['host'] or
  61.       ''==options['port']):
  62.     print __main__.__doc__
  63.     sys.exit()
  64.  
  65.   if options['critical'] >= options['warning']:
  66.     print "Critical must be smaller then warning"
  67.     print __main__.__doc__
  68.     sys.exit()
  69.  
  70.   return options
  71.  
  72. def main():
  73.   options = get_options()
  74.  
  75.   # Initialize context
  76.   if options['method']=='SSLv3':
  77.     ctx = SSL.Context(SSL.SSLv3_METHOD)
  78.   elif options['method']=='SSLv2':
  79.     ctx = SSL.Context(SSL.SSLv2_METHOD)
  80.   elif options['method']=='SSLv23':
  81.     ctx = SSL.Context(SSL.SSLv23_METHOD)
  82.   else:
  83.     ctx = SSL.Context(SSL.TLSv1_METHOD)
  84.  
  85.   # Set up client
  86.   sock = SSL.Connection(ctx, socket.socket(socket.AF_INET, socket.SOCK_STREAM))
  87.   sock.connect((options['host'], int(options['port'])))
  88.   # Send an EOF
  89.   try:
  90.     sock.send("\x04")
  91.     sock.shutdown()
  92.     peer_cert=sock.get_peer_certificate()
  93.     sock.close()
  94.   except SSL.Error,e:
  95.     print e
  96.  
  97.   exit_status=0
  98.   exit_message=[]
  99.  
  100.   cur_date = datetime.datetime.utcnow()
  101.   cert_nbefore = datetime.datetime.strptime(peer_cert.get_notBefore(),'%Y%m%d%H%M%SZ')
  102.   cert_nafter = datetime.datetime.strptime(peer_cert.get_notAfter(),'%Y%m%d%H%M%SZ')
  103.  
  104.   expire_days = int((cert_nafter - cur_date).days)
  105.  
  106.   if cert_nbefore > cur_date:
  107.     if exit_status < 2:
  108.       exit_status = 2
  109.     exit_message.append('C: cert is not valid')
  110.   elif expire_days < 0:
  111.     if exit_status < 2:
  112.       exit_status = 2
  113.     exit_message.append('Expire critical (expired)')
  114.   elif options['critical'] > expire_days:
  115.     if exit_status < 2:
  116.       exit_status = 2
  117.     exit_message.append('Expire critical')
  118.   elif options['warning'] > expire_days:
  119.     if exit_status < 1:
  120.       exit_status = 1
  121.     exit_message.append('Expire warning')
  122.   else:
  123.     exit_message.append('Expire OK')
  124.  
  125.   exit_message.append('['+str(expire_days)+'d]')
  126.  
  127.   for part in peer_cert.get_subject().get_components():
  128.     if part[0]=='CN':
  129.       cert_cn=part[1]
  130.  
  131.   if options['cn']!='' and options['cn'].lower()!=cert_cn.lower():
  132.     if exit_status < 2:
  133.       exit_status = 2
  134.     exit_message.append(' - CN mismatch')
  135.   else:
  136.     exit_message.append(' - CN OK')
  137.  
  138.   exit_message.append(' - cn:'+cert_cn)
  139.  
  140.   print ''.join(exit_message)
  141.   sys.exit(exit_status)
  142.  
  143. if __name__ == "__main__":
  144.   main()