c#获取ssl证书有效性_SSL证书:证书有效期及证书链获取
importdatetimeimportsocketimportjsonimportrefrom OpenSSL importSSLimportlogging”””pip install pyOpenSSL”””
defchoice2dict(choices):”””:param choices: [(‘a’, ‘1’), (‘b’, ‘2’),]
”””trans=dict()for key, value inchoices:ifisinstance(key, bytes):
key=key.decode()ifisinstance(value, bytes):
value=value.decode()
trans[str(key)]=valuereturntrans#该类可以实现基本功能, 但优化空间非常大
classSSLCertificateAnalyzer(object):def __init__(self, host: str, port: int, domain: str, purpose=’extranet’):
self._result={}
self.host=host
self.port=port
self.domain=domain
self.purpose=purpose
self.sock=Nonedefget_result(self):returnself._resultdefdoing(self)
context=SSL.Context(SSL.SSLv23_METHOD)
s=socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.settimeout(15)
self.sock= SSL.Connection(context=context, socket=s)
self.sock.connect((self.host, self.port))
self.sock.setblocking(1)
self.sock.do_handshake()
self.construct_result()exceptException as e:
logging.error(e)
self._result={‘issuer_cn’: ‘’, ‘cert_type’: ‘’, ‘due_date’: ‘’, ‘serial_number’: ‘’, ‘subject_cn’: ‘’,’has_expired’: ‘’, ‘extension_subject_dns’: ‘’, ‘cn_matched’: ‘’, ‘cert_chain’: ‘’,’check_all’: ‘Connect to the server failed’}defconstruct_result(self):
x509=self.sock.get_peer_certificate()
result=self.analysis_certificate_x509(x509)
cert_chain_json=self.get_peer_cert_chain()
self._result.update(result)
self._result[‘cert_chain’] =cert_chain_jsonif self._result[‘has_expired’] == ‘Yes’:
self._result[‘check_all’] = ‘Expired’
else:
self._result[‘check_all’] = ‘Good’
if not self._result[‘cert_chain’]:
self._result[‘check_all’] += ‘, No certificate chain’
if self._result[‘cn_matched’] == ‘No’:
self._result[‘check_all’] += ‘, CN not matched’
if self._result[‘cert_type’] == ‘self-signed’ and self.purpose == ‘extranet’:
self._result[‘check_all’] += ‘, self-signed’
defget_peer_cert_chain(self):
cert_chain=self.sock.get_peer_cert_chain()
cert_chain_result=list()for x509 incert_chain:
result=self.analysis_certificate_x509(x509)
cert_chain_result.append(result)return json.dumps(cert_chain_result) if cert_chain_result else ‘’
defget_cn_matched(self, flag, subject_cn)
_convert= re.sub(r’\*\.’, ‘.*?[.]‘, subject_cn)
pattern= ‘(‘ + _convert + ‘)(.*)’
ifre.search(pattern, self.domain, re.I):
flag= ‘Yes’
returnflagdefanalysis_certificate_x509(self, x509):
cn_matched= ‘No’result={‘issuer_cn’: ‘’, ‘cert_type’: ‘’, ‘due_date’: ‘’, ‘serial_number’: ‘serial_number’,’subject_cn’: ‘’, ‘has_expired’: ‘No’, ‘extension_subject_dns’: ‘’, ‘cn_matched’: cn_matched
}try:
issuer=choice2dict(x509.get_issuer().get_components())
issuer_cn= issuer[‘CN’] if ‘CN’ in issuer else ‘’
if ‘lenovo’ in issuer_cn.lower() or ‘local’ inissuer_cn.lower():
cert_type= ‘self-signed’
else:
cert_type= ‘commercial’result[‘issuer_cn’] =issuer_cn
result[‘cert_type’] =cert_typeexceptException as e:
logging.warning(e)try:
subject=choice2dict(x509.get_subject().get_components())
result[‘subject_cn’] = subject[‘CN’] if ‘CN’ in subject else ‘’cn_matched= self.get_cn_matched(cn_matched, result[‘subject_cn’])exceptException as e:
logging.warning(e)try:
not_after=x509.get_notAfter()#due_date = datetime.datetime.strptime(not_after[:14], ‘%Y%m%d%H%M%S’)
due_date =datetime.datetime(
year=int(not_after[0:4]), month=int(not_after[4:6]), day=int(not_after[6:8]),
hour=int(not_after[8:10]), minute=int(not_after[10:12]), second=int(not_after[10:12])
)ifisinstance(due_date, datetime.datetime):
result[‘due_date’] = due_date.strftime(‘%Y-%m-%d %H:%M:%S’)ifisinstance(due_date, datetime.date):
result[‘due_date’] = due_date.strftime(‘%Y-%m-%d %H:%M:%S’)exceptException as e:passresult[‘cn_matched’] = ‘No’result[‘has_expired’] = ‘Yes’result[‘serial_number’] = ‘’
try:
x509_extension=x509.get_extension(0)
x509_extension_short_name=x509_extension.get_short_name()if x509_extension_short_name == ‘subjectAltName’
x509_extension_subject_alt_name=x509_extension._subjectAltNameString()if ‘:’ inx509_extension_subject_alt_name:
extension_subject_dns= x509_extension_subject_alt_name.split(‘:’)[1].strip()
result[‘extension_subject_dns’] =extension_subject_dns
cn_matched=self.get_cn_matched(cn_matched, extension_subject_dns)exceptException as e:
logging.warning(e)
result[‘serial_number’] =str(x509.get_serial_number())
result[‘has_expired’] = ‘Yes’ if x509.has_expired() else ‘No’result[‘cn_matched’] =cn_matchedexceptException as e:
logging.error(e)returnresultif __name__ == ‘__main__‘:
sca= SSLCertificateAnalyzer(host=’118.112.225.33’, port=443, domain=’baidu.com’, purpose=’extranet’)
sca.doing()print(sca.get_result())
还没有评论,来说两句吧...