def update(self, certificate):
"""Process the certificate to be verified.
Raises an exception if the certificate is invalid. Stores it
otherwise.
:param certificate: the cryptography certificate to be verified
:raises: SignatureVerificationError if the certificate is not of the
right type or if it is outside its valid date range.
"""
if not isinstance(certificate, x509.Certificate):
raise exception.SignatureVerificationError(
"The certificate must be an x509.Certificate object."
)
if self._enforce_valid_dates:
if not is_within_valid_dates(certificate):
raise exception.SignatureVerificationError(
"The certificate is outside its valid date range."
)
self._signed_certificate = certificate
python类Certificate()的实例源码
def test_verify_invalid_certificate(self, mock_utcnow, mock_get_cert):
mock_utcnow.return_value = datetime.datetime(2017, 1, 1)
certs = self.load_certificates(
['self_signed_cert.pem', 'self_signed_cert.der',
'orphaned_cert.pem']
)
mock_get_cert.side_effect = certs
cert_uuid = '3'
trusted_cert_uuids = ['1', '2']
self.assertRaisesRegex(
exception.SignatureVerificationError,
"Certificate chain building failed. Could not locate the "
"signing certificate for the base certificate in the set of "
"trusted certificates.",
certificate_utils.verify_certificate,
None,
cert_uuid,
trusted_cert_uuids
)
def test_verify_valid_certificate_with_no_root(self, mock_utcnow,
mock_get_cert):
mock_utcnow.return_value = datetime.datetime(2017, 1, 1)
# Test verifying a valid certificate against an empty list of trusted
# certificates.
certs = self.load_certificates(['signed_cert.pem'])
mock_get_cert.side_effect = certs
cert_uuid = '3'
trusted_cert_uuids = []
self.assertRaisesRegex(
exception.SignatureVerificationError,
"Certificate chain building failed. Could not locate the "
"signing certificate for the base certificate in the set of "
"trusted certificates.",
certificate_utils.verify_certificate,
None,
cert_uuid,
trusted_cert_uuids
)
def from_cryptography(cls, crypto_cert):
"""
Construct based on a ``cryptography`` *crypto_cert*.
:param crypto_key: A ``cryptography`` X.509 certificate.
:type crypto_key: ``cryptography.x509.Certificate``
:rtype: PKey
.. versionadded:: 17.1.0
"""
if not isinstance(crypto_cert, x509.Certificate):
raise TypeError("Must be a certificate")
cert = cls()
cert._x509 = crypto_cert._x509
return cert
def from_cryptography(cls, crypto_cert):
"""
Construct based on a ``cryptography`` *crypto_cert*.
:param crypto_key: A ``cryptography`` X.509 certificate.
:type crypto_key: ``cryptography.x509.Certificate``
:rtype: PKey
.. versionadded:: 17.1.0
"""
if not isinstance(crypto_cert, x509.Certificate):
raise TypeError("Must be a certificate")
cert = cls()
cert._x509 = crypto_cert._x509
return cert
def _assert_admin(self, cert):
if cert is not None:
if isinstance(cert, bytes):
cert = load_certificate(cert_bytes=cert)
if isinstance(cert, x509.Certificate):
host = cert.subject.get_attributes_for_oid(NameOID.COMMON_NAME)[0].value
else:
raise TypeError('cert must be a raw certificate in PEM or DER format or an x509.Certificate instance.')
else:
logger.warning('Admin command received by unauthentified host.')
raise HTTPResponse(
status=401,
body={'message': 'Authentication required'}
)
if host not in self.admin_hosts:
logger.warning('Host %s unauthorized for admin commands.', host)
raise HTTPResponse(
status=403,
body={'message': 'Host {} unauthorized for admin commands'.format(host)}
)
def __verify_x509_signature(self, c, key):
"""Verify the signature of a certificate or CRL 'c' against a
provided public key 'key'."""
verifier = key.verifier(
c.signature, padding.PKCS1v15(),
c.signature_hash_algorithm)
if isinstance(c, x509.Certificate):
data = c.tbs_certificate_bytes
elif isinstance(c, x509.CertificateRevocationList):
data = c.tbs_certlist_bytes
else:
raise AssertionError("Invalid x509 object for "
"signature verification: {0}".format(type(c)))
verifier.update(data)
try:
verifier.verify()
return True
except Exception:
return False
def __repr__(self):
return "<Certificate(subject={0}, ...)>".format(self.subject)
def __eq__(self, other):
if not isinstance(other, x509.Certificate):
return NotImplemented
res = self._backend._lib.X509_cmp(self._x509, other._x509)
return res == 0
def public_key(self):
pkey = self._backend._lib.X509_get_pubkey(self._x509)
if pkey == self._backend._ffi.NULL:
# Remove errors from the stack.
self._backend._consume_errors()
raise ValueError("Certificate public key is of an unknown type")
pkey = self._backend._ffi.gc(pkey, self._backend._lib.EVP_PKEY_free)
return self._backend._evp_pkey_to_public_key(pkey)
def __repr__(self):
return "<Certificate(subject={0}, ...)>".format(self.subject)
def __eq__(self, other):
if not isinstance(other, x509.Certificate):
return NotImplemented
res = self._backend._lib.X509_cmp(self._x509, other._x509)
return res == 0
def __repr__(self):
return "<Certificate(subject={0}, ...)>".format(self.subject)
def __eq__(self, other):
if not isinstance(other, x509.Certificate):
return NotImplemented
res = self._backend._lib.X509_cmp(self._x509, other._x509)
return res == 0
def serial(self):
warnings.warn(
"Certificate serial is deprecated, use serial_number instead.",
utils.DeprecatedIn14,
stacklevel=2
)
return self.serial_number
def public_key(self):
pkey = self._backend._lib.X509_get_pubkey(self._x509)
if pkey == self._backend._ffi.NULL:
# Remove errors from the stack.
self._backend._consume_errors()
raise ValueError("Certificate public key is of an unknown type")
pkey = self._backend._ffi.gc(pkey, self._backend._lib.EVP_PKEY_free)
return self._backend._evp_pkey_to_public_key(pkey)
def __init__(self, certificate_tuples, enforce_valid_dates=True,
enforce_signing_extensions=True,
enforce_path_length=True):
self._signing_certificates = []
for certificate_tuple in certificate_tuples:
certificate_uuid, certificate = certificate_tuple
if not isinstance(certificate, x509.Certificate):
LOG.error(
"A signing certificate must be an x509.Certificate object."
)
continue
if enforce_valid_dates:
if not is_within_valid_dates(certificate):
LOG.warning(
"Certificate '%s' is outside its valid date range and "
"cannot be used as a signing certificate.",
certificate_uuid)
continue
if enforce_signing_extensions:
if not can_sign_certificates(certificate, certificate_uuid):
LOG.warning(
"Certificate '%s' is not configured to act as a "
"signing certificate. It will not be used as a "
"signing certificate.",
certificate_uuid)
continue
self._signing_certificates.append(certificate_tuple)
self._signed_certificate = None
self._enforce_valid_dates = enforce_valid_dates
self._enforce_path_length = enforce_path_length
def test_context_verify_invalid_chain_length(self, mock_utcnow):
mock_utcnow.return_value = datetime.datetime(2017, 11, 1)
certs = self.load_certificates(
['grandparent_cert.pem', 'parent_cert.pem', 'child_cert.pem']
)
cert_tuples = [
('1', certs[0]),
('2', certs[1]),
('3', certs[2])
]
cert = self.load_certificate('grandchild_cert.pem')
context = certificate_utils.CertificateVerificationContext(
cert_tuples
)
context.update(cert)
self.assertRaisesRegex(
exception.SignatureVerificationError,
"Certificate validation failed. The signing certificate '1' is "
"not configured to support certificate chains of sufficient "
"length.",
context.verify
)
context = certificate_utils.CertificateVerificationContext(
cert_tuples,
enforce_path_length=False
)
context.update(cert)
context.verify()
def __repr__(self):
return "<Certificate(subject={0}, ...)>".format(self.subject)
def __eq__(self, other):
if not isinstance(other, x509.Certificate):
return NotImplemented
res = self._backend._lib.X509_cmp(self._x509, other._x509)
return res == 0
def public_key(self):
pkey = self._backend._lib.X509_get_pubkey(self._x509)
if pkey == self._backend._ffi.NULL:
# Remove errors from the stack.
self._backend._consume_errors()
raise ValueError("Certificate public key is of an unknown type")
pkey = self._backend._ffi.gc(pkey, self._backend._lib.EVP_PKEY_free)
return self._backend._evp_pkey_to_public_key(pkey)
def __repr__(self):
return "<Certificate(subject={0}, ...)>".format(self.subject)
def __eq__(self, other):
if not isinstance(other, x509.Certificate):
return NotImplemented
res = self._backend._lib.X509_cmp(self._x509, other._x509)
return res == 0
def __repr__(self):
return "<Certificate(subject={0}, ...)>".format(self.subject)
def __eq__(self, other):
if not isinstance(other, x509.Certificate):
return NotImplemented
res = self._backend._lib.X509_cmp(self._x509, other._x509)
return res == 0
def public_key(self):
pkey = self._backend._lib.X509_get_pubkey(self._x509)
if pkey == self._backend._ffi.NULL:
# Remove errors from the stack.
self._backend._consume_errors()
raise ValueError("Certificate public key is of an unknown type")
pkey = self._backend._ffi.gc(pkey, self._backend._lib.EVP_PKEY_free)
return self._backend._evp_pkey_to_public_key(pkey)
def __repr__(self):
return "<Certificate(subject={0}, ...)>".format(self.subject)
def __eq__(self, other):
if not isinstance(other, x509.Certificate):
return NotImplemented
res = self._backend._lib.X509_cmp(self._x509, other._x509)
return res == 0
def test_convert_to_cryptography_key(self):
cert = load_certificate(FILETYPE_PEM, intermediate_cert_pem)
crypto_cert = cert.to_cryptography()
assert isinstance(crypto_cert, x509.Certificate)
assert crypto_cert.version.value == cert.get_version()
def to_cryptography(self):
"""
Export as a ``cryptography`` certificate.
:rtype: ``cryptography.x509.Certificate``
.. versionadded:: 17.1.0
"""
from cryptography.hazmat.backends.openssl.x509 import _Certificate
backend = _get_backend()
return _Certificate(backend, self._x509)