| Server IP : 185.208.173.17 / Your IP : 87.236.161.98 Web Server : Microsoft-IIS/10.0 System : Windows NT SRV8576125506 10.0 build 26100 (Windows Server 2016) AMD64 User : IUSR ( 0) PHP Version : 7.4.13 Disable Function : NONE MySQL : OFF | cURL : ON | WGET : OFF | Perl : OFF | Python : OFF | Sudo : OFF | Pkexec : OFF Directory : C:/Program Files/MySQL/MySQL Shell 8.0/lib/Python3.13/Lib/site-packages/tests/x509/ |
Upload File : |
# This file is dual licensed under the terms of the Apache License, Version
# 2.0, and the BSD License. See the LICENSE file in the root of this repository
# for complete details.
import binascii
import datetime
import ipaddress
import os
import typing
import pretend
import pytest
from cryptography import x509
from cryptography.hazmat._oid import _OID_NAMES
from cryptography.hazmat.bindings._rust import x509 as rust_x509
from cryptography.hazmat.primitives import hashes
from cryptography.hazmat.primitives.asymmetric import ec, rsa
from cryptography.x509 import (
DNSName,
NameConstraints,
SubjectAlternativeName,
ocsp,
)
from cryptography.x509.extensions import (
ExtensionType,
_key_identifier_from_public_key,
)
from cryptography.x509.oid import (
AuthorityInformationAccessOID,
ExtendedKeyUsageOID,
ExtensionOID,
NameOID,
ObjectIdentifier,
SubjectInformationAccessOID,
)
from ..hazmat.primitives.test_ec import _skip_curve_unsupported
from ..hazmat.primitives.test_rsa import rsa_key_2048
from ..utils import load_vectors_from_file
from .test_x509 import _load_cert
# Make ruff happy since we're importing fixtures that pytest patches in as
# func args
__all__ = ["rsa_key_2048"]
def _make_certbuilder(private_key):
name = x509.Name([x509.NameAttribute(NameOID.COMMON_NAME, "example.org")])
return (
x509.CertificateBuilder()
.subject_name(name)
.issuer_name(name)
.public_key(private_key.public_key())
.serial_number(777)
.not_valid_before(datetime.datetime(1999, 1, 1))
.not_valid_after(datetime.datetime(2020, 1, 1))
)
class TestExtension:
def test_not_an_oid(self):
bc = x509.BasicConstraints(ca=False, path_length=None)
with pytest.raises(TypeError):
x509.Extension("notanoid", True, bc) # type:ignore[arg-type]
def test_critical_not_a_bool(self):
bc = x509.BasicConstraints(ca=False, path_length=None)
with pytest.raises(TypeError):
x509.Extension(
ExtensionOID.BASIC_CONSTRAINTS,
"notabool", # type:ignore[arg-type]
bc,
)
def test_repr(self):
bc = x509.BasicConstraints(ca=False, path_length=None)
ext = x509.Extension(ExtensionOID.BASIC_CONSTRAINTS, True, bc)
assert repr(ext) == (
"<Extension(oid=<ObjectIdentifier(oid=2.5.29.19, name=basicConst"
"raints)>, critical=True, value=<BasicConstraints(ca=False, path"
"_length=None)>)>"
)
def test_eq(self):
ext1 = x509.Extension(
x509.ObjectIdentifier("1.2.3.4"),
False,
x509.BasicConstraints(ca=False, path_length=None),
)
ext2 = x509.Extension(
x509.ObjectIdentifier("1.2.3.4"),
False,
x509.BasicConstraints(ca=False, path_length=None),
)
assert ext1 == ext2
def test_ne(self):
ext1 = x509.Extension(
x509.ObjectIdentifier("1.2.3.4"),
False,
x509.BasicConstraints(ca=False, path_length=None),
)
ext2 = x509.Extension(
x509.ObjectIdentifier("1.2.3.5"),
False,
x509.BasicConstraints(ca=False, path_length=None),
)
ext3 = x509.Extension(
x509.ObjectIdentifier("1.2.3.4"),
True,
x509.BasicConstraints(ca=False, path_length=None),
)
ext4 = x509.Extension(
x509.ObjectIdentifier("1.2.3.4"),
False,
x509.BasicConstraints(ca=True, path_length=None),
)
assert ext1 != ext2
assert ext1 != ext3
assert ext1 != ext4
assert ext1 != object()
def test_hash(self):
ext1 = x509.Extension(
ExtensionOID.BASIC_CONSTRAINTS,
False,
x509.BasicConstraints(ca=False, path_length=None),
)
ext2 = x509.Extension(
ExtensionOID.BASIC_CONSTRAINTS,
False,
x509.BasicConstraints(ca=False, path_length=None),
)
ext3 = x509.Extension(
ExtensionOID.BASIC_CONSTRAINTS,
False,
x509.BasicConstraints(ca=True, path_length=None),
)
assert hash(ext1) == hash(ext2)
assert hash(ext1) != hash(ext3)
class TestTLSFeature:
def test_not_enum_type(self):
with pytest.raises(TypeError):
x509.TLSFeature([3]) # type:ignore[list-item]
def test_empty_list(self):
with pytest.raises(TypeError):
x509.TLSFeature([])
def test_repr(self):
ext1 = x509.TLSFeature([x509.TLSFeatureType.status_request])
assert repr(ext1) == (
"<TLSFeature(features=[<TLSFeatureType.status_request: 5>])>"
)
def test_eq(self):
ext1 = x509.TLSFeature([x509.TLSFeatureType.status_request])
ext2 = x509.TLSFeature([x509.TLSFeatureType.status_request])
assert ext1 == ext2
def test_ne(self):
ext1 = x509.TLSFeature([x509.TLSFeatureType.status_request])
ext2 = x509.TLSFeature([x509.TLSFeatureType.status_request_v2])
ext3 = x509.TLSFeature(
[
x509.TLSFeatureType.status_request,
x509.TLSFeatureType.status_request_v2,
]
)
assert ext1 != ext2
assert ext1 != ext3
assert ext1 != object()
def test_hash(self):
ext1 = x509.TLSFeature([x509.TLSFeatureType.status_request])
ext2 = x509.TLSFeature([x509.TLSFeatureType.status_request])
ext3 = x509.TLSFeature(
[
x509.TLSFeatureType.status_request,
x509.TLSFeatureType.status_request_v2,
]
)
assert hash(ext1) == hash(ext2)
assert hash(ext1) != hash(ext3)
def test_iter(self):
ext1_features = [x509.TLSFeatureType.status_request]
ext1 = x509.TLSFeature(ext1_features)
assert len(ext1) == 1
assert list(ext1) == ext1_features
ext2_features = [
x509.TLSFeatureType.status_request,
x509.TLSFeatureType.status_request_v2,
]
ext2 = x509.TLSFeature(ext2_features)
assert len(ext2) == 2
assert list(ext2) == ext2_features
def test_indexing(self):
ext = x509.TLSFeature(
[
x509.TLSFeatureType.status_request,
x509.TLSFeatureType.status_request_v2,
]
)
assert ext[-1] == ext[1]
assert ext[0] == x509.TLSFeatureType.status_request
def test_public_bytes(self):
ext1 = x509.TLSFeature([x509.TLSFeatureType.status_request])
assert ext1.public_bytes() == b"\x30\x03\x02\x01\x05"
ext2 = x509.TLSFeature([x509.TLSFeatureType.status_request_v2])
assert ext2.public_bytes() == b"\x30\x03\x02\x01\x11"
class TestUnrecognizedExtension:
def test_invalid_oid(self):
with pytest.raises(TypeError):
x509.UnrecognizedExtension(
"notanoid", # type:ignore[arg-type]
b"somedata",
)
def test_eq(self):
ext1 = x509.UnrecognizedExtension(
x509.ObjectIdentifier("1.2.3.4"), b"\x03\x02\x01"
)
ext2 = x509.UnrecognizedExtension(
x509.ObjectIdentifier("1.2.3.4"), b"\x03\x02\x01"
)
assert ext1 == ext2
def test_ne(self):
ext1 = x509.UnrecognizedExtension(
x509.ObjectIdentifier("1.2.3.4"), b"\x03\x02\x01"
)
ext2 = x509.UnrecognizedExtension(
x509.ObjectIdentifier("1.2.3.4"), b"\x03\x02\x02"
)
ext3 = x509.UnrecognizedExtension(
x509.ObjectIdentifier("1.2.3.5"), b"\x03\x02\x01"
)
assert ext1 != ext2
assert ext1 != ext3
assert ext1 != object()
def test_repr(self):
ext1 = x509.UnrecognizedExtension(
x509.ObjectIdentifier("1.2.3.4"), b"\x03\x02\x01"
)
assert repr(ext1) == (
"<UnrecognizedExtension(oid=<ObjectIdentifier(oid=1.2.3.4, "
"name=Unknown OID)>, value=b'\\x03\\x02\\x01')>"
)
def test_hash(self):
ext1 = x509.UnrecognizedExtension(
x509.ObjectIdentifier("1.2.3.4"), b"\x03\x02\x01"
)
ext2 = x509.UnrecognizedExtension(
x509.ObjectIdentifier("1.2.3.4"), b"\x03\x02\x01"
)
ext3 = x509.UnrecognizedExtension(
x509.ObjectIdentifier("1.2.3.5"), b"\x03\x02\x01"
)
assert hash(ext1) == hash(ext2)
assert hash(ext1) != hash(ext3)
def test_public_bytes(self):
ext1 = x509.UnrecognizedExtension(
x509.ObjectIdentifier("1.2.3.5"), b"\x03\x02\x01"
)
assert ext1.public_bytes() == b"\x03\x02\x01"
# The following creates a BasicConstraints extension with an invalid
# value. The serialization code should still handle it correctly by
# special-casing UnrecognizedExtension.
ext2 = x509.UnrecognizedExtension(
x509.oid.ExtensionOID.BASIC_CONSTRAINTS, b"\x03\x02\x01"
)
assert ext2.public_bytes() == b"\x03\x02\x01"
class TestCertificateIssuer:
def test_iter_names(self):
ci = x509.CertificateIssuer(
[x509.DNSName("cryptography.io"), x509.DNSName("crypto.local")]
)
assert len(ci) == 2
assert list(ci) == [
x509.DNSName("cryptography.io"),
x509.DNSName("crypto.local"),
]
def test_indexing(self):
ci = x509.CertificateIssuer(
[
x509.DNSName("cryptography.io"),
x509.DNSName("crypto.local"),
x509.DNSName("another.local"),
x509.RFC822Name("email@another.local"),
x509.UniformResourceIdentifier("http://another.local"),
]
)
assert ci[-1] == ci[4]
assert ci[2:6:2] == [ci[2], ci[4]]
def test_eq(self):
ci1 = x509.CertificateIssuer([x509.DNSName("cryptography.io")])
ci2 = x509.CertificateIssuer([x509.DNSName("cryptography.io")])
assert ci1 == ci2
def test_ne(self):
ci1 = x509.CertificateIssuer([x509.DNSName("cryptography.io")])
ci2 = x509.CertificateIssuer([x509.DNSName("somethingelse.tld")])
assert ci1 != ci2
assert ci1 != object()
def test_repr(self):
ci = x509.CertificateIssuer([x509.DNSName("cryptography.io")])
assert repr(ci) == (
"<CertificateIssuer(<GeneralNames([<DNSName(value="
"'cryptography.io')>])>)>"
)
def test_get_values_for_type(self):
ci = x509.CertificateIssuer([x509.DNSName("cryptography.io")])
names = ci.get_values_for_type(x509.DNSName)
assert names == ["cryptography.io"]
def test_hash(self):
ci1 = x509.CertificateIssuer([x509.DNSName("cryptography.io")])
ci2 = x509.CertificateIssuer([x509.DNSName("cryptography.io")])
ci3 = x509.CertificateIssuer(
[x509.UniformResourceIdentifier("http://something")]
)
assert hash(ci1) == hash(ci2)
assert hash(ci1) != hash(ci3)
def test_public_bytes(self):
ext = x509.CertificateIssuer([x509.DNSName("cryptography.io")])
assert ext.public_bytes() == b"0\x11\x82\x0fcryptography.io"
class TestCRLReason:
def test_invalid_reason_flags(self):
with pytest.raises(TypeError):
x509.CRLReason("notareason") # type:ignore[arg-type]
def test_eq(self):
reason1 = x509.CRLReason(x509.ReasonFlags.unspecified)
reason2 = x509.CRLReason(x509.ReasonFlags.unspecified)
assert reason1 == reason2
def test_ne(self):
reason1 = x509.CRLReason(x509.ReasonFlags.unspecified)
reason2 = x509.CRLReason(x509.ReasonFlags.ca_compromise)
assert reason1 != reason2
assert reason1 != object()
def test_hash(self):
reason1 = x509.CRLReason(x509.ReasonFlags.unspecified)
reason2 = x509.CRLReason(x509.ReasonFlags.unspecified)
reason3 = x509.CRLReason(x509.ReasonFlags.ca_compromise)
assert hash(reason1) == hash(reason2)
assert hash(reason1) != hash(reason3)
def test_repr(self):
reason1 = x509.CRLReason(x509.ReasonFlags.unspecified)
assert repr(reason1) == ("<CRLReason(reason=ReasonFlags.unspecified)>")
def test_public_bytes(self):
ext = x509.CRLReason(x509.ReasonFlags.ca_compromise)
assert ext.public_bytes() == b"\n\x01\x02"
class TestDeltaCRLIndicator:
def test_not_int(self):
with pytest.raises(TypeError):
x509.DeltaCRLIndicator("notanint") # type:ignore[arg-type]
def test_eq(self):
delta1 = x509.DeltaCRLIndicator(1)
delta2 = x509.DeltaCRLIndicator(1)
assert delta1 == delta2
def test_ne(self):
delta1 = x509.DeltaCRLIndicator(1)
delta2 = x509.DeltaCRLIndicator(2)
assert delta1 != delta2
assert delta1 != object()
def test_repr(self):
delta1 = x509.DeltaCRLIndicator(2)
assert repr(delta1) == ("<DeltaCRLIndicator(crl_number=2)>")
def test_hash(self):
delta1 = x509.DeltaCRLIndicator(1)
delta2 = x509.DeltaCRLIndicator(1)
delta3 = x509.DeltaCRLIndicator(2)
assert hash(delta1) == hash(delta2)
assert hash(delta1) != hash(delta3)
def test_public_bytes(self):
ext = x509.DeltaCRLIndicator(2)
assert ext.public_bytes() == b"\x02\x01\x02"
class TestInvalidityDate:
def test_invalid_invalidity_date(self):
with pytest.raises(TypeError):
x509.InvalidityDate("notadate") # type:ignore[arg-type]
def test_eq(self):
invalid1 = x509.InvalidityDate(datetime.datetime(2015, 1, 1, 1, 1))
invalid2 = x509.InvalidityDate(datetime.datetime(2015, 1, 1, 1, 1))
assert invalid1 == invalid2
def test_ne(self):
invalid1 = x509.InvalidityDate(datetime.datetime(2015, 1, 1, 1, 1))
invalid2 = x509.InvalidityDate(datetime.datetime(2015, 1, 1, 1, 2))
assert invalid1 != invalid2
assert invalid1 != object()
def test_repr(self):
invalid1 = x509.InvalidityDate(datetime.datetime(2015, 1, 1, 1, 1))
assert repr(invalid1) == (
"<InvalidityDate(invalidity_date=2015-01-01 01:01:00)>"
)
def test_hash(self):
invalid1 = x509.InvalidityDate(datetime.datetime(2015, 1, 1, 1, 1))
invalid2 = x509.InvalidityDate(datetime.datetime(2015, 1, 1, 1, 1))
invalid3 = x509.InvalidityDate(datetime.datetime(2015, 1, 1, 1, 2))
assert hash(invalid1) == hash(invalid2)
assert hash(invalid1) != hash(invalid3)
def test_public_bytes(self):
ext = x509.InvalidityDate(datetime.datetime(2015, 1, 1, 1, 1))
assert ext.public_bytes() == b"\x18\x0f20150101010100Z"
def test_timezone_aware_api(self):
naive_date = datetime.datetime(2015, 1, 1, 1, 1)
ext_naive = x509.InvalidityDate(invalidity_date=naive_date)
assert ext_naive.invalidity_date_utc == datetime.datetime(
2015, 1, 1, 1, 1, tzinfo=datetime.timezone.utc
)
tz_aware_date = datetime.datetime(
2015,
1,
1,
1,
1,
tzinfo=datetime.timezone(datetime.timedelta(hours=-8)),
)
ext_aware = x509.InvalidityDate(invalidity_date=tz_aware_date)
assert ext_aware.invalidity_date_utc == datetime.datetime(
2015, 1, 1, 9, 1, tzinfo=datetime.timezone.utc
)
class TestNoticeReference:
def test_notice_numbers_not_all_int(self):
with pytest.raises(TypeError):
x509.NoticeReference(
"org",
[1, 2, "three"], # type:ignore[list-item]
)
def test_notice_numbers_none(self):
with pytest.raises(TypeError):
x509.NoticeReference("org", None) # type:ignore[arg-type]
def test_iter_input(self):
numbers = [1, 3, 4]
nr = x509.NoticeReference("org", iter(numbers))
assert list(nr.notice_numbers) == numbers
def test_repr(self):
nr = x509.NoticeReference("org", [1, 3, 4])
assert repr(nr) == (
"<NoticeReference(organization='org', notice_numbers=[1, 3, 4])>"
)
def test_eq(self):
nr = x509.NoticeReference("org", [1, 2])
nr2 = x509.NoticeReference("org", [1, 2])
assert nr == nr2
def test_ne(self):
nr = x509.NoticeReference("org", [1, 2])
nr2 = x509.NoticeReference("org", [1])
nr3 = x509.NoticeReference(None, [1, 2])
assert nr != nr2
assert nr != nr3
assert nr != object()
def test_hash(self):
nr = x509.NoticeReference("org", [1, 2])
nr2 = x509.NoticeReference("org", [1, 2])
nr3 = x509.NoticeReference(None, [1, 2])
assert hash(nr) == hash(nr2)
assert hash(nr) != hash(nr3)
class TestUserNotice:
def test_notice_reference_invalid(self):
with pytest.raises(TypeError):
x509.UserNotice("invalid", None) # type:ignore[arg-type]
def test_notice_reference_none(self):
un = x509.UserNotice(None, "text")
assert un.notice_reference is None
assert un.explicit_text == "text"
def test_repr(self):
un = x509.UserNotice(x509.NoticeReference("org", [1]), "text")
assert repr(un) == (
"<UserNotice(notice_reference=<NoticeReference(organization='"
"org', notice_numbers=[1])>, explicit_text='text')>"
)
def test_eq(self):
nr = x509.NoticeReference("org", [1, 2])
nr2 = x509.NoticeReference("org", [1, 2])
un = x509.UserNotice(nr, "text")
un2 = x509.UserNotice(nr2, "text")
assert un == un2
def test_ne(self):
nr = x509.NoticeReference("org", [1, 2])
nr2 = x509.NoticeReference("org", [1])
un = x509.UserNotice(nr, "text")
un2 = x509.UserNotice(nr2, "text")
un3 = x509.UserNotice(nr, "text3")
assert un != un2
assert un != un3
assert un != object()
def test_hash(self):
nr = x509.NoticeReference("org", [1, 2])
nr2 = x509.NoticeReference("org", [1, 2])
un = x509.UserNotice(nr, "text")
un2 = x509.UserNotice(nr2, "text")
un3 = x509.UserNotice(None, "text")
assert hash(un) == hash(un2)
assert hash(un) != hash(un3)
class TestPolicyInformation:
def test_invalid_policy_identifier(self):
with pytest.raises(TypeError):
x509.PolicyInformation("notanoid", None) # type:ignore[arg-type]
def test_none_policy_qualifiers(self):
pi = x509.PolicyInformation(x509.ObjectIdentifier("1.2.3"), None)
assert pi.policy_identifier == x509.ObjectIdentifier("1.2.3")
assert pi.policy_qualifiers is None
def test_policy_qualifiers(self):
pq = ["string"]
pi = x509.PolicyInformation(x509.ObjectIdentifier("1.2.3"), pq)
assert pi.policy_identifier == x509.ObjectIdentifier("1.2.3")
assert pi.policy_qualifiers == pq
def test_invalid_policy_identifiers(self):
with pytest.raises(TypeError):
x509.PolicyInformation(
x509.ObjectIdentifier("1.2.3"),
[1, 2], # type:ignore[list-item]
)
def test_iter_input(self):
qual = ["foo", "bar"]
pi = x509.PolicyInformation(x509.ObjectIdentifier("1.2.3"), iter(qual))
assert pi.policy_qualifiers is not None
assert list(pi.policy_qualifiers) == qual
def test_repr(self):
pq: typing.List[typing.Union[str, x509.UserNotice]] = [
"string",
x509.UserNotice(None, "hi"),
]
pi = x509.PolicyInformation(x509.ObjectIdentifier("1.2.3"), pq)
assert repr(pi) == (
"<PolicyInformation(policy_identifier=<ObjectIdentifier(oid=1."
"2.3, name=Unknown OID)>, policy_qualifiers=['string', <UserNo"
"tice(notice_reference=None, explicit_text='hi')>])>"
)
def test_eq(self):
pi = x509.PolicyInformation(
x509.ObjectIdentifier("1.2.3"),
["string", x509.UserNotice(None, "hi")],
)
pi2 = x509.PolicyInformation(
x509.ObjectIdentifier("1.2.3"),
["string", x509.UserNotice(None, "hi")],
)
assert pi == pi2
def test_ne(self):
pi = x509.PolicyInformation(x509.ObjectIdentifier("1.2.3"), ["string"])
pi2 = x509.PolicyInformation(
x509.ObjectIdentifier("1.2.3"), ["string2"]
)
pi3 = x509.PolicyInformation(
x509.ObjectIdentifier("1.2.3.4"), ["string"]
)
assert pi != pi2
assert pi != pi3
assert pi != object()
def test_hash(self):
pi = x509.PolicyInformation(
x509.ObjectIdentifier("1.2.3"),
["string", x509.UserNotice(None, "hi")],
)
pi2 = x509.PolicyInformation(
x509.ObjectIdentifier("1.2.3"),
["string", x509.UserNotice(None, "hi")],
)
pi3 = x509.PolicyInformation(x509.ObjectIdentifier("1.2.3"), None)
assert hash(pi) == hash(pi2)
assert hash(pi) != hash(pi3)
class TestCertificatePolicies:
def test_invalid_policies(self):
pq = ["string"]
pi = x509.PolicyInformation(x509.ObjectIdentifier("1.2.3"), pq)
with pytest.raises(TypeError):
x509.CertificatePolicies([1, pi]) # type:ignore[list-item]
def test_iter_len(self):
pq = ["string"]
pi = x509.PolicyInformation(x509.ObjectIdentifier("1.2.3"), pq)
cp = x509.CertificatePolicies([pi])
assert len(cp) == 1
for policyinfo in cp:
assert policyinfo == pi
def test_iter_input(self):
policies = [
x509.PolicyInformation(x509.ObjectIdentifier("1.2.3"), ["string"])
]
cp = x509.CertificatePolicies(iter(policies))
assert list(cp) == policies
def test_repr(self):
pq = ["string"]
pi = x509.PolicyInformation(x509.ObjectIdentifier("1.2.3"), pq)
cp = x509.CertificatePolicies([pi])
assert repr(cp) == (
"<CertificatePolicies([<PolicyInformation(policy_identifier=<O"
"bjectIdentifier(oid=1.2.3, name=Unknown OID)>, policy_qualifi"
"ers=['string'])>])>"
)
def test_eq(self):
pi = x509.PolicyInformation(x509.ObjectIdentifier("1.2.3"), ["string"])
cp = x509.CertificatePolicies([pi])
pi2 = x509.PolicyInformation(
x509.ObjectIdentifier("1.2.3"), ["string"]
)
cp2 = x509.CertificatePolicies([pi2])
assert cp == cp2
def test_ne(self):
pi = x509.PolicyInformation(x509.ObjectIdentifier("1.2.3"), ["string"])
cp = x509.CertificatePolicies([pi])
pi2 = x509.PolicyInformation(
x509.ObjectIdentifier("1.2.3"), ["string2"]
)
cp2 = x509.CertificatePolicies([pi2])
assert cp != cp2
assert cp != object()
def test_indexing(self):
pi = x509.PolicyInformation(x509.ObjectIdentifier("1.2.3"), ["test"])
pi2 = x509.PolicyInformation(x509.ObjectIdentifier("1.2.4"), ["test"])
pi3 = x509.PolicyInformation(x509.ObjectIdentifier("1.2.5"), ["test"])
pi4 = x509.PolicyInformation(x509.ObjectIdentifier("1.2.6"), ["test"])
pi5 = x509.PolicyInformation(x509.ObjectIdentifier("1.2.7"), ["test"])
cp = x509.CertificatePolicies([pi, pi2, pi3, pi4, pi5])
assert cp[-1] == cp[4]
assert cp[2:6:2] == [cp[2], cp[4]]
def test_long_oid(self, backend):
"""
Test that parsing a CertificatePolicies ext with
a very long OID succeeds.
"""
cert = _load_cert(
os.path.join("x509", "bigoid.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(x509.CertificatePolicies)
oid = x509.ObjectIdentifier(
"1.3.6.1.4.1.311.21.8.8950086.10656446.2706058"
".12775672.480128.147.13466065.13029902"
)
assert ext.value[0].policy_identifier == oid
def test_hash(self):
pi = x509.PolicyInformation(x509.ObjectIdentifier("1.2.3"), ["string"])
cp = x509.CertificatePolicies([pi])
pi2 = x509.PolicyInformation(
x509.ObjectIdentifier("1.2.3"), ["string"]
)
cp2 = x509.CertificatePolicies([pi2])
pi3 = x509.PolicyInformation(
x509.ObjectIdentifier("1.2.3"), [x509.UserNotice(None, "text")]
)
cp3 = x509.CertificatePolicies([pi3])
assert hash(cp) == hash(cp2)
assert hash(cp) != hash(cp3)
class TestCertificatePoliciesExtension:
def test_cps_uri_policy_qualifier(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "cp_cps_uri.pem"),
x509.load_pem_x509_certificate,
)
cp = cert.extensions.get_extension_for_oid(
ExtensionOID.CERTIFICATE_POLICIES
).value
assert cp == x509.CertificatePolicies(
[
x509.PolicyInformation(
x509.ObjectIdentifier("2.16.840.1.12345.1.2.3.4.1"),
["http://other.com/cps"],
)
]
)
def test_user_notice_with_notice_reference(self, backend):
cert = _load_cert(
os.path.join(
"x509", "custom", "cp_user_notice_with_notice_reference.pem"
),
x509.load_pem_x509_certificate,
)
cp = cert.extensions.get_extension_for_oid(
ExtensionOID.CERTIFICATE_POLICIES
).value
assert cp == x509.CertificatePolicies(
[
x509.PolicyInformation(
x509.ObjectIdentifier("2.16.840.1.12345.1.2.3.4.1"),
[
"http://example.com/cps",
"http://other.com/cps",
x509.UserNotice(
x509.NoticeReference("my org", [1, 2, 3, 4]),
"thing",
),
],
)
]
)
def test_user_notice_with_explicit_text(self, backend):
cert = _load_cert(
os.path.join(
"x509", "custom", "cp_user_notice_with_explicit_text.pem"
),
x509.load_pem_x509_certificate,
)
cp = cert.extensions.get_extension_for_oid(
ExtensionOID.CERTIFICATE_POLICIES
).value
assert cp == x509.CertificatePolicies(
[
x509.PolicyInformation(
x509.ObjectIdentifier("2.16.840.1.12345.1.2.3.4.1"),
[x509.UserNotice(None, "thing")],
)
]
)
def test_user_notice_no_explicit_text(self, backend):
cert = _load_cert(
os.path.join(
"x509", "custom", "cp_user_notice_no_explicit_text.pem"
),
x509.load_pem_x509_certificate,
)
cp = cert.extensions.get_extension_for_oid(
ExtensionOID.CERTIFICATE_POLICIES
).value
assert cp == x509.CertificatePolicies(
[
x509.PolicyInformation(
x509.ObjectIdentifier("2.16.840.1.12345.1.2.3.4.1"),
[
x509.UserNotice(
x509.NoticeReference("my org", [1, 2, 3, 4]), None
)
],
)
]
)
def test_non_ascii_qualifier(
self, rsa_key_2048: rsa.RSAPrivateKey, backend
):
issuer_private_key = rsa_key_2048
subject_private_key = rsa_key_2048
not_valid_before = datetime.datetime(2002, 1, 1, 12, 1)
not_valid_after = datetime.datetime(2030, 12, 31, 8, 30)
builder = (
x509.CertificateBuilder()
.subject_name(
x509.Name([x509.NameAttribute(NameOID.COUNTRY_NAME, "US")])
)
.issuer_name(
x509.Name([x509.NameAttribute(NameOID.COUNTRY_NAME, "US")])
)
.not_valid_before(not_valid_before)
.not_valid_after(not_valid_after)
.public_key(subject_private_key.public_key())
.serial_number(123)
.add_extension(
x509.CertificatePolicies(
[
x509.PolicyInformation(
x509.ObjectIdentifier("1.2.3"), "🤓"
)
]
),
critical=False,
)
)
with pytest.raises(ValueError, match="Qualifier"):
builder.sign(issuer_private_key, hashes.SHA256(), backend)
def test_public_bytes(self):
ext = x509.CertificatePolicies(
[
x509.PolicyInformation(
x509.ObjectIdentifier("2.16.840.1.12345.1.2.3.4.1"),
[
x509.UserNotice(
x509.NoticeReference("my org", [1, 2, 3, 4]), None
)
],
)
]
)
assert (
ext.public_bytes()
== b"0705\x06\x0b`\x86H\x01\xe09\x01\x02\x03\x04\x010&0$\x06\x08+"
b"\x06\x01\x05\x05\x07\x02\x020\x180\x16\x0c\x06my org0\x0c\x02"
b"\x01\x01\x02\x01\x02\x02\x01\x03\x02\x01\x04"
)
class TestKeyUsage:
def test_key_agreement_false_encipher_decipher_true(self):
with pytest.raises(ValueError):
x509.KeyUsage(
digital_signature=False,
content_commitment=False,
key_encipherment=False,
data_encipherment=False,
key_agreement=False,
key_cert_sign=False,
crl_sign=False,
encipher_only=True,
decipher_only=False,
)
with pytest.raises(ValueError):
x509.KeyUsage(
digital_signature=False,
content_commitment=False,
key_encipherment=False,
data_encipherment=False,
key_agreement=False,
key_cert_sign=False,
crl_sign=False,
encipher_only=True,
decipher_only=True,
)
with pytest.raises(ValueError):
x509.KeyUsage(
digital_signature=False,
content_commitment=False,
key_encipherment=False,
data_encipherment=False,
key_agreement=False,
key_cert_sign=False,
crl_sign=False,
encipher_only=False,
decipher_only=True,
)
def test_properties_key_agreement_true(self):
ku = x509.KeyUsage(
digital_signature=True,
content_commitment=True,
key_encipherment=False,
data_encipherment=False,
key_agreement=False,
key_cert_sign=True,
crl_sign=False,
encipher_only=False,
decipher_only=False,
)
assert ku.digital_signature is True
assert ku.content_commitment is True
assert ku.key_encipherment is False
assert ku.data_encipherment is False
assert ku.key_agreement is False
assert ku.key_cert_sign is True
assert ku.crl_sign is False
def test_key_agreement_true_properties(self):
ku = x509.KeyUsage(
digital_signature=False,
content_commitment=False,
key_encipherment=False,
data_encipherment=False,
key_agreement=True,
key_cert_sign=False,
crl_sign=False,
encipher_only=False,
decipher_only=True,
)
assert ku.key_agreement is True
assert ku.encipher_only is False
assert ku.decipher_only is True
def test_key_agreement_false_properties(self):
ku = x509.KeyUsage(
digital_signature=False,
content_commitment=False,
key_encipherment=False,
data_encipherment=False,
key_agreement=False,
key_cert_sign=False,
crl_sign=False,
encipher_only=False,
decipher_only=False,
)
assert ku.key_agreement is False
with pytest.raises(ValueError):
ku.encipher_only
with pytest.raises(ValueError):
ku.decipher_only
def test_repr_key_agreement_false(self):
ku = x509.KeyUsage(
digital_signature=True,
content_commitment=True,
key_encipherment=False,
data_encipherment=False,
key_agreement=False,
key_cert_sign=True,
crl_sign=False,
encipher_only=False,
decipher_only=False,
)
assert repr(ku) == (
"<KeyUsage(digital_signature=True, content_commitment=True, key_en"
"cipherment=False, data_encipherment=False, key_agreement=False, k"
"ey_cert_sign=True, crl_sign=False, encipher_only=False, decipher_"
"only=False)>"
)
def test_repr_key_agreement_true(self):
ku = x509.KeyUsage(
digital_signature=True,
content_commitment=True,
key_encipherment=False,
data_encipherment=False,
key_agreement=True,
key_cert_sign=True,
crl_sign=False,
encipher_only=False,
decipher_only=False,
)
assert repr(ku) == (
"<KeyUsage(digital_signature=True, content_commitment=True, key_en"
"cipherment=False, data_encipherment=False, key_agreement=True, k"
"ey_cert_sign=True, crl_sign=False, encipher_only=False, decipher_"
"only=False)>"
)
def test_eq(self):
ku = x509.KeyUsage(
digital_signature=False,
content_commitment=False,
key_encipherment=False,
data_encipherment=False,
key_agreement=True,
key_cert_sign=False,
crl_sign=False,
encipher_only=False,
decipher_only=True,
)
ku2 = x509.KeyUsage(
digital_signature=False,
content_commitment=False,
key_encipherment=False,
data_encipherment=False,
key_agreement=True,
key_cert_sign=False,
crl_sign=False,
encipher_only=False,
decipher_only=True,
)
assert ku == ku2
def test_ne(self):
ku = x509.KeyUsage(
digital_signature=False,
content_commitment=False,
key_encipherment=False,
data_encipherment=False,
key_agreement=True,
key_cert_sign=False,
crl_sign=False,
encipher_only=False,
decipher_only=True,
)
ku2 = x509.KeyUsage(
digital_signature=False,
content_commitment=False,
key_encipherment=False,
data_encipherment=False,
key_agreement=False,
key_cert_sign=False,
crl_sign=False,
encipher_only=False,
decipher_only=False,
)
assert ku != ku2
assert ku != object()
def test_hash(self):
ku = x509.KeyUsage(
digital_signature=False,
content_commitment=False,
key_encipherment=False,
data_encipherment=False,
key_agreement=True,
key_cert_sign=False,
crl_sign=False,
encipher_only=False,
decipher_only=True,
)
ku2 = x509.KeyUsage(
digital_signature=False,
content_commitment=False,
key_encipherment=False,
data_encipherment=False,
key_agreement=True,
key_cert_sign=False,
crl_sign=False,
encipher_only=False,
decipher_only=True,
)
ku3 = x509.KeyUsage(
digital_signature=False,
content_commitment=True,
key_encipherment=False,
data_encipherment=False,
key_agreement=False,
key_cert_sign=False,
crl_sign=False,
encipher_only=False,
decipher_only=False,
)
assert hash(ku) == hash(ku2)
assert hash(ku) != hash(ku3)
@pytest.mark.parametrize(
("ext", "serialized"),
[
(
x509.KeyUsage(
digital_signature=False,
content_commitment=True,
key_encipherment=False,
data_encipherment=False,
key_agreement=False,
key_cert_sign=False,
crl_sign=False,
encipher_only=False,
decipher_only=False,
),
b"\x03\x02\x06@",
),
(
x509.KeyUsage(
digital_signature=False,
content_commitment=True,
key_encipherment=False,
data_encipherment=False,
key_agreement=True,
key_cert_sign=False,
crl_sign=False,
encipher_only=False,
decipher_only=True,
),
b"\x03\x03\x07H\x80",
),
(
x509.KeyUsage(
digital_signature=True,
content_commitment=False,
key_encipherment=False,
data_encipherment=False,
key_agreement=True,
key_cert_sign=False,
crl_sign=False,
encipher_only=True,
decipher_only=False,
),
b"\x03\x02\x00\x89",
),
(
x509.KeyUsage(
digital_signature=True,
content_commitment=False,
key_encipherment=False,
data_encipherment=True,
key_agreement=False,
key_cert_sign=True,
crl_sign=False,
encipher_only=False,
decipher_only=False,
),
b"\x03\x02\x02\x94",
),
(
x509.KeyUsage(
digital_signature=False,
content_commitment=False,
key_encipherment=False,
data_encipherment=False,
key_agreement=False,
key_cert_sign=False,
crl_sign=False,
encipher_only=False,
decipher_only=False,
),
b"\x03\x01\x00",
),
],
)
def test_public_bytes(self, ext, serialized):
assert ext.public_bytes() == serialized
class TestSubjectKeyIdentifier:
def test_properties(self):
value = binascii.unhexlify(b"092384932230498bc980aa8098456f6ff7ff3ac9")
ski = x509.SubjectKeyIdentifier(value)
assert ski.digest == value
assert ski.key_identifier == value
def test_repr(self):
ski = x509.SubjectKeyIdentifier(
binascii.unhexlify(b"092384932230498bc980aa8098456f6ff7ff3ac9")
)
ext = x509.Extension(ExtensionOID.SUBJECT_KEY_IDENTIFIER, False, ski)
assert repr(ext) == (
"<Extension(oid=<ObjectIdentifier(oid=2.5.29.14, name=subjectK"
"eyIdentifier)>, critical=False, value=<SubjectKeyIdentifier(d"
"igest=b'\\t#\\x84\\x93\"0I\\x8b\\xc9\\x80\\xaa\\x80\\x98Eoo"
"\\xf7\\xff:\\xc9')>)>"
)
def test_eq(self):
ski = x509.SubjectKeyIdentifier(
binascii.unhexlify(b"092384932230498bc980aa8098456f6ff7ff3ac9")
)
ski2 = x509.SubjectKeyIdentifier(
binascii.unhexlify(b"092384932230498bc980aa8098456f6ff7ff3ac9")
)
assert ski == ski2
def test_ne(self):
ski = x509.SubjectKeyIdentifier(
binascii.unhexlify(b"092384932230498bc980aa8098456f6ff7ff3ac9")
)
ski2 = x509.SubjectKeyIdentifier(
binascii.unhexlify(b"aa8098456f6ff7ff3ac9092384932230498bc980")
)
assert ski != ski2
assert ski != object()
def test_hash(self):
ski1 = x509.SubjectKeyIdentifier(
binascii.unhexlify(b"092384932230498bc980aa8098456f6ff7ff3ac9")
)
ski2 = x509.SubjectKeyIdentifier(
binascii.unhexlify(b"092384932230498bc980aa8098456f6ff7ff3ac9")
)
ski3 = x509.SubjectKeyIdentifier(
binascii.unhexlify(b"aa8098456f6ff7ff3ac9092384932230498bc980")
)
assert hash(ski1) == hash(ski2)
assert hash(ski1) != hash(ski3)
def test_public_bytes(self):
ext = x509.SubjectKeyIdentifier(
binascii.unhexlify(b"092384932230498bc980aa8098456f6ff7ff3ac9")
)
assert (
ext.public_bytes()
== b'\x04\x14\t#\x84\x93"0I\x8b\xc9\x80\xaa\x80\x98Eoo\xf7\xff:'
b"\xc9"
)
class TestAuthorityKeyIdentifier:
def test_authority_cert_issuer_not_generalname(self):
with pytest.raises(TypeError):
x509.AuthorityKeyIdentifier(
b"identifier",
["notname"], # type:ignore[list-item]
3,
)
def test_authority_cert_serial_number_not_integer(self):
dirname = x509.DirectoryName(
x509.Name(
[
x509.NameAttribute(
x509.ObjectIdentifier("2.999.1"), "value1"
),
x509.NameAttribute(
x509.ObjectIdentifier("2.999.2"), "value2"
),
]
)
)
with pytest.raises(TypeError):
x509.AuthorityKeyIdentifier(
b"identifier",
[dirname],
"notanint", # type:ignore[arg-type]
)
def test_authority_issuer_none_serial_not_none(self):
with pytest.raises(ValueError):
x509.AuthorityKeyIdentifier(b"identifier", None, 3)
def test_authority_issuer_not_none_serial_none(self):
dirname = x509.DirectoryName(
x509.Name(
[
x509.NameAttribute(
x509.ObjectIdentifier("2.999.1"), "value1"
),
x509.NameAttribute(
x509.ObjectIdentifier("2.999.2"), "value2"
),
]
)
)
with pytest.raises(ValueError):
x509.AuthorityKeyIdentifier(b"identifier", [dirname], None)
def test_authority_cert_serial_and_issuer_none(self):
aki = x509.AuthorityKeyIdentifier(b"id", None, None)
assert aki.key_identifier == b"id"
assert aki.authority_cert_issuer is None
assert aki.authority_cert_serial_number is None
def test_authority_cert_serial_zero(self):
dns = x509.DNSName("SomeIssuer")
aki = x509.AuthorityKeyIdentifier(b"id", [dns], 0)
assert aki.key_identifier == b"id"
assert aki.authority_cert_issuer == [dns]
assert aki.authority_cert_serial_number == 0
def test_iter_input(self):
dirnames = [
x509.DirectoryName(
x509.Name([x509.NameAttribute(NameOID.COMMON_NAME, "myCN")])
)
]
aki = x509.AuthorityKeyIdentifier(b"digest", iter(dirnames), 1234)
assert aki.authority_cert_issuer is not None
assert list(aki.authority_cert_issuer) == dirnames
def test_repr(self):
dirname = x509.DirectoryName(
x509.Name([x509.NameAttribute(NameOID.COMMON_NAME, "myCN")])
)
aki = x509.AuthorityKeyIdentifier(b"digest", [dirname], 1234)
assert repr(aki) == (
"<AuthorityKeyIdentifier(key_identifier=b'digest', authority_"
"cert_issuer=[<DirectoryName(value=<Name(CN=myCN)>)>], author"
"ity_cert_serial_number=1234)>"
)
def test_eq(self):
dirname = x509.DirectoryName(
x509.Name([x509.NameAttribute(NameOID.COMMON_NAME, "myCN")])
)
aki = x509.AuthorityKeyIdentifier(b"digest", [dirname], 1234)
dirname2 = x509.DirectoryName(
x509.Name([x509.NameAttribute(NameOID.COMMON_NAME, "myCN")])
)
aki2 = x509.AuthorityKeyIdentifier(b"digest", [dirname2], 1234)
assert aki == aki2
def test_ne(self):
dirname = x509.DirectoryName(
x509.Name([x509.NameAttribute(NameOID.COMMON_NAME, "myCN")])
)
dirname5 = x509.DirectoryName(
x509.Name([x509.NameAttribute(NameOID.COMMON_NAME, "aCN")])
)
aki = x509.AuthorityKeyIdentifier(b"digest", [dirname], 1234)
aki2 = x509.AuthorityKeyIdentifier(b"diges", [dirname], 1234)
aki3 = x509.AuthorityKeyIdentifier(b"digest", None, None)
aki4 = x509.AuthorityKeyIdentifier(b"digest", [dirname], 12345)
aki5 = x509.AuthorityKeyIdentifier(b"digest", [dirname5], 12345)
assert aki != aki2
assert aki != aki3
assert aki != aki4
assert aki != aki5
assert aki != object()
def test_hash(self):
dirname = x509.DirectoryName(
x509.Name([x509.NameAttribute(NameOID.COMMON_NAME, "myCN")])
)
aki1 = x509.AuthorityKeyIdentifier(b"digest", [dirname], 1234)
aki2 = x509.AuthorityKeyIdentifier(b"digest", [dirname], 1234)
aki3 = x509.AuthorityKeyIdentifier(b"digest", None, None)
assert hash(aki1) == hash(aki2)
assert hash(aki1) != hash(aki3)
def test_public_bytes(self):
dirname = x509.DirectoryName(
x509.Name([x509.NameAttribute(NameOID.COMMON_NAME, "myCN")])
)
ext = x509.AuthorityKeyIdentifier(b"digest", [dirname], 1234)
assert (
ext.public_bytes()
== b"0!\x80\x06digest\xa1\x13\xa4\x110\x0f1\r0\x0b\x06\x03U\x04"
b"\x03\x0c\x04myCN\x82\x02\x04\xd2"
)
class TestBasicConstraints:
def test_ca_not_boolean(self):
with pytest.raises(TypeError):
x509.BasicConstraints(
ca="notbool", # type:ignore[arg-type]
path_length=None,
)
def test_path_length_not_ca(self):
with pytest.raises(ValueError):
x509.BasicConstraints(ca=False, path_length=0)
def test_path_length_not_int(self):
with pytest.raises(TypeError):
x509.BasicConstraints(
ca=True,
path_length=1.1, # type:ignore[arg-type]
)
with pytest.raises(TypeError):
x509.BasicConstraints(
ca=True,
path_length="notint", # type:ignore[arg-type]
)
def test_path_length_negative(self):
with pytest.raises(TypeError):
x509.BasicConstraints(ca=True, path_length=-1)
def test_repr(self):
na = x509.BasicConstraints(ca=True, path_length=None)
assert repr(na) == ("<BasicConstraints(ca=True, path_length=None)>")
def test_hash(self):
na = x509.BasicConstraints(ca=True, path_length=None)
na2 = x509.BasicConstraints(ca=True, path_length=None)
na3 = x509.BasicConstraints(ca=True, path_length=0)
assert hash(na) == hash(na2)
assert hash(na) != hash(na3)
def test_eq(self):
na = x509.BasicConstraints(ca=True, path_length=None)
na2 = x509.BasicConstraints(ca=True, path_length=None)
assert na == na2
def test_ne(self):
na = x509.BasicConstraints(ca=True, path_length=None)
na2 = x509.BasicConstraints(ca=True, path_length=1)
na3 = x509.BasicConstraints(ca=False, path_length=None)
assert na != na2
assert na != na3
assert na != object()
def test_public_bytes(self):
ext = x509.BasicConstraints(ca=True, path_length=None)
assert ext.public_bytes() == b"0\x03\x01\x01\xff"
class TestExtendedKeyUsage:
def test_not_all_oids(self):
with pytest.raises(TypeError):
x509.ExtendedKeyUsage(["notoid"]) # type:ignore[list-item]
def test_iter_len(self):
eku = x509.ExtendedKeyUsage(
[
x509.ObjectIdentifier("1.3.6.1.5.5.7.3.1"),
x509.ObjectIdentifier("1.3.6.1.5.5.7.3.2"),
]
)
assert len(eku) == 2
assert list(eku) == [
ExtendedKeyUsageOID.SERVER_AUTH,
ExtendedKeyUsageOID.CLIENT_AUTH,
]
def test_iter_input(self):
usages = [
x509.ObjectIdentifier("1.3.6.1.5.5.7.3.1"),
x509.ObjectIdentifier("1.3.6.1.5.5.7.3.2"),
]
aia = x509.ExtendedKeyUsage(iter(usages))
assert list(aia) == usages
def test_repr(self):
eku = x509.ExtendedKeyUsage(
[
x509.ObjectIdentifier("1.3.6.1.5.5.7.3.1"),
x509.ObjectIdentifier("1.3.6.1.5.5.7.3.2"),
]
)
assert repr(eku) == (
"<ExtendedKeyUsage([<ObjectIdentifier(oid=1.3.6.1.5.5.7.3.1, name="
"serverAuth)>, <ObjectIdentifier(oid=1.3.6.1.5.5.7.3.2, name=clien"
"tAuth)>])>"
)
def test_eq(self):
eku = x509.ExtendedKeyUsage(
[x509.ObjectIdentifier("1.3.6"), x509.ObjectIdentifier("1.3.7")]
)
eku2 = x509.ExtendedKeyUsage(
[x509.ObjectIdentifier("1.3.6"), x509.ObjectIdentifier("1.3.7")]
)
assert eku == eku2
def test_ne(self):
eku = x509.ExtendedKeyUsage([x509.ObjectIdentifier("1.3.6")])
eku2 = x509.ExtendedKeyUsage([x509.ObjectIdentifier("1.3.6.1")])
assert eku != eku2
assert eku != object()
def test_hash(self):
eku = x509.ExtendedKeyUsage(
[x509.ObjectIdentifier("1.3.6"), x509.ObjectIdentifier("1.3.7")]
)
eku2 = x509.ExtendedKeyUsage(
[x509.ObjectIdentifier("1.3.6"), x509.ObjectIdentifier("1.3.7")]
)
eku3 = x509.ExtendedKeyUsage([x509.ObjectIdentifier("1.3.6")])
assert hash(eku) == hash(eku2)
assert hash(eku) != hash(eku3)
def test_public_bytes(self):
ext = x509.ExtendedKeyUsage(
[x509.ObjectIdentifier("1.3.6"), x509.ObjectIdentifier("1.3.7")]
)
assert ext.public_bytes() == b"0\x08\x06\x02+\x06\x06\x02+\x07"
class TestExtensions:
def test_no_extensions(self, backend):
cert = _load_cert(
os.path.join("x509", "verisign_md2_root.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions
assert len(ext) == 0
assert list(ext) == []
with pytest.raises(x509.ExtensionNotFound) as exc:
ext.get_extension_for_oid(ExtensionOID.BASIC_CONSTRAINTS)
assert exc.value.oid == ExtensionOID.BASIC_CONSTRAINTS
def test_one_extension(self, backend):
cert = _load_cert(
os.path.join(
"x509", "custom", "basic_constraints_not_critical.pem"
),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(x509.BasicConstraints)
assert ext is not None
assert ext.value.ca is False
def test_duplicate_extension(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "two_basic_constraints.pem"),
x509.load_pem_x509_certificate,
)
with pytest.raises(x509.DuplicateExtension) as exc:
cert.extensions
assert exc.value.oid == ExtensionOID.BASIC_CONSTRAINTS
def test_unsupported_critical_extension(self, backend):
cert = _load_cert(
os.path.join(
"x509", "custom", "unsupported_extension_critical.pem"
),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_oid(
x509.ObjectIdentifier("1.2.3.4")
)
assert isinstance(ext.value, x509.UnrecognizedExtension)
assert ext.value.value == b"value"
def test_unsupported_extension(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "unsupported_extension_2.pem"),
x509.load_pem_x509_certificate,
)
extensions = cert.extensions
assert len(extensions) == 2
assert extensions[0].critical is False
assert extensions[0].oid == x509.ObjectIdentifier(
"1.3.6.1.4.1.41482.2"
)
assert extensions[0].value == x509.UnrecognizedExtension(
x509.ObjectIdentifier("1.3.6.1.4.1.41482.2"),
b"1.3.6.1.4.1.41482.1.2",
)
assert extensions[1].critical is False
assert extensions[1].oid == x509.ObjectIdentifier(
"1.3.6.1.4.1.45724.2.1.1"
)
assert extensions[1].value == x509.UnrecognizedExtension(
x509.ObjectIdentifier("1.3.6.1.4.1.45724.2.1.1"), b"\x03\x02\x040"
)
def test_no_extensions_get_for_class(self, backend):
cert = _load_cert(
os.path.join("x509", "cryptography.io.pem"),
x509.load_pem_x509_certificate,
)
exts = cert.extensions
with pytest.raises(x509.ExtensionNotFound) as exc:
exts.get_extension_for_class(x509.IssuerAlternativeName)
assert exc.value.oid == ExtensionOID.ISSUER_ALTERNATIVE_NAME
def test_unrecognized_extension_for_class(self):
exts = x509.Extensions([])
with pytest.raises(TypeError):
exts.get_extension_for_class(x509.UnrecognizedExtension)
def test_indexing(self, backend):
cert = _load_cert(
os.path.join("x509", "cryptography.io.pem"),
x509.load_pem_x509_certificate,
)
exts = cert.extensions
assert exts[-1] == exts[7]
assert exts[2:6:2] == [exts[2], exts[4]]
def test_one_extension_get_for_class(self, backend):
cert = _load_cert(
os.path.join(
"x509", "custom", "basic_constraints_not_critical.pem"
),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(x509.BasicConstraints)
assert ext is not None
def test_repr(self, backend):
cert = _load_cert(
os.path.join(
"x509", "custom", "basic_constraints_not_critical.pem"
),
x509.load_pem_x509_certificate,
)
assert repr(cert.extensions) == (
"<Extensions([<Extension(oid=<ObjectIdentifier(oid=2.5.29.19, name"
"=basicConstraints)>, critical=False, value=<BasicConstraints(ca=F"
"alse, path_length=None)>)>])>"
)
class TestBasicConstraintsExtension:
def test_ca_true_pathlen_6(self, backend):
cert = _load_cert(
os.path.join(
"x509", "PKITS_data", "certs", "pathLenConstraint6CACert.crt"
),
x509.load_der_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(x509.BasicConstraints)
assert ext is not None
assert ext.critical is True
assert ext.value.ca is True
assert ext.value.path_length == 6
def test_path_length_zero(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "bc_path_length_zero.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(x509.BasicConstraints)
assert ext is not None
assert ext.critical is True
assert ext.value.ca is True
assert ext.value.path_length == 0
def test_ca_true_no_pathlen(self, backend):
cert = _load_cert(
os.path.join("x509", "PKITS_data", "certs", "GoodCACert.crt"),
x509.load_der_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(x509.BasicConstraints)
assert ext is not None
assert ext.critical is True
assert ext.value.ca is True
assert ext.value.path_length is None
def test_ca_false(self, backend):
cert = _load_cert(
os.path.join("x509", "cryptography.io.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(x509.BasicConstraints)
assert ext is not None
assert ext.critical is True
assert ext.value.ca is False
assert ext.value.path_length is None
def test_no_basic_constraints(self, backend):
cert = _load_cert(
os.path.join(
"x509",
"PKITS_data",
"certs",
"ValidCertificatePathTest1EE.crt",
),
x509.load_der_x509_certificate,
)
with pytest.raises(x509.ExtensionNotFound):
cert.extensions.get_extension_for_oid(
ExtensionOID.BASIC_CONSTRAINTS
)
def test_basic_constraint_not_critical(self, backend):
cert = _load_cert(
os.path.join(
"x509", "custom", "basic_constraints_not_critical.pem"
),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(x509.BasicConstraints)
assert ext is not None
assert ext.critical is False
assert ext.value.ca is False
class TestSubjectKeyIdentifierExtension:
def test_subject_key_identifier(self, backend):
cert = _load_cert(
os.path.join("x509", "PKITS_data", "certs", "GoodCACert.crt"),
x509.load_der_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(
x509.SubjectKeyIdentifier
)
ski = ext.value
assert ext is not None
assert ext.critical is False
assert ski.digest == binascii.unhexlify(
b"580184241bbc2b52944a3da510721451f5af3ac9"
)
def test_no_subject_key_identifier(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "bc_path_length_zero.pem"),
x509.load_pem_x509_certificate,
)
with pytest.raises(x509.ExtensionNotFound):
cert.extensions.get_extension_for_oid(
ExtensionOID.SUBJECT_KEY_IDENTIFIER
)
def test_from_rsa_public_key(self, backend):
cert = _load_cert(
os.path.join("x509", "PKITS_data", "certs", "GoodCACert.crt"),
x509.load_der_x509_certificate,
)
ext = cert.extensions.get_extension_for_oid(
ExtensionOID.SUBJECT_KEY_IDENTIFIER
)
ski = x509.SubjectKeyIdentifier.from_public_key(cert.public_key())
assert ext.value == ski
@pytest.mark.supported(
only_if=lambda backend: backend.dsa_supported(),
skip_message="Does not support DSA.",
)
def test_from_dsa_public_key(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "dsa_selfsigned_ca.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_oid(
ExtensionOID.SUBJECT_KEY_IDENTIFIER
)
ski = x509.SubjectKeyIdentifier.from_public_key(cert.public_key())
assert ext.value == ski
def test_invalid_bit_string_padding_from_public_key(self, backend):
data = load_vectors_from_file(
filename=os.path.join(
"asymmetric",
"DER_Serialization",
"dsa_public_key_invalid_bit_string.der",
),
loader=lambda data: data.read(),
mode="rb",
)
pretend_key = pretend.stub(public_bytes=lambda x, y: data)
with pytest.raises(ValueError):
_key_identifier_from_public_key(pretend_key)
# The previous value is invalid for 2 reasons: a) it's got non-zero
# padding bits (i.e. the first byte of the value is not zero), b) the
# padding bits aren't all set to zero (i.e. the last bits of the value)
# Here we swap the last byte out with zeros so we can hit both error
# checks.
pretend_key = pretend.stub(
public_bytes=lambda x, y: data[:-1] + b"\x00"
)
with pytest.raises(ValueError, match="Invalid public key encoding"):
_key_identifier_from_public_key(pretend_key)
def test_from_ec_public_key(self, backend):
_skip_curve_unsupported(backend, ec.SECP384R1())
cert = _load_cert(
os.path.join("x509", "ecdsa_root.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_oid(
ExtensionOID.SUBJECT_KEY_IDENTIFIER
)
ski = x509.SubjectKeyIdentifier.from_public_key(cert.public_key())
assert ext.value == ski
@pytest.mark.supported(
only_if=lambda backend: backend.ed25519_supported(),
skip_message="Requires OpenSSL with Ed25519 support",
)
def test_from_ed25519_public_key(self, backend):
cert = _load_cert(
os.path.join("x509", "ed25519", "root-ed25519.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_oid(
ExtensionOID.SUBJECT_KEY_IDENTIFIER
)
ski = x509.SubjectKeyIdentifier.from_public_key(cert.public_key())
assert ext.value == ski
@pytest.mark.supported(
only_if=lambda backend: backend.ed448_supported(),
skip_message="Requires OpenSSL with Ed448 support",
)
def test_from_ed448_public_key(self, backend):
cert = _load_cert(
os.path.join("x509", "ed448", "root-ed448.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_oid(
ExtensionOID.SUBJECT_KEY_IDENTIFIER
)
ski = x509.SubjectKeyIdentifier.from_public_key(cert.public_key())
assert ext.value == ski
class TestKeyUsageExtension:
def test_no_key_usage(self, backend):
cert = _load_cert(
os.path.join("x509", "verisign_md2_root.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions
with pytest.raises(x509.ExtensionNotFound) as exc:
ext.get_extension_for_oid(ExtensionOID.KEY_USAGE)
assert exc.value.oid == ExtensionOID.KEY_USAGE
def test_all_purposes(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "all_key_usages.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(x509.KeyUsage)
assert ext is not None
ku = ext.value
assert ku.digital_signature is True
assert ku.content_commitment is True
assert ku.key_encipherment is True
assert ku.data_encipherment is True
assert ku.key_agreement is True
assert ku.key_cert_sign is True
assert ku.crl_sign is True
assert ku.encipher_only is True
assert ku.decipher_only is True
def test_key_cert_sign_crl_sign(self, backend):
cert = _load_cert(
os.path.join(
"x509", "PKITS_data", "certs", "pathLenConstraint6CACert.crt"
),
x509.load_der_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(x509.KeyUsage)
assert ext is not None
assert ext.critical is True
ku = ext.value
assert ku.digital_signature is False
assert ku.content_commitment is False
assert ku.key_encipherment is False
assert ku.data_encipherment is False
assert ku.key_agreement is False
assert ku.key_cert_sign is True
assert ku.crl_sign is True
class TestPrivateKeyUsagePeriodExtension:
def test_not_validity(self):
with pytest.raises(TypeError):
x509.PrivateKeyUsagePeriod("notValidBefore", "notValidAfter") # type:ignore[arg-type]
def test_repr(self):
period = x509.PrivateKeyUsagePeriod(
not_before=datetime.datetime(2012, 1, 1),
not_after=datetime.datetime(2013, 1, 1),
)
assert repr(period) == (
"<PrivateKeyUsagePeriod(not_before=2012-01-01 00:00:00, "
"not_after=2013-01-01 00:00:00)>"
)
def test_eq(self):
period = x509.PrivateKeyUsagePeriod(
not_before=datetime.datetime(2012, 1, 1),
not_after=datetime.datetime(2013, 1, 1),
)
period2 = x509.PrivateKeyUsagePeriod(
not_before=datetime.datetime(2012, 1, 1),
not_after=datetime.datetime(2013, 1, 1),
)
assert period == period2
def test_ne(self):
period = x509.PrivateKeyUsagePeriod(
not_before=datetime.datetime(2012, 1, 1),
not_after=datetime.datetime(2013, 1, 1),
)
period2 = x509.PrivateKeyUsagePeriod(
not_before=datetime.datetime(2012, 1, 1),
not_after=datetime.datetime(2014, 1, 1),
)
assert period != period2
assert period != object()
def test_hash(self):
period = x509.PrivateKeyUsagePeriod(
not_before=datetime.datetime(2012, 1, 1),
not_after=datetime.datetime(2013, 1, 1),
)
period2 = x509.PrivateKeyUsagePeriod(
not_before=datetime.datetime(2012, 1, 1),
not_after=datetime.datetime(2013, 1, 1),
)
period3 = x509.PrivateKeyUsagePeriod(
not_before=datetime.datetime(2012, 1, 1),
not_after=datetime.datetime(2014, 1, 1),
)
assert hash(period) == hash(period2)
assert hash(period) != hash(period3)
def test_both_none(self):
with pytest.raises(ValueError):
x509.PrivateKeyUsagePeriod(
not_before=None,
not_after=None,
)
def test_invalid_not_after_type(self):
with pytest.raises(TypeError):
x509.PrivateKeyUsagePeriod(
not_before=datetime.datetime(2012, 1, 1),
not_after="invalid type", # type:ignore[arg-type]
)
def test_not_before_after_not_after(self):
with pytest.raises(
ValueError, match="not_before must be before not_after"
):
x509.PrivateKeyUsagePeriod(
not_before=datetime.datetime(2014, 1, 1),
not_after=datetime.datetime(2013, 1, 1),
)
def test_public_bytes(self):
period = x509.PrivateKeyUsagePeriod(
not_before=datetime.datetime(2012, 1, 1, 0, 0, 0),
not_after=datetime.datetime(2013, 1, 1, 0, 0, 0),
)
serialized = period.public_bytes()
assert serialized == (
b"\x30\x22\x80\x0f\x32\x30\x31\x32\x30\x31\x30\x31\x30"
b"\x30\x30\x30\x30\x30\x5a\x81\x0f\x32\x30\x31\x33\x30"
b"\x31\x30\x31\x30\x30\x30\x30\x30\x30\x5a"
)
def test_only_not_before(self):
period = x509.PrivateKeyUsagePeriod(
not_before=datetime.datetime(2012, 1, 1),
not_after=None,
)
assert period.not_before == datetime.datetime(2012, 1, 1)
assert period.not_after is None
serialized = period.public_bytes()
assert serialized == (
b"\x30\x11\x80\x0f\x32\x30\x31\x32\x30\x31\x30\x31\x30"
b"\x30\x30\x30\x30\x30\x5a"
)
def test_only_not_after(self):
period = x509.PrivateKeyUsagePeriod(
not_before=None,
not_after=datetime.datetime(2013, 1, 1),
)
assert period.not_before is None
assert period.not_after == datetime.datetime(2013, 1, 1)
serialized = period.public_bytes()
assert serialized == (
b"\x30\x11\x81\x0f\x32\x30\x31\x33\x30\x31\x30\x31\x30"
b"\x30\x30\x30\x30\x30\x5a"
)
def test_load_pem_certificate_with_extension(self, backend):
cert_path = os.path.join(
"x509", "custom", "private_key_usage_period_both_dates.pem"
)
cert = load_vectors_from_file(
cert_path,
lambda pemdata: x509.load_pem_x509_certificate(pemdata.read()),
mode="rb",
)
ext = cert.extensions.get_extension_for_class(
x509.PrivateKeyUsagePeriod
)
assert ext.critical is False
assert ext.value.not_before == datetime.datetime(2024, 1, 1, 0, 0)
assert ext.value.not_after == datetime.datetime(
2024, 12, 31, 23, 59, 59
)
def test_load_pem_only_not_before(self, backend):
cert_path = os.path.join(
"x509", "custom", "private_key_usage_period_only_not_before.pem"
)
cert = load_vectors_from_file(
cert_path,
lambda pemdata: x509.load_pem_x509_certificate(pemdata.read()),
mode="rb",
)
ext = cert.extensions.get_extension_for_class(
x509.PrivateKeyUsagePeriod
)
assert ext.value.not_before == datetime.datetime(2024, 1, 1, 0, 0)
assert ext.value.not_after is None
def test_load_pem_only_not_after(self, backend):
cert_path = os.path.join(
"x509", "custom", "private_key_usage_period_only_not_after.pem"
)
cert = load_vectors_from_file(
cert_path,
lambda pemdata: x509.load_pem_x509_certificate(pemdata.read()),
mode="rb",
)
ext = cert.extensions.get_extension_for_class(
x509.PrivateKeyUsagePeriod
)
assert ext.value.not_before is None
assert ext.value.not_after == datetime.datetime(
2024, 12, 31, 23, 59, 59
)
def test_certificate_builder_with_extension(self, backend):
private_key = ec.generate_private_key(ec.SECP256R1())
period = x509.PrivateKeyUsagePeriod(
not_before=datetime.datetime(2012, 1, 1),
not_after=datetime.datetime(2013, 1, 1),
)
builder = x509.CertificateBuilder()
builder = builder.subject_name(
x509.Name(
[
x509.NameAttribute(
x509.NameOID.COMMON_NAME, "cryptography.io"
),
]
)
)
builder = builder.issuer_name(
x509.Name(
[
x509.NameAttribute(
x509.NameOID.COMMON_NAME, "cryptography.io"
),
]
)
)
builder = builder.not_valid_before(datetime.datetime(2010, 1, 1))
builder = builder.not_valid_after(datetime.datetime(2020, 1, 1))
builder = builder.serial_number(123)
builder = builder.public_key(private_key.public_key())
builder = builder.add_extension(period, critical=True)
certificate = builder.sign(private_key, hashes.SHA256())
ext = certificate.extensions.get_extension_for_class(
x509.PrivateKeyUsagePeriod
)
assert ext.critical is True
assert ext.value.not_before == datetime.datetime(2012, 1, 1)
assert ext.value.not_after == datetime.datetime(2013, 1, 1)
class TestDNSName:
def test_non_a_label(self):
with pytest.raises(ValueError):
x509.DNSName(".\xf5\xe4\xf6\xfc.example.com")
def test_init(self):
name = x509.DNSName("*.xn--4ca7aey.example.com")
assert name.value == "*.xn--4ca7aey.example.com"
with pytest.raises(TypeError):
x509.DNSName(1.3) # type:ignore[arg-type]
with pytest.raises(TypeError):
x509.DNSName(b"bytes not allowed") # type:ignore[arg-type]
def test_ne(self):
n1 = x509.DNSName("test1")
n2 = x509.DNSName("test2")
n3 = x509.DNSName("test2")
assert n1 != n2
assert not (n2 != n3)
def test_hash(self):
n1 = x509.DNSName("test1")
n2 = x509.DNSName("test2")
n3 = x509.DNSName("test2")
assert hash(n1) != hash(n2)
assert hash(n2) == hash(n3)
class TestDirectoryName:
def test_not_name(self):
with pytest.raises(TypeError):
x509.DirectoryName(b"notaname") # type:ignore[arg-type]
with pytest.raises(TypeError):
x509.DirectoryName(1.3) # type:ignore[arg-type]
def test_repr(self):
name = x509.Name([x509.NameAttribute(NameOID.COMMON_NAME, "value1")])
gn = x509.DirectoryName(name)
assert repr(gn) == "<DirectoryName(value=<Name(CN=value1)>)>"
def test_eq(self):
name = x509.Name(
[x509.NameAttribute(x509.ObjectIdentifier("2.999.1"), "value1")]
)
name2 = x509.Name(
[x509.NameAttribute(x509.ObjectIdentifier("2.999.1"), "value1")]
)
gn = x509.DirectoryName(name)
gn2 = x509.DirectoryName(name2)
assert gn == gn2
def test_ne(self):
name = x509.Name(
[x509.NameAttribute(x509.ObjectIdentifier("2.999.1"), "value1")]
)
name2 = x509.Name(
[x509.NameAttribute(x509.ObjectIdentifier("2.999.2"), "value2")]
)
gn = x509.DirectoryName(name)
gn2 = x509.DirectoryName(name2)
assert gn != gn2
assert gn != object()
def test_hash(self):
name = x509.Name(
[x509.NameAttribute(x509.ObjectIdentifier("2.999.1"), "value1")]
)
name2 = x509.Name(
[x509.NameAttribute(x509.ObjectIdentifier("2.999.2"), "value2")]
)
gn = x509.DirectoryName(name)
gn2 = x509.DirectoryName(name)
gn3 = x509.DirectoryName(name2)
assert hash(gn) == hash(gn2)
assert hash(gn) != hash(gn3)
class TestRFC822Name:
def test_repr(self):
gn = x509.RFC822Name("string")
assert repr(gn) == "<RFC822Name(value='string')>"
def test_equality(self):
gn = x509.RFC822Name("string")
gn2 = x509.RFC822Name("string2")
gn3 = x509.RFC822Name("string")
assert gn != gn2
assert gn != object()
assert gn == gn3
def test_not_text(self):
with pytest.raises(TypeError):
x509.RFC822Name(1.3) # type:ignore[arg-type]
with pytest.raises(TypeError):
x509.RFC822Name(b"bytes") # type:ignore[arg-type]
def test_invalid_email(self):
with pytest.raises(ValueError):
x509.RFC822Name("Name <email>")
with pytest.raises(ValueError):
x509.RFC822Name("")
def test_single_label(self):
gn = x509.RFC822Name("administrator")
assert gn.value == "administrator"
def test_non_a_label(self):
with pytest.raises(ValueError):
x509.RFC822Name("email@em\xe5\xefl.com")
def test_hash(self):
g1 = x509.RFC822Name("email@host.com")
g2 = x509.RFC822Name("email@host.com")
g3 = x509.RFC822Name("admin@host.com")
assert hash(g1) == hash(g2)
assert hash(g1) != hash(g3)
class TestUniformResourceIdentifier:
def test_equality(self):
gn = x509.UniformResourceIdentifier("string")
gn2 = x509.UniformResourceIdentifier("string2")
gn3 = x509.UniformResourceIdentifier("string")
assert gn != gn2
assert gn != object()
assert gn == gn3
def test_not_text(self):
with pytest.raises(TypeError):
x509.UniformResourceIdentifier(1.3) # type:ignore[arg-type]
def test_no_parsed_hostname(self):
gn = x509.UniformResourceIdentifier("singlelabel")
assert gn.value == "singlelabel"
def test_with_port(self):
gn = x509.UniformResourceIdentifier("singlelabel:443/test")
assert gn.value == "singlelabel:443/test"
def test_non_a_label(self):
with pytest.raises(ValueError):
x509.UniformResourceIdentifier(
"http://\u043f\u044b\u043a\u0430.cryptography"
)
def test_empty_hostname(self):
gn = x509.UniformResourceIdentifier("ldap:///some-nonsense")
assert gn.value == "ldap:///some-nonsense"
def test_hash(self):
g1 = x509.UniformResourceIdentifier("http://host.com")
g2 = x509.UniformResourceIdentifier("http://host.com")
g3 = x509.UniformResourceIdentifier("http://other.com")
assert hash(g1) == hash(g2)
assert hash(g1) != hash(g3)
def test_repr(self):
gn = x509.UniformResourceIdentifier("string")
assert repr(gn) == ("<UniformResourceIdentifier(value='string')>")
class TestRegisteredID:
def test_not_oid(self):
with pytest.raises(TypeError):
x509.RegisteredID(b"notanoid") # type:ignore[arg-type]
with pytest.raises(TypeError):
x509.RegisteredID(1.3) # type:ignore[arg-type]
def test_repr(self):
gn = x509.RegisteredID(NameOID.COMMON_NAME)
assert repr(gn) == (
"<RegisteredID(value=<ObjectIdentifier(oid=2.5.4.3, name=commonNam"
"e)>)>"
)
def test_eq(self):
gn = x509.RegisteredID(NameOID.COMMON_NAME)
gn2 = x509.RegisteredID(NameOID.COMMON_NAME)
assert gn == gn2
def test_ne(self):
gn = x509.RegisteredID(NameOID.COMMON_NAME)
gn2 = x509.RegisteredID(ExtensionOID.BASIC_CONSTRAINTS)
assert gn != gn2
assert gn != object()
def test_hash(self):
gn = x509.RegisteredID(NameOID.COMMON_NAME)
gn2 = x509.RegisteredID(NameOID.COMMON_NAME)
gn3 = x509.RegisteredID(ExtensionOID.BASIC_CONSTRAINTS)
assert hash(gn) == hash(gn2)
assert hash(gn) != hash(gn3)
class TestIPAddress:
def test_not_ipaddress(self):
with pytest.raises(TypeError):
x509.IPAddress(b"notanipaddress") # type:ignore[arg-type]
with pytest.raises(TypeError):
x509.IPAddress(1.3) # type:ignore[arg-type]
def test_repr(self):
gn = x509.IPAddress(ipaddress.IPv4Address("127.0.0.1"))
assert repr(gn) == "<IPAddress(value=127.0.0.1)>"
gn2 = x509.IPAddress(ipaddress.IPv6Address("ff::"))
assert repr(gn2) == "<IPAddress(value=ff::)>"
gn3 = x509.IPAddress(ipaddress.IPv4Network("192.168.0.0/24"))
assert repr(gn3) == "<IPAddress(value=192.168.0.0/24)>"
gn4 = x509.IPAddress(ipaddress.IPv6Network("ff::/96"))
assert repr(gn4) == "<IPAddress(value=ff::/96)>"
def test_eq(self):
gn = x509.IPAddress(ipaddress.IPv4Address("127.0.0.1"))
gn2 = x509.IPAddress(ipaddress.IPv4Address("127.0.0.1"))
assert gn == gn2
def test_ne(self):
gn = x509.IPAddress(ipaddress.IPv4Address("127.0.0.1"))
gn2 = x509.IPAddress(ipaddress.IPv4Address("127.0.0.2"))
assert gn != gn2
assert gn != object()
def test_hash(self):
gn = x509.IPAddress(ipaddress.IPv4Address("127.0.0.1"))
gn2 = x509.IPAddress(ipaddress.IPv4Address("127.0.0.1"))
gn3 = x509.IPAddress(ipaddress.IPv4Address("127.0.0.2"))
assert hash(gn) == hash(gn2)
assert hash(gn) != hash(gn3)
class TestOtherName:
def test_invalid_args(self):
with pytest.raises(TypeError):
x509.OtherName(
b"notanobjectidentifier", # type:ignore[arg-type]
b"derdata",
)
with pytest.raises(TypeError):
x509.OtherName(
x509.ObjectIdentifier("1.2.3.4"),
"notderdata", # type:ignore[arg-type]
)
def test_repr(self):
gn = x509.OtherName(x509.ObjectIdentifier("1.2.3.4"), b"derdata")
assert repr(gn) == (
"<OtherName(type_id=<ObjectIdentifier(oid=1.2.3.4, "
"name=Unknown OID)>, value=b'derdata')>"
)
gn = x509.OtherName(x509.ObjectIdentifier("2.5.4.65"), b"derdata")
assert repr(gn) == (
"<OtherName(type_id=<ObjectIdentifier(oid=2.5.4.65, "
"name=pseudonym)>, value=b'derdata')>"
)
def test_eq(self):
gn = x509.OtherName(x509.ObjectIdentifier("1.2.3.4"), b"derdata")
gn2 = x509.OtherName(x509.ObjectIdentifier("1.2.3.4"), b"derdata")
assert gn == gn2
def test_ne(self):
gn = x509.OtherName(x509.ObjectIdentifier("1.2.3.4"), b"derdata")
assert gn != object()
gn2 = x509.OtherName(x509.ObjectIdentifier("1.2.3.4"), b"derdata2")
assert gn != gn2
gn2 = x509.OtherName(x509.ObjectIdentifier("1.2.3.5"), b"derdata")
assert gn != gn2
def test_hash(self):
gn = x509.OtherName(x509.ObjectIdentifier("1.2.3.4"), b"derdata")
gn2 = x509.OtherName(x509.ObjectIdentifier("1.2.3.4"), b"derdata")
gn3 = x509.OtherName(x509.ObjectIdentifier("1.2.3.5"), b"derdata")
assert hash(gn) == hash(gn2)
assert hash(gn) != hash(gn3)
class TestGeneralNames:
def test_get_values_for_type(self):
gns = x509.GeneralNames([x509.DNSName("cryptography.io")])
names = gns.get_values_for_type(x509.DNSName)
assert names == ["cryptography.io"]
def test_iter_names(self):
gns = x509.GeneralNames(
[x509.DNSName("cryptography.io"), x509.DNSName("crypto.local")]
)
assert len(gns) == 2
assert list(gns) == [
x509.DNSName("cryptography.io"),
x509.DNSName("crypto.local"),
]
def test_iter_input(self):
names = [
x509.DNSName("cryptography.io"),
x509.DNSName("crypto.local"),
]
gns = x509.GeneralNames(iter(names))
assert list(gns) == names
def test_indexing(self):
gn = x509.GeneralNames(
[
x509.DNSName("cryptography.io"),
x509.DNSName("crypto.local"),
x509.DNSName("another.local"),
x509.RFC822Name("email@another.local"),
x509.UniformResourceIdentifier("http://another.local"),
]
)
assert gn[-1] == gn[4]
assert gn[2:6:2] == [gn[2], gn[4]]
def test_invalid_general_names(self):
with pytest.raises(TypeError):
x509.GeneralNames(
[
x509.DNSName("cryptography.io"),
"invalid", # type:ignore[list-item]
]
)
def test_repr(self):
gns = x509.GeneralNames([x509.DNSName("cryptography.io")])
assert repr(gns) == (
"<GeneralNames([<DNSName(value='cryptography.io')>])>"
)
def test_eq(self):
gns = x509.GeneralNames([x509.DNSName("cryptography.io")])
gns2 = x509.GeneralNames([x509.DNSName("cryptography.io")])
assert gns == gns2
def test_ne(self):
gns = x509.GeneralNames([x509.DNSName("cryptography.io")])
gns2 = x509.GeneralNames([x509.RFC822Name("admin@cryptography.io")])
assert gns != gns2
assert gns != object()
def test_hash(self):
gns = x509.GeneralNames([x509.DNSName("cryptography.io")])
gns2 = x509.GeneralNames([x509.DNSName("cryptography.io")])
gns3 = x509.GeneralNames([x509.RFC822Name("admin@cryptography.io")])
assert hash(gns) == hash(gns2)
assert hash(gns) != hash(gns3)
class TestIssuerAlternativeName:
def test_get_values_for_type(self):
san = x509.IssuerAlternativeName([x509.DNSName("cryptography.io")])
names = san.get_values_for_type(x509.DNSName)
assert names == ["cryptography.io"]
def test_iter_names(self):
san = x509.IssuerAlternativeName(
[x509.DNSName("cryptography.io"), x509.DNSName("crypto.local")]
)
assert len(san) == 2
assert list(san) == [
x509.DNSName("cryptography.io"),
x509.DNSName("crypto.local"),
]
def test_indexing(self):
ian = x509.IssuerAlternativeName(
[
x509.DNSName("cryptography.io"),
x509.DNSName("crypto.local"),
x509.DNSName("another.local"),
x509.RFC822Name("email@another.local"),
x509.UniformResourceIdentifier("http://another.local"),
]
)
assert ian[-1] == ian[4]
assert ian[2:6:2] == [ian[2], ian[4]]
def test_invalid_general_names(self):
with pytest.raises(TypeError):
x509.IssuerAlternativeName(
[
x509.DNSName("cryptography.io"),
"invalid", # type:ignore[list-item]
]
)
def test_repr(self):
san = x509.IssuerAlternativeName([x509.DNSName("cryptography.io")])
assert repr(san) == (
"<IssuerAlternativeName("
"<GeneralNames([<DNSName(value='cryptography.io')>])>)>"
)
def test_eq(self):
san = x509.IssuerAlternativeName([x509.DNSName("cryptography.io")])
san2 = x509.IssuerAlternativeName([x509.DNSName("cryptography.io")])
assert san == san2
def test_ne(self):
san = x509.IssuerAlternativeName([x509.DNSName("cryptography.io")])
san2 = x509.IssuerAlternativeName(
[x509.RFC822Name("admin@cryptography.io")]
)
assert san != san2
assert san != object()
def test_hash(self):
ian = x509.IssuerAlternativeName([x509.DNSName("cryptography.io")])
ian2 = x509.IssuerAlternativeName([x509.DNSName("cryptography.io")])
ian3 = x509.IssuerAlternativeName(
[x509.RFC822Name("admin@cryptography.io")]
)
assert hash(ian) == hash(ian2)
assert hash(ian) != hash(ian3)
def test_public_bytes(self):
ext = x509.IssuerAlternativeName([x509.DNSName("cryptography.io")])
assert ext.public_bytes() == b"0\x11\x82\x0fcryptography.io"
class TestRSAIssuerAlternativeNameExtension:
def test_uri(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "ian_uri.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(
x509.IssuerAlternativeName
)
assert list(ext.value) == [
x509.UniformResourceIdentifier("http://path.to.root/root.crt"),
]
def test_malformed(self):
cert = _load_cert(
os.path.join("x509", "custom", "malformed-ian.pem"),
x509.load_pem_x509_certificate,
)
with pytest.raises(ValueError, match="issuer_alternative_name"):
cert.extensions
class TestCRLNumber:
def test_eq(self):
crl_number = x509.CRLNumber(15)
assert crl_number == x509.CRLNumber(15)
def test_ne(self):
crl_number = x509.CRLNumber(15)
assert crl_number != x509.CRLNumber(14)
assert crl_number != object()
def test_repr(self):
crl_number = x509.CRLNumber(15)
assert repr(crl_number) == "<CRLNumber(15)>"
def test_invalid_number(self):
with pytest.raises(TypeError):
x509.CRLNumber("notanumber") # type:ignore[arg-type]
def test_hash(self):
c1 = x509.CRLNumber(1)
c2 = x509.CRLNumber(1)
c3 = x509.CRLNumber(2)
assert hash(c1) == hash(c2)
assert hash(c1) != hash(c3)
def test_public_bytes(self):
ext = x509.CRLNumber(15)
assert ext.public_bytes() == b"\x02\x01\x0f"
class TestSubjectAlternativeName:
def test_get_values_for_type(self):
san = x509.SubjectAlternativeName([x509.DNSName("cryptography.io")])
names = san.get_values_for_type(x509.DNSName)
assert names == ["cryptography.io"]
def test_iter_names(self):
san = x509.SubjectAlternativeName(
[x509.DNSName("cryptography.io"), x509.DNSName("crypto.local")]
)
assert len(san) == 2
assert list(san) == [
x509.DNSName("cryptography.io"),
x509.DNSName("crypto.local"),
]
def test_indexing(self):
san = x509.SubjectAlternativeName(
[
x509.DNSName("cryptography.io"),
x509.DNSName("crypto.local"),
x509.DNSName("another.local"),
x509.RFC822Name("email@another.local"),
x509.UniformResourceIdentifier("http://another.local"),
]
)
assert san[-1] == san[4]
assert san[2:6:2] == [san[2], san[4]]
def test_invalid_general_names(self):
with pytest.raises(TypeError):
x509.SubjectAlternativeName(
[
x509.DNSName("cryptography.io"),
"invalid", # type:ignore[list-item]
]
)
def test_repr(self):
san = x509.SubjectAlternativeName([x509.DNSName("cryptography.io")])
assert repr(san) == (
"<SubjectAlternativeName("
"<GeneralNames([<DNSName(value='cryptography.io')>])>)>"
)
def test_eq(self):
san = x509.SubjectAlternativeName([x509.DNSName("cryptography.io")])
san2 = x509.SubjectAlternativeName([x509.DNSName("cryptography.io")])
assert san == san2
def test_ne(self):
san = x509.SubjectAlternativeName([x509.DNSName("cryptography.io")])
san2 = x509.SubjectAlternativeName(
[x509.RFC822Name("admin@cryptography.io")]
)
assert san != san2
assert san != object()
def test_hash(self):
san = x509.SubjectAlternativeName([x509.DNSName("cryptography.io")])
san2 = x509.SubjectAlternativeName([x509.DNSName("cryptography.io")])
san3 = x509.SubjectAlternativeName(
[x509.RFC822Name("admin@cryptography.io")]
)
assert hash(san) == hash(san2)
assert hash(san) != hash(san3)
def test_public_bytes(self):
ext = x509.SubjectAlternativeName([x509.DNSName("cryptography.io")])
assert ext.public_bytes() == b"0\x11\x82\x0fcryptography.io"
class TestRSASubjectAlternativeNameExtension:
def test_dns_name(self, backend):
cert = _load_cert(
os.path.join("x509", "cryptography.io.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(
x509.SubjectAlternativeName
)
assert ext is not None
assert ext.critical is False
san = ext.value
dns = san.get_values_for_type(x509.DNSName)
assert dns == ["www.cryptography.io", "cryptography.io"]
def test_wildcard_dns_name(self, backend):
cert = _load_cert(
os.path.join("x509", "wildcard_san.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(
x509.SubjectAlternativeName
)
dns = ext.value.get_values_for_type(x509.DNSName)
assert dns == [
"*.langui.sh",
"langui.sh",
"*.saseliminator.com",
"saseliminator.com",
]
def test_san_empty_hostname(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "san_empty_hostname.pem"),
x509.load_pem_x509_certificate,
)
san = cert.extensions.get_extension_for_oid(
ExtensionOID.SUBJECT_ALTERNATIVE_NAME
)
assert isinstance(san.value, x509.SubjectAlternativeName)
dns = san.value.get_values_for_type(x509.DNSName)
assert dns == [""]
def test_san_wildcard_idna_dns_name(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "san_wildcard_idna.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(
x509.SubjectAlternativeName
)
dns = ext.value.get_values_for_type(x509.DNSName)
assert dns == ["*.xn--80ato2c.cryptography"]
def test_unsupported_gn(self, backend):
cert = _load_cert(
os.path.join("x509", "san_x400address.der"),
x509.load_der_x509_certificate,
)
with pytest.raises(x509.UnsupportedGeneralNameType):
cert.extensions
def test_registered_id(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "san_registered_id.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(
x509.SubjectAlternativeName
)
assert ext is not None
assert ext.critical is False
san = ext.value
rid = san.get_values_for_type(x509.RegisteredID)
assert rid == [x509.ObjectIdentifier("1.2.3.4")]
def test_uri(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "san_uri_with_port.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(
x509.SubjectAlternativeName
)
assert ext is not None
uri = ext.value.get_values_for_type(x509.UniformResourceIdentifier)
assert uri == [
"gopher://xn--80ato2c.cryptography:70/path?q=s#hello",
"http://someregulardomain.com",
]
def test_ipaddress(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "san_ipaddr.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(
x509.SubjectAlternativeName
)
assert ext is not None
assert ext.critical is False
san = ext.value
ip = san.get_values_for_type(x509.IPAddress)
assert [
ipaddress.ip_address("127.0.0.1"),
ipaddress.ip_address("ff::"),
] == ip
def test_dirname(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "san_dirname.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(
x509.SubjectAlternativeName
)
assert ext is not None
assert ext.critical is False
san = ext.value
dirname = san.get_values_for_type(x509.DirectoryName)
assert [
x509.Name(
[
x509.NameAttribute(NameOID.COMMON_NAME, "test"),
x509.NameAttribute(NameOID.ORGANIZATION_NAME, "Org"),
x509.NameAttribute(
NameOID.STATE_OR_PROVINCE_NAME, "Texas"
),
]
)
] == dirname
def test_rfc822name(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "san_rfc822_idna.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(
x509.SubjectAlternativeName
)
assert ext is not None
assert ext.critical is False
san = ext.value
rfc822name = san.get_values_for_type(x509.RFC822Name)
assert ["email@xn--eml-vla4c.com"] == rfc822name
def test_idna2003_invalid(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "san_idna2003_dnsname.pem"),
x509.load_pem_x509_certificate,
)
san = cert.extensions.get_extension_for_class(
x509.SubjectAlternativeName
).value
assert len(san) == 1
[name] = san
assert name.value == "xn--k4h.ws"
def test_unicode_rfc822_name_dns_name_uri(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "san_idna_names.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(
x509.SubjectAlternativeName
)
assert ext is not None
rfc822_name = ext.value.get_values_for_type(x509.RFC822Name)
dns_name = ext.value.get_values_for_type(x509.DNSName)
uri = ext.value.get_values_for_type(x509.UniformResourceIdentifier)
assert rfc822_name == ["email@xn--80ato2c.cryptography"]
assert dns_name == ["xn--80ato2c.cryptography"]
assert uri == ["https://www.xn--80ato2c.cryptography"]
def test_rfc822name_dnsname_ipaddress_directoryname_uri(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "san_email_dns_ip_dirname_uri.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(
x509.SubjectAlternativeName
)
assert ext is not None
assert ext.critical is False
san = ext.value
rfc822_name = san.get_values_for_type(x509.RFC822Name)
uri = san.get_values_for_type(x509.UniformResourceIdentifier)
dns = san.get_values_for_type(x509.DNSName)
ip = san.get_values_for_type(x509.IPAddress)
dirname = san.get_values_for_type(x509.DirectoryName)
assert ["user@cryptography.io"] == rfc822_name
assert ["https://cryptography.io"] == uri
assert ["cryptography.io"] == dns
assert [
x509.Name(
[
x509.NameAttribute(NameOID.COMMON_NAME, "dirCN"),
x509.NameAttribute(
NameOID.ORGANIZATION_NAME, "Cryptographic Authority"
),
]
)
] == dirname
assert [
ipaddress.ip_address("127.0.0.1"),
ipaddress.ip_address("ff::"),
] == ip
def test_invalid_rfc822name(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "san_rfc822_names.pem"),
x509.load_pem_x509_certificate,
)
san = cert.extensions.get_extension_for_class(
x509.SubjectAlternativeName
).value
values = san.get_values_for_type(x509.RFC822Name)
assert values == [
"email",
"email <email>",
"email <email@email>",
"email <email@xn--eml-vla4c.com>",
"myemail:",
]
def test_other_name(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "san_other_name.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(
x509.SubjectAlternativeName
)
assert ext is not None
assert ext.critical is False
expected = x509.OtherName(
x509.ObjectIdentifier("1.2.3.4"), b"\x16\x0bHello World"
)
assert len(ext.value) == 1
assert next(iter(ext.value)) == expected
othernames = ext.value.get_values_for_type(x509.OtherName)
assert othernames == [expected]
def test_certbuilder(self, rsa_key_2048: rsa.RSAPrivateKey, backend):
sans = [
"*.example.org",
"*.xn--4ca7aey.example.com",
"foobar.example.net",
]
private_key = rsa_key_2048
builder = _make_certbuilder(private_key)
builder = builder.add_extension(
SubjectAlternativeName(list(map(DNSName, sans))), True
)
cert = builder.sign(private_key, hashes.SHA256(), backend)
result = [
x.value
for x in cert.extensions.get_extension_for_class(
SubjectAlternativeName
).value
]
assert result == sans
def test_malformed(self):
cert = _load_cert(
os.path.join("x509", "custom", "malformed-san.pem"),
x509.load_pem_x509_certificate,
)
with pytest.raises(ValueError, match="subject_alternative_name"):
cert.extensions
class TestExtendedKeyUsageExtension:
def test_eku(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "extended_key_usage.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(x509.ExtendedKeyUsage)
assert ext is not None
assert ext.critical is False
assert [
x509.ObjectIdentifier("1.3.6.1.5.5.7.3.1"),
x509.ObjectIdentifier("1.3.6.1.5.5.7.3.2"),
x509.ObjectIdentifier("1.3.6.1.5.5.7.3.3"),
x509.ObjectIdentifier("1.3.6.1.5.5.7.3.4"),
x509.ObjectIdentifier("1.3.6.1.5.5.7.3.9"),
x509.ObjectIdentifier("1.3.6.1.5.5.7.3.8"),
x509.ObjectIdentifier("2.5.29.37.0"),
x509.ObjectIdentifier("2.16.840.1.113730.4.1"),
] == list(ext.value)
class TestAccessDescription:
def test_invalid_access_method(self):
with pytest.raises(TypeError):
x509.AccessDescription(
"notanoid", # type:ignore[arg-type]
x509.DNSName("test"),
)
def test_invalid_access_location(self):
with pytest.raises(TypeError):
x509.AccessDescription(
AuthorityInformationAccessOID.CA_ISSUERS,
"invalid", # type:ignore[arg-type]
)
def test_valid_nonstandard_method(self):
ad = x509.AccessDescription(
ObjectIdentifier("2.999.1"),
x509.UniformResourceIdentifier("http://example.com"),
)
assert ad is not None
def test_repr(self):
ad = x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp.domain.com"),
)
assert repr(ad) == (
"<AccessDescription(access_method=<ObjectIdentifier(oid=1.3.6"
".1.5.5.7.48.1, name=OCSP)>, access_location=<UniformResource"
"Identifier(value='http://ocsp.domain.com')>)>"
)
def test_eq(self):
ad = x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp.domain.com"),
)
ad2 = x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp.domain.com"),
)
assert ad == ad2
def test_ne(self):
ad = x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp.domain.com"),
)
ad2 = x509.AccessDescription(
AuthorityInformationAccessOID.CA_ISSUERS,
x509.UniformResourceIdentifier("http://ocsp.domain.com"),
)
ad3 = x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://notthesame"),
)
assert ad != ad2
assert ad != ad3
assert ad != object()
def test_hash(self):
ad = x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp.domain.com"),
)
ad2 = x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp.domain.com"),
)
ad3 = x509.AccessDescription(
AuthorityInformationAccessOID.CA_ISSUERS,
x509.UniformResourceIdentifier("http://ocsp.domain.com"),
)
assert hash(ad) == hash(ad2)
assert hash(ad) != hash(ad3)
class TestPolicyConstraints:
def test_invalid_explicit_policy(self):
with pytest.raises(TypeError):
x509.PolicyConstraints("invalid", None) # type:ignore[arg-type]
def test_invalid_inhibit_policy(self):
with pytest.raises(TypeError):
x509.PolicyConstraints(None, "invalid") # type:ignore[arg-type]
def test_both_none(self):
with pytest.raises(ValueError):
x509.PolicyConstraints(None, None)
def test_repr(self):
pc = x509.PolicyConstraints(0, None)
assert repr(pc) == (
"<PolicyConstraints(require_explicit_policy=0, inhibit_policy_ma"
"pping=None)>"
)
def test_eq(self):
pc = x509.PolicyConstraints(2, 1)
pc2 = x509.PolicyConstraints(2, 1)
assert pc == pc2
def test_ne(self):
pc = x509.PolicyConstraints(2, 1)
pc2 = x509.PolicyConstraints(2, 2)
pc3 = x509.PolicyConstraints(3, 1)
assert pc != pc2
assert pc != pc3
assert pc != object()
def test_hash(self):
pc = x509.PolicyConstraints(2, 1)
pc2 = x509.PolicyConstraints(2, 1)
pc3 = x509.PolicyConstraints(2, None)
assert hash(pc) == hash(pc2)
assert hash(pc) != hash(pc3)
def test_public_bytes(self):
ext = x509.PolicyConstraints(2, 1)
assert ext.public_bytes() == b"0\x06\x80\x01\x02\x81\x01\x01"
class TestPolicyConstraintsExtension:
def test_inhibit_policy_mapping(self, backend):
cert = _load_cert(
os.path.join("x509", "department-of-state-root.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_oid(
ExtensionOID.POLICY_CONSTRAINTS,
)
assert ext.critical is True
assert ext.value == x509.PolicyConstraints(
require_explicit_policy=None,
inhibit_policy_mapping=0,
)
def test_require_explicit_policy(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "policy_constraints_explicit.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_oid(
ExtensionOID.POLICY_CONSTRAINTS
)
assert ext.critical is True
assert ext.value == x509.PolicyConstraints(
require_explicit_policy=1,
inhibit_policy_mapping=None,
)
def test_public_bytes(self):
ext = x509.PolicyConstraints(
require_explicit_policy=None,
inhibit_policy_mapping=0,
)
assert ext.public_bytes() == b"\x30\x03\x81\x01\x00"
class TestAuthorityInformationAccess:
def test_invalid_descriptions(self):
with pytest.raises(TypeError):
x509.AuthorityInformationAccess(
["notanAccessDescription"] # type:ignore[list-item]
)
def test_iter_len(self):
aia = x509.AuthorityInformationAccess(
[
x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp.domain.com"),
),
x509.AccessDescription(
AuthorityInformationAccessOID.CA_ISSUERS,
x509.UniformResourceIdentifier("http://domain.com/ca.crt"),
),
]
)
assert len(aia) == 2
assert list(aia) == [
x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp.domain.com"),
),
x509.AccessDescription(
AuthorityInformationAccessOID.CA_ISSUERS,
x509.UniformResourceIdentifier("http://domain.com/ca.crt"),
),
]
def test_iter_input(self):
desc = [
x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp.domain.com"),
)
]
aia = x509.AuthorityInformationAccess(iter(desc))
assert list(aia) == desc
def test_repr(self):
aia = x509.AuthorityInformationAccess(
[
x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp.domain.com"),
),
x509.AccessDescription(
AuthorityInformationAccessOID.CA_ISSUERS,
x509.UniformResourceIdentifier("http://domain.com/ca.crt"),
),
]
)
assert repr(aia) == (
"<AuthorityInformationAccess([<AccessDescription(access_method"
"=<ObjectIdentifier(oid=1.3.6.1.5.5.7.48.1, name=OCSP)>, acces"
"s_location=<UniformResourceIdentifier(value='http://oc"
"sp.domain.com')>)>, <AccessDescription(access_method=<ObjectI"
"dentifier(oid=1.3.6.1.5.5.7.48.2, name=caIssuers)>, access_lo"
"cation=<UniformResourceIdentifier(value='http://domain"
".com/ca.crt')>)>])>"
)
def test_eq(self):
aia = x509.AuthorityInformationAccess(
[
x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp.domain.com"),
),
x509.AccessDescription(
AuthorityInformationAccessOID.CA_ISSUERS,
x509.UniformResourceIdentifier("http://domain.com/ca.crt"),
),
]
)
aia2 = x509.AuthorityInformationAccess(
[
x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp.domain.com"),
),
x509.AccessDescription(
AuthorityInformationAccessOID.CA_ISSUERS,
x509.UniformResourceIdentifier("http://domain.com/ca.crt"),
),
]
)
assert aia == aia2
def test_ne(self):
aia = x509.AuthorityInformationAccess(
[
x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp.domain.com"),
),
x509.AccessDescription(
AuthorityInformationAccessOID.CA_ISSUERS,
x509.UniformResourceIdentifier("http://domain.com/ca.crt"),
),
]
)
aia2 = x509.AuthorityInformationAccess(
[
x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp.domain.com"),
),
]
)
assert aia != aia2
assert aia != object()
def test_indexing(self):
aia = x509.AuthorityInformationAccess(
[
x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp.domain.com"),
),
x509.AccessDescription(
AuthorityInformationAccessOID.CA_ISSUERS,
x509.UniformResourceIdentifier("http://domain.com/ca.crt"),
),
x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp2.domain.com"),
),
x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp3.domain.com"),
),
x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp4.domain.com"),
),
]
)
assert aia[-1] == aia[4]
assert aia[2:6:2] == [aia[2], aia[4]]
def test_hash(self):
aia = x509.AuthorityInformationAccess(
[
x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp.domain.com"),
),
x509.AccessDescription(
AuthorityInformationAccessOID.CA_ISSUERS,
x509.UniformResourceIdentifier("http://domain.com/ca.crt"),
),
]
)
aia2 = x509.AuthorityInformationAccess(
[
x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp.domain.com"),
),
x509.AccessDescription(
AuthorityInformationAccessOID.CA_ISSUERS,
x509.UniformResourceIdentifier("http://domain.com/ca.crt"),
),
]
)
aia3 = x509.AuthorityInformationAccess(
[
x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp.other.com"),
),
x509.AccessDescription(
AuthorityInformationAccessOID.CA_ISSUERS,
x509.UniformResourceIdentifier("http://domain.com/ca.crt"),
),
]
)
assert hash(aia) == hash(aia2)
assert hash(aia) != hash(aia3)
def test_public_bytes(self):
ext = x509.AuthorityInformationAccess(
[
x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp.other.com"),
),
x509.AccessDescription(
AuthorityInformationAccessOID.CA_ISSUERS,
x509.UniformResourceIdentifier("http://domain.com/ca.crt"),
),
]
)
assert (
ext.public_bytes()
== b"0I0!\x06\x08+\x06\x01\x05\x05\x070\x01\x86\x15http://"
b"ocsp.other.com0$\x06\x08+\x06\x01\x05\x05\x070\x02\x86\x18"
b"http://domain.com/ca.crt"
)
class TestSubjectInformationAccess:
def test_invalid_descriptions(self):
with pytest.raises(TypeError):
x509.SubjectInformationAccess(
["notanAccessDescription"] # type:ignore[list-item]
)
def test_iter_len(self):
sia = x509.SubjectInformationAccess(
[
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca.domain.com"),
),
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca2.domain.com"),
),
]
)
assert len(sia) == 2
assert list(sia) == [
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca.domain.com"),
),
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca2.domain.com"),
),
]
def test_iter_input(self):
desc = [
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca.domain.com"),
)
]
sia = x509.SubjectInformationAccess(iter(desc))
assert list(sia) == desc
def test_repr(self):
sia = x509.SubjectInformationAccess(
[
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca.domain.com"),
)
]
)
assert repr(sia) == (
"<SubjectInformationAccess([<AccessDescription(access_method"
"=<ObjectIdentifier(oid=1.3.6.1.5.5.7.48.5, name=caRepositor"
"y)>, access_location=<UniformResourceIdentifier(value='http"
"://ca.domain.com')>)>])>"
)
def test_eq(self):
sia = x509.SubjectInformationAccess(
[
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca.domain.com"),
),
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca2.domain.com"),
),
]
)
sia2 = x509.SubjectInformationAccess(
[
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca.domain.com"),
),
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca2.domain.com"),
),
]
)
assert sia == sia2
def test_ne(self):
sia = x509.SubjectInformationAccess(
[
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca.domain.com"),
),
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca2.domain.com"),
),
]
)
sia2 = x509.SubjectInformationAccess(
[
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca.domain.com"),
),
]
)
assert sia != sia2
assert sia != object()
def test_indexing(self):
sia = x509.SubjectInformationAccess(
[
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca.domain.com"),
),
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca2.domain.com"),
),
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca3.domain.com"),
),
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca4.domain.com"),
),
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca5.domain.com"),
),
]
)
assert sia[-1] == sia[4]
assert sia[2:6:2] == [sia[2], sia[4]]
def test_hash(self):
sia = x509.SubjectInformationAccess(
[
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca.domain.com"),
),
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca2.domain.com"),
),
]
)
sia2 = x509.SubjectInformationAccess(
[
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca.domain.com"),
),
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca2.domain.com"),
),
]
)
sia3 = x509.SubjectInformationAccess(
[
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca.domain.com"),
),
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca3.domain.com"),
),
]
)
assert hash(sia) == hash(sia2)
assert hash(sia) != hash(sia3)
def test_public_bytes(self):
ext = x509.SubjectInformationAccess(
[
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca.domain.com"),
),
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("http://ca3.domain.com"),
),
]
)
assert (
ext.public_bytes()
== b"0E0 \x06\x08+\x06\x01\x05\x05\x070\x05\x86\x14http://"
b"ca.domain.com0!\x06\x08+\x06\x01\x05\x05\x070\x05\x86\x15"
b"http://ca3.domain.com"
)
class TestSubjectInformationAccessExtension:
def test_sia(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "sia.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_oid(
ExtensionOID.SUBJECT_INFORMATION_ACCESS
)
assert ext is not None
assert ext.critical is False
assert ext.value == x509.SubjectInformationAccess(
[
x509.AccessDescription(
SubjectInformationAccessOID.CA_REPOSITORY,
x509.UniformResourceIdentifier("https://my.ca.issuer/"),
),
x509.AccessDescription(
x509.ObjectIdentifier("2.999.7"),
x509.UniformResourceIdentifier(
"gopher://info-mac-archive"
),
),
]
)
class TestAuthorityInformationAccessExtension:
def test_aia_ocsp_ca_issuers(self, backend):
cert = _load_cert(
os.path.join("x509", "cryptography.io.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_oid(
ExtensionOID.AUTHORITY_INFORMATION_ACCESS
)
assert ext is not None
assert ext.critical is False
assert ext.value == x509.AuthorityInformationAccess(
[
x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://gv.symcd.com"),
),
x509.AccessDescription(
AuthorityInformationAccessOID.CA_ISSUERS,
x509.UniformResourceIdentifier(
"http://gv.symcb.com/gv.crt"
),
),
]
)
def test_aia_multiple_ocsp_ca_issuers(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "aia_ocsp_ca_issuers.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_oid(
ExtensionOID.AUTHORITY_INFORMATION_ACCESS
)
assert ext is not None
assert ext.critical is False
assert ext.value == x509.AuthorityInformationAccess(
[
x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp.domain.com"),
),
x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp2.domain.com"),
),
x509.AccessDescription(
AuthorityInformationAccessOID.CA_ISSUERS,
x509.DirectoryName(
x509.Name(
[
x509.NameAttribute(
NameOID.COMMON_NAME, "myCN"
),
x509.NameAttribute(
NameOID.ORGANIZATION_NAME, "some Org"
),
]
)
),
),
]
)
def test_aia_ocsp_only(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "aia_ocsp.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_oid(
ExtensionOID.AUTHORITY_INFORMATION_ACCESS
)
assert ext is not None
assert ext.critical is False
assert ext.value == x509.AuthorityInformationAccess(
[
x509.AccessDescription(
AuthorityInformationAccessOID.OCSP,
x509.UniformResourceIdentifier("http://ocsp.domain.com"),
),
]
)
def test_aia_ca_issuers_only(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "aia_ca_issuers.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_oid(
ExtensionOID.AUTHORITY_INFORMATION_ACCESS
)
assert ext is not None
assert ext.critical is False
assert ext.value == x509.AuthorityInformationAccess(
[
x509.AccessDescription(
AuthorityInformationAccessOID.CA_ISSUERS,
x509.DirectoryName(
x509.Name(
[
x509.NameAttribute(
NameOID.COMMON_NAME, "myCN"
),
x509.NameAttribute(
NameOID.ORGANIZATION_NAME, "some Org"
),
]
)
),
),
]
)
def test_public_bytes(self):
ext = x509.AuthorityInformationAccess(
[
x509.AccessDescription(
AuthorityInformationAccessOID.CA_ISSUERS,
x509.DirectoryName(
x509.Name(
[
x509.NameAttribute(
NameOID.COMMON_NAME, "myCN"
),
x509.NameAttribute(
NameOID.ORGANIZATION_NAME, "some Org"
),
]
)
),
),
]
)
assert (
ext.public_bytes()
== b'0200\x06\x08+\x06\x01\x05\x05\x070\x02\xa4$0"1\r0\x0b\x06'
b"\x03U\x04\x03\x0c\x04myCN1\x110\x0f\x06\x03U\x04\n\x0c\x08"
b"some Org"
)
class TestAuthorityKeyIdentifierExtension:
def test_aki_keyid(self, backend):
cert = _load_cert(
os.path.join("x509", "cryptography.io.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(
x509.AuthorityKeyIdentifier
)
assert ext is not None
assert ext.critical is False
assert ext.value.key_identifier == (
b"\xc3\x9c\xf3\xfc\xd3F\x084\xbb\xceF\x7f\xa0|[\xf3\xe2\x08\xcbY"
)
assert ext.value.authority_cert_issuer is None
assert ext.value.authority_cert_serial_number is None
def test_aki_all_fields(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "authority_key_identifier.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(
x509.AuthorityKeyIdentifier
)
assert ext is not None
assert ext.critical is False
assert ext.value.key_identifier == (
b"9E>\xca=b\x1d\xea\x86I\xf6Z\xab@\xb7\xa4p\x98\xf1\xec"
)
assert ext.value.authority_cert_issuer == [
x509.DirectoryName(
x509.Name(
[
x509.NameAttribute(NameOID.ORGANIZATION_NAME, "PyCA"),
x509.NameAttribute(
NameOID.COMMON_NAME, "cryptography.io"
),
]
)
)
]
assert ext.value.authority_cert_serial_number == 3
def test_aki_no_keyid(self, backend):
cert = _load_cert(
os.path.join(
"x509", "custom", "authority_key_identifier_no_keyid.pem"
),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_class(
x509.AuthorityKeyIdentifier
)
assert ext is not None
assert ext.critical is False
assert ext.value.key_identifier is None
assert ext.value.authority_cert_issuer == [
x509.DirectoryName(
x509.Name(
[
x509.NameAttribute(NameOID.ORGANIZATION_NAME, "PyCA"),
x509.NameAttribute(
NameOID.COMMON_NAME, "cryptography.io"
),
]
)
)
]
assert ext.value.authority_cert_serial_number == 3
def test_from_certificate(self, backend):
issuer_cert = _load_cert(
os.path.join("x509", "rapidssl_sha256_ca_g3.pem"),
x509.load_pem_x509_certificate,
)
cert = _load_cert(
os.path.join("x509", "cryptography.io.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_oid(
ExtensionOID.AUTHORITY_KEY_IDENTIFIER
)
public_key = issuer_cert.public_key()
assert isinstance(public_key, rsa.RSAPublicKey)
aki = x509.AuthorityKeyIdentifier.from_issuer_public_key(public_key)
assert ext.value == aki
def test_from_issuer_subject_key_identifier(self, backend):
issuer_cert = _load_cert(
os.path.join("x509", "rapidssl_sha256_ca_g3.pem"),
x509.load_pem_x509_certificate,
)
cert = _load_cert(
os.path.join("x509", "cryptography.io.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_oid(
ExtensionOID.AUTHORITY_KEY_IDENTIFIER
)
ski_ext = issuer_cert.extensions.get_extension_for_class(
x509.SubjectKeyIdentifier
)
aki = x509.AuthorityKeyIdentifier.from_issuer_subject_key_identifier(
ski_ext.value
)
assert ext.value == aki
class TestNameConstraints:
def test_ipaddress_wrong_type(self):
with pytest.raises(TypeError):
x509.NameConstraints(
permitted_subtrees=[
x509.IPAddress(ipaddress.IPv4Address("127.0.0.1"))
],
excluded_subtrees=None,
)
with pytest.raises(TypeError):
x509.NameConstraints(
permitted_subtrees=None,
excluded_subtrees=[
x509.IPAddress(ipaddress.IPv4Address("127.0.0.1"))
],
)
def test_ipaddress_allowed_type(self):
permitted = [x509.IPAddress(ipaddress.IPv4Network("192.168.0.0/29"))]
excluded = [x509.IPAddress(ipaddress.IPv4Network("10.10.0.0/24"))]
nc = x509.NameConstraints(
permitted_subtrees=permitted, excluded_subtrees=excluded
)
assert nc.permitted_subtrees == permitted
assert nc.excluded_subtrees == excluded
def test_dnsname_wrong_value(self):
with pytest.raises(ValueError):
x509.NameConstraints(
permitted_subtrees=[x509.DNSName("*.example.com")],
excluded_subtrees=None,
)
with pytest.raises(ValueError):
x509.NameConstraints(
permitted_subtrees=None,
excluded_subtrees=[x509.DNSName("*.example.com")],
)
def test_dnsname_allowed_value(self):
permitted = [x509.DNSName("example.com")]
excluded = [x509.DNSName("www.example.com")]
nc = x509.NameConstraints(
permitted_subtrees=permitted, excluded_subtrees=excluded
)
assert nc.permitted_subtrees == permitted
assert nc.excluded_subtrees == excluded
def test_invalid_permitted_subtrees(self):
with pytest.raises(TypeError):
x509.NameConstraints("badpermitted", None) # type:ignore[arg-type]
def test_invalid_excluded_subtrees(self):
with pytest.raises(TypeError):
x509.NameConstraints(None, "badexcluded") # type:ignore[arg-type]
def test_no_subtrees(self):
with pytest.raises(ValueError):
x509.NameConstraints(None, None)
def test_permitted_none(self):
excluded = [x509.DNSName("name.local")]
nc = x509.NameConstraints(
permitted_subtrees=None, excluded_subtrees=excluded
)
assert nc.permitted_subtrees is None
assert nc.excluded_subtrees is not None
def test_excluded_none(self):
permitted = [x509.DNSName("name.local")]
nc = x509.NameConstraints(
permitted_subtrees=permitted, excluded_subtrees=None
)
assert nc.permitted_subtrees is not None
assert nc.excluded_subtrees is None
def test_iter_input(self):
subtrees = [x509.IPAddress(ipaddress.IPv4Network("192.168.0.0/24"))]
nc = x509.NameConstraints(iter(subtrees), iter(subtrees))
assert nc.permitted_subtrees is not None
assert list(nc.permitted_subtrees) == subtrees
assert nc.excluded_subtrees is not None
assert list(nc.excluded_subtrees) == subtrees
def test_empty_lists(self):
with pytest.raises(ValueError):
x509.NameConstraints(permitted_subtrees=None, excluded_subtrees=[])
with pytest.raises(ValueError):
x509.NameConstraints(permitted_subtrees=[], excluded_subtrees=None)
def test_repr(self):
permitted = [x509.DNSName("name.local"), x509.DNSName("name2.local")]
nc = x509.NameConstraints(
permitted_subtrees=permitted, excluded_subtrees=None
)
assert repr(nc) == (
"<NameConstraints(permitted_subtrees=[<DNSName("
"value='name.local')>, <DNSName(value="
"'name2.local')>], excluded_subtrees=None)>"
)
def test_eq(self):
nc = x509.NameConstraints(
permitted_subtrees=[x509.DNSName("name.local")],
excluded_subtrees=[x509.DNSName("name2.local")],
)
nc2 = x509.NameConstraints(
permitted_subtrees=[x509.DNSName("name.local")],
excluded_subtrees=[x509.DNSName("name2.local")],
)
assert nc == nc2
def test_ne(self):
nc = x509.NameConstraints(
permitted_subtrees=[x509.DNSName("name.local")],
excluded_subtrees=[x509.DNSName("name2.local")],
)
nc2 = x509.NameConstraints(
permitted_subtrees=[x509.DNSName("name.local")],
excluded_subtrees=None,
)
nc3 = x509.NameConstraints(
permitted_subtrees=None,
excluded_subtrees=[x509.DNSName("name2.local")],
)
assert nc != nc2
assert nc != nc3
assert nc != object()
def test_hash(self):
nc = x509.NameConstraints(
permitted_subtrees=[x509.DNSName("name.local")],
excluded_subtrees=[x509.DNSName("name2.local")],
)
nc2 = x509.NameConstraints(
permitted_subtrees=[x509.DNSName("name.local")],
excluded_subtrees=[x509.DNSName("name2.local")],
)
nc3 = x509.NameConstraints(
permitted_subtrees=[x509.DNSName("name.local")],
excluded_subtrees=None,
)
nc4 = x509.NameConstraints(
permitted_subtrees=None,
excluded_subtrees=[x509.DNSName("name.local")],
)
assert hash(nc) == hash(nc2)
assert hash(nc) != hash(nc3)
assert hash(nc3) != hash(nc4)
def test_public_bytes(self):
ext = x509.NameConstraints(
permitted_subtrees=[x509.DNSName("name.local")],
excluded_subtrees=[x509.DNSName("name2.local")],
)
assert (
ext.public_bytes()
== b"0!\xa0\x0e0\x0c\x82\nname.local\xa1\x0f0\r\x82\x0bname2.local"
)
class TestNameConstraintsExtension:
def test_permitted_excluded(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "nc_permitted_excluded_2.pem"),
x509.load_pem_x509_certificate,
)
nc = cert.extensions.get_extension_for_oid(
ExtensionOID.NAME_CONSTRAINTS
).value
assert nc == x509.NameConstraints(
permitted_subtrees=[x509.DNSName("zombo.local")],
excluded_subtrees=[
x509.DirectoryName(
x509.Name(
[x509.NameAttribute(NameOID.COMMON_NAME, "zombo")]
)
)
],
)
def test_permitted(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "nc_permitted_2.pem"),
x509.load_pem_x509_certificate,
)
nc = cert.extensions.get_extension_for_oid(
ExtensionOID.NAME_CONSTRAINTS
).value
assert nc == x509.NameConstraints(
permitted_subtrees=[x509.DNSName("zombo.local")],
excluded_subtrees=None,
)
def test_permitted_with_leading_period(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "nc_permitted.pem"),
x509.load_pem_x509_certificate,
)
nc = cert.extensions.get_extension_for_oid(
ExtensionOID.NAME_CONSTRAINTS
).value
assert nc == x509.NameConstraints(
permitted_subtrees=[
x509.DNSName(".cryptography.io"),
x509.UniformResourceIdentifier("ftp://cryptography.test"),
],
excluded_subtrees=None,
)
def test_excluded_with_leading_period(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "nc_excluded.pem"),
x509.load_pem_x509_certificate,
)
nc = cert.extensions.get_extension_for_oid(
ExtensionOID.NAME_CONSTRAINTS
).value
assert nc == x509.NameConstraints(
permitted_subtrees=None,
excluded_subtrees=[
x509.DNSName(".cryptography.io"),
x509.UniformResourceIdentifier("gopher://cryptography.test"),
],
)
def test_permitted_excluded_with_ips(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "nc_permitted_excluded.pem"),
x509.load_pem_x509_certificate,
)
nc = cert.extensions.get_extension_for_oid(
ExtensionOID.NAME_CONSTRAINTS
).value
assert nc == x509.NameConstraints(
permitted_subtrees=[
x509.IPAddress(ipaddress.IPv4Network("192.168.0.0/24")),
x509.IPAddress(ipaddress.IPv6Network("FF:0:0:0:0:0:0:0/96")),
],
excluded_subtrees=[
x509.DNSName(".domain.com"),
x509.UniformResourceIdentifier("http://test.local"),
],
)
def test_single_ip_netmask(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "nc_single_ip_netmask.pem"),
x509.load_pem_x509_certificate,
)
nc = cert.extensions.get_extension_for_oid(
ExtensionOID.NAME_CONSTRAINTS
).value
assert nc == x509.NameConstraints(
permitted_subtrees=[
x509.IPAddress(ipaddress.IPv6Network("FF:0:0:0:0:0:0:0/128")),
x509.IPAddress(ipaddress.IPv4Network("192.168.0.1/32")),
],
excluded_subtrees=None,
)
def test_ip_invalid_length(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "nc_ip_invalid_length.pem"),
x509.load_pem_x509_certificate,
)
with pytest.raises(ValueError):
cert.extensions.get_extension_for_oid(
ExtensionOID.NAME_CONSTRAINTS
)
def test_invalid_ipv6_netmask(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "nc_invalid_ip_netmask.pem"),
x509.load_pem_x509_certificate,
)
with pytest.raises(ValueError):
cert.extensions.get_extension_for_oid(
ExtensionOID.NAME_CONSTRAINTS
)
def test_invalid_ipv4_netmask(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "nc_invalid_ip4_netmask.der"),
x509.load_der_x509_certificate,
)
with pytest.raises(ValueError):
cert.extensions.get_extension_for_oid(
ExtensionOID.NAME_CONSTRAINTS
)
def test_certbuilder(self, rsa_key_2048: rsa.RSAPrivateKey, backend):
permitted = [
".example.org",
".xn--4ca7aey.example.com",
"foobar.example.net",
]
private_key = rsa_key_2048
builder = _make_certbuilder(private_key)
builder = builder.add_extension(
NameConstraints(
permitted_subtrees=list(map(DNSName, permitted)),
excluded_subtrees=None,
),
True,
)
cert = builder.sign(private_key, hashes.SHA256(), backend)
result = [
x.value
for x in cert.extensions.get_extension_for_class(
NameConstraints
).value.permitted_subtrees
]
assert result == permitted
def test_public_bytes(self):
ext = x509.NameConstraints(
permitted_subtrees=[x509.DNSName("zombo.local")],
excluded_subtrees=[
x509.DirectoryName(
x509.Name(
[x509.NameAttribute(NameOID.COMMON_NAME, "zombo")]
)
)
],
)
assert (
ext.public_bytes()
== b"0)\xa0\x0f0\r\x82\x0bzombo.local\xa1\x160\x14\xa4\x120\x101"
b"\x0e0\x0c\x06\x03U\x04\x03\x0c\x05zombo"
)
class TestDistributionPoint:
def test_distribution_point_full_name_not_general_names(self):
with pytest.raises(TypeError):
x509.DistributionPoint(
["notgn"], # type:ignore[list-item]
None,
None,
None,
)
def test_distribution_point_relative_name_not_name(self):
with pytest.raises(TypeError):
x509.DistributionPoint(
None,
"notname", # type:ignore[arg-type]
None,
None,
)
def test_distribution_point_full_and_relative_not_none(self):
with pytest.raises(ValueError):
x509.DistributionPoint(
[x509.UniformResourceIdentifier("http://crypt.og/crl")],
x509.RelativeDistinguishedName(
[x509.NameAttribute(NameOID.TITLE, "Test")]
),
None,
None,
)
def test_no_full_name_relative_name_or_crl_issuer(self):
with pytest.raises(ValueError):
x509.DistributionPoint(None, None, None, None)
def test_crl_issuer_not_general_names(self):
with pytest.raises(TypeError):
x509.DistributionPoint(
None,
None,
None,
["notgn"], # type:ignore[list-item]
)
def test_reason_not_reasonflags(self):
with pytest.raises(TypeError):
x509.DistributionPoint(
[x509.UniformResourceIdentifier("http://crypt.og/crl")],
None,
frozenset(["notreasonflags"]), # type:ignore[list-item]
None,
)
def test_reason_not_frozenset(self):
with pytest.raises(TypeError):
x509.DistributionPoint(
[x509.UniformResourceIdentifier("http://crypt.og/crl")],
None,
[x509.ReasonFlags.ca_compromise], # type:ignore[arg-type]
None,
)
def test_disallowed_reasons(self):
with pytest.raises(ValueError):
x509.DistributionPoint(
[x509.UniformResourceIdentifier("http://crypt.og/crl")],
None,
frozenset([x509.ReasonFlags.unspecified]),
None,
)
with pytest.raises(ValueError):
x509.DistributionPoint(
[x509.UniformResourceIdentifier("http://crypt.og/crl")],
None,
frozenset([x509.ReasonFlags.remove_from_crl]),
None,
)
def test_reason_only(self):
with pytest.raises(ValueError):
x509.DistributionPoint(
None, None, frozenset([x509.ReasonFlags.aa_compromise]), None
)
def test_eq(self):
dp = x509.DistributionPoint(
[x509.UniformResourceIdentifier("http://crypt.og/crl")],
None,
frozenset([x509.ReasonFlags.superseded]),
[
x509.DirectoryName(
x509.Name(
[
x509.NameAttribute(
NameOID.COMMON_NAME, "Important CA"
)
]
)
)
],
)
dp2 = x509.DistributionPoint(
[x509.UniformResourceIdentifier("http://crypt.og/crl")],
None,
frozenset([x509.ReasonFlags.superseded]),
[
x509.DirectoryName(
x509.Name(
[
x509.NameAttribute(
NameOID.COMMON_NAME, "Important CA"
)
]
)
)
],
)
assert dp == dp2
def test_ne(self):
dp = x509.DistributionPoint(
[x509.UniformResourceIdentifier("http://crypt.og/crl")],
None,
frozenset([x509.ReasonFlags.superseded]),
[
x509.DirectoryName(
x509.Name(
[
x509.NameAttribute(
NameOID.COMMON_NAME, "Important CA"
)
]
)
)
],
)
dp2 = x509.DistributionPoint(
[x509.UniformResourceIdentifier("http://crypt.og/crl")],
None,
None,
None,
)
assert dp != dp2
assert dp != object()
def test_iter_input(self):
name = [x509.UniformResourceIdentifier("http://crypt.og/crl")]
issuer = [
x509.DirectoryName(
x509.Name(
[x509.NameAttribute(NameOID.COMMON_NAME, "Important CA")]
)
)
]
dp = x509.DistributionPoint(
iter(name),
None,
frozenset([x509.ReasonFlags.ca_compromise]),
iter(issuer),
)
assert dp.full_name is not None
assert list(dp.full_name) == name
assert dp.crl_issuer is not None
assert list(dp.crl_issuer) == issuer
def test_repr(self):
dp = x509.DistributionPoint(
None,
x509.RelativeDistinguishedName(
[x509.NameAttribute(NameOID.COMMON_NAME, "myCN")]
),
frozenset([x509.ReasonFlags.ca_compromise]),
[
x509.DirectoryName(
x509.Name(
[
x509.NameAttribute(
NameOID.COMMON_NAME, "Important CA"
)
]
)
)
],
)
assert repr(dp) == (
"<DistributionPoint(full_name=None, relative_name=<RelativeDis"
"tinguishedName(CN=myCN)>, reasons=frozenset({<ReasonFlags.ca_"
"compromise: 'cACompromise'>}), crl_issuer=[<DirectoryName(val"
"ue=<Name(CN=Important CA)>)>])>"
)
def test_hash(self):
dp = x509.DistributionPoint(
[x509.UniformResourceIdentifier("http://crypt.og/crl")],
None,
frozenset([x509.ReasonFlags.superseded]),
[
x509.DirectoryName(
x509.Name(
[
x509.NameAttribute(
NameOID.COMMON_NAME, "Important CA"
)
]
)
)
],
)
dp2 = x509.DistributionPoint(
[x509.UniformResourceIdentifier("http://crypt.og/crl")],
None,
frozenset([x509.ReasonFlags.superseded]),
[
x509.DirectoryName(
x509.Name(
[
x509.NameAttribute(
NameOID.COMMON_NAME, "Important CA"
)
]
)
)
],
)
dp3 = x509.DistributionPoint(
None,
x509.RelativeDistinguishedName(
[x509.NameAttribute(NameOID.COMMON_NAME, "myCN")]
),
None,
None,
)
assert hash(dp) == hash(dp2)
assert hash(dp) != hash(dp3)
class TestFreshestCRL:
def test_invalid_distribution_points(self):
with pytest.raises(TypeError):
x509.FreshestCRL(
["notadistributionpoint"] # type:ignore[list-item]
)
def test_iter_len(self):
fcrl = x509.FreshestCRL(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("http://domain")],
None,
None,
None,
),
]
)
assert len(fcrl) == 1
assert list(fcrl) == [
x509.DistributionPoint(
[x509.UniformResourceIdentifier("http://domain")],
None,
None,
None,
),
]
def test_iter_input(self):
points = [
x509.DistributionPoint(
[x509.UniformResourceIdentifier("http://domain")],
None,
None,
None,
),
]
fcrl = x509.FreshestCRL(iter(points))
assert list(fcrl) == points
def test_repr(self):
fcrl = x509.FreshestCRL(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain")],
None,
frozenset([x509.ReasonFlags.key_compromise]),
None,
),
]
)
assert repr(fcrl) == (
"<FreshestCRL([<DistributionPoint(full_name=[<Unifo"
"rmResourceIdentifier(value='ftp://domain')>], relative"
"_name=None, reasons=frozenset({<ReasonFlags.key_compromise: "
"'keyCompromise'>}), crl_issuer=None)>])>"
)
def test_eq(self):
fcrl = x509.FreshestCRL(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain")],
None,
frozenset(
[
x509.ReasonFlags.key_compromise,
x509.ReasonFlags.ca_compromise,
]
),
[x509.UniformResourceIdentifier("uri://thing")],
),
]
)
fcrl2 = x509.FreshestCRL(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain")],
None,
frozenset(
[
x509.ReasonFlags.key_compromise,
x509.ReasonFlags.ca_compromise,
]
),
[x509.UniformResourceIdentifier("uri://thing")],
),
]
)
assert fcrl == fcrl2
def test_ne(self):
fcrl = x509.FreshestCRL(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain")],
None,
frozenset(
[
x509.ReasonFlags.key_compromise,
x509.ReasonFlags.ca_compromise,
]
),
[x509.UniformResourceIdentifier("uri://thing")],
),
]
)
fcrl2 = x509.FreshestCRL(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain2")],
None,
frozenset(
[
x509.ReasonFlags.key_compromise,
x509.ReasonFlags.ca_compromise,
]
),
[x509.UniformResourceIdentifier("uri://thing")],
),
]
)
fcrl3 = x509.FreshestCRL(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain")],
None,
frozenset([x509.ReasonFlags.key_compromise]),
[x509.UniformResourceIdentifier("uri://thing")],
),
]
)
fcrl4 = x509.FreshestCRL(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain")],
None,
frozenset(
[
x509.ReasonFlags.key_compromise,
x509.ReasonFlags.ca_compromise,
]
),
[x509.UniformResourceIdentifier("uri://thing2")],
),
]
)
assert fcrl != fcrl2
assert fcrl != fcrl3
assert fcrl != fcrl4
assert fcrl != object()
def test_hash(self):
fcrl = x509.FreshestCRL(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain")],
None,
frozenset(
[
x509.ReasonFlags.key_compromise,
x509.ReasonFlags.ca_compromise,
]
),
[x509.UniformResourceIdentifier("uri://thing")],
),
]
)
fcrl2 = x509.FreshestCRL(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain")],
None,
frozenset(
[
x509.ReasonFlags.key_compromise,
x509.ReasonFlags.ca_compromise,
]
),
[x509.UniformResourceIdentifier("uri://thing")],
),
]
)
fcrl3 = x509.FreshestCRL(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain")],
None,
frozenset([x509.ReasonFlags.key_compromise]),
[x509.UniformResourceIdentifier("uri://thing")],
),
]
)
assert hash(fcrl) == hash(fcrl2)
assert hash(fcrl) != hash(fcrl3)
def test_indexing(self):
fcrl = x509.FreshestCRL(
[
x509.DistributionPoint(
None,
None,
None,
[x509.UniformResourceIdentifier("uri://thing")],
),
x509.DistributionPoint(
None,
None,
None,
[x509.UniformResourceIdentifier("uri://thing2")],
),
x509.DistributionPoint(
None,
None,
None,
[x509.UniformResourceIdentifier("uri://thing3")],
),
x509.DistributionPoint(
None,
None,
None,
[x509.UniformResourceIdentifier("uri://thing4")],
),
x509.DistributionPoint(
None,
None,
None,
[x509.UniformResourceIdentifier("uri://thing5")],
),
]
)
assert fcrl[-1] == fcrl[4]
assert fcrl[2:6:2] == [fcrl[2], fcrl[4]]
def test_public_bytes(self):
ext = x509.FreshestCRL(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain")],
None,
frozenset([x509.ReasonFlags.key_compromise]),
None,
),
]
)
assert (
ext.public_bytes()
== b"0\x180\x16\xa0\x10\xa0\x0e\x86\x0cftp://domain\x81\x02\x06@"
)
class TestCRLDistributionPoints:
def test_invalid_distribution_points(self):
with pytest.raises(TypeError):
x509.CRLDistributionPoints(
["notadistributionpoint"], # type:ignore[list-item]
)
def test_iter_len(self):
cdp = x509.CRLDistributionPoints(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("http://domain")],
None,
None,
None,
),
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain")],
None,
frozenset(
[
x509.ReasonFlags.key_compromise,
x509.ReasonFlags.ca_compromise,
]
),
None,
),
]
)
assert len(cdp) == 2
assert list(cdp) == [
x509.DistributionPoint(
[x509.UniformResourceIdentifier("http://domain")],
None,
None,
None,
),
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain")],
None,
frozenset(
[
x509.ReasonFlags.key_compromise,
x509.ReasonFlags.ca_compromise,
]
),
None,
),
]
def test_iter_input(self):
points = [
x509.DistributionPoint(
[x509.UniformResourceIdentifier("http://domain")],
None,
None,
None,
),
]
cdp = x509.CRLDistributionPoints(iter(points))
assert list(cdp) == points
def test_repr(self):
cdp = x509.CRLDistributionPoints(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain")],
None,
frozenset([x509.ReasonFlags.key_compromise]),
None,
),
]
)
assert repr(cdp) == (
"<CRLDistributionPoints([<DistributionPoint(full_name=[<Unifo"
"rmResourceIdentifier(value='ftp://domain')>], relative"
"_name=None, reasons=frozenset({<ReasonFlags.key_compromise: "
"'keyCompromise'>}), crl_issuer=None)>])>"
)
def test_eq(self):
cdp = x509.CRLDistributionPoints(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain")],
None,
frozenset(
[
x509.ReasonFlags.key_compromise,
x509.ReasonFlags.ca_compromise,
]
),
[x509.UniformResourceIdentifier("uri://thing")],
),
]
)
cdp2 = x509.CRLDistributionPoints(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain")],
None,
frozenset(
[
x509.ReasonFlags.key_compromise,
x509.ReasonFlags.ca_compromise,
]
),
[x509.UniformResourceIdentifier("uri://thing")],
),
]
)
assert cdp == cdp2
def test_ne(self):
cdp = x509.CRLDistributionPoints(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain")],
None,
frozenset(
[
x509.ReasonFlags.key_compromise,
x509.ReasonFlags.ca_compromise,
]
),
[x509.UniformResourceIdentifier("uri://thing")],
),
]
)
cdp2 = x509.CRLDistributionPoints(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain2")],
None,
frozenset(
[
x509.ReasonFlags.key_compromise,
x509.ReasonFlags.ca_compromise,
]
),
[x509.UniformResourceIdentifier("uri://thing")],
),
]
)
cdp3 = x509.CRLDistributionPoints(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain")],
None,
frozenset([x509.ReasonFlags.key_compromise]),
[x509.UniformResourceIdentifier("uri://thing")],
),
]
)
cdp4 = x509.CRLDistributionPoints(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain")],
None,
frozenset(
[
x509.ReasonFlags.key_compromise,
x509.ReasonFlags.ca_compromise,
]
),
[x509.UniformResourceIdentifier("uri://thing2")],
),
]
)
assert cdp != cdp2
assert cdp != cdp3
assert cdp != cdp4
assert cdp != object()
def test_hash(self):
cdp = x509.CRLDistributionPoints(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain")],
None,
frozenset(
[
x509.ReasonFlags.key_compromise,
x509.ReasonFlags.ca_compromise,
]
),
[x509.UniformResourceIdentifier("uri://thing")],
),
]
)
cdp2 = x509.CRLDistributionPoints(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain")],
None,
frozenset(
[
x509.ReasonFlags.key_compromise,
x509.ReasonFlags.ca_compromise,
]
),
[x509.UniformResourceIdentifier("uri://thing")],
),
]
)
cdp3 = x509.CRLDistributionPoints(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain")],
None,
frozenset([x509.ReasonFlags.key_compromise]),
[x509.UniformResourceIdentifier("uri://thing")],
),
]
)
assert hash(cdp) == hash(cdp2)
assert hash(cdp) != hash(cdp3)
def test_indexing(self):
ci = x509.CRLDistributionPoints(
[
x509.DistributionPoint(
None,
None,
None,
[x509.UniformResourceIdentifier("uri://thing")],
),
x509.DistributionPoint(
None,
None,
None,
[x509.UniformResourceIdentifier("uri://thing2")],
),
x509.DistributionPoint(
None,
None,
None,
[x509.UniformResourceIdentifier("uri://thing3")],
),
x509.DistributionPoint(
None,
None,
None,
[x509.UniformResourceIdentifier("uri://thing4")],
),
x509.DistributionPoint(
None,
None,
None,
[x509.UniformResourceIdentifier("uri://thing5")],
),
]
)
assert ci[-1] == ci[4]
assert ci[2:6:2] == [ci[2], ci[4]]
def test_public_bytes(self):
ext = x509.CRLDistributionPoints(
[
x509.DistributionPoint(
[x509.UniformResourceIdentifier("ftp://domain")],
None,
frozenset(
[
x509.ReasonFlags.key_compromise,
x509.ReasonFlags.ca_compromise,
]
),
[x509.UniformResourceIdentifier("uri://thing")],
),
]
)
assert (
ext.public_bytes()
== b"0'0%\xa0\x10\xa0\x0e\x86\x0cftp://domain\x81\x02\x05`\xa2\r"
b"\x86\x0buri://thing"
)
class TestCRLDistributionPointsExtension:
def test_fullname_and_crl_issuer(self, backend):
cert = _load_cert(
os.path.join(
"x509", "PKITS_data", "certs", "ValidcRLIssuerTest28EE.crt"
),
x509.load_der_x509_certificate,
)
cdps = cert.extensions.get_extension_for_oid(
ExtensionOID.CRL_DISTRIBUTION_POINTS
).value
assert cdps == x509.CRLDistributionPoints(
[
x509.DistributionPoint(
full_name=[
x509.DirectoryName(
x509.Name(
[
x509.NameAttribute(
NameOID.COUNTRY_NAME, "US"
),
x509.NameAttribute(
NameOID.ORGANIZATION_NAME,
"Test Certificates 2011",
),
x509.NameAttribute(
NameOID.ORGANIZATIONAL_UNIT_NAME,
"indirectCRL CA3 cRLIssuer",
),
x509.NameAttribute(
NameOID.COMMON_NAME,
"indirect CRL for indirectCRL CA3",
),
]
)
)
],
relative_name=None,
reasons=None,
crl_issuer=[
x509.DirectoryName(
x509.Name(
[
x509.NameAttribute(
NameOID.COUNTRY_NAME, "US"
),
x509.NameAttribute(
NameOID.ORGANIZATION_NAME,
"Test Certificates 2011",
),
x509.NameAttribute(
NameOID.ORGANIZATIONAL_UNIT_NAME,
"indirectCRL CA3 cRLIssuer",
),
]
)
)
],
)
]
)
def test_relativename_and_crl_issuer(self, backend):
cert = _load_cert(
os.path.join(
"x509", "PKITS_data", "certs", "ValidcRLIssuerTest29EE.crt"
),
x509.load_der_x509_certificate,
)
cdps = cert.extensions.get_extension_for_oid(
ExtensionOID.CRL_DISTRIBUTION_POINTS
).value
assert cdps == x509.CRLDistributionPoints(
[
x509.DistributionPoint(
full_name=None,
relative_name=x509.RelativeDistinguishedName(
[
x509.NameAttribute(
NameOID.COMMON_NAME,
"indirect CRL for indirectCRL CA3",
),
]
),
reasons=None,
crl_issuer=[
x509.DirectoryName(
x509.Name(
[
x509.NameAttribute(
NameOID.COUNTRY_NAME, "US"
),
x509.NameAttribute(
NameOID.ORGANIZATION_NAME,
"Test Certificates 2011",
),
x509.NameAttribute(
NameOID.ORGANIZATIONAL_UNIT_NAME,
"indirectCRL CA3 cRLIssuer",
),
]
)
)
],
)
]
)
def test_fullname_crl_issuer_reasons(self, backend):
cert = _load_cert(
os.path.join(
"x509", "custom", "cdp_fullname_reasons_crl_issuer.pem"
),
x509.load_pem_x509_certificate,
)
cdps = cert.extensions.get_extension_for_oid(
ExtensionOID.CRL_DISTRIBUTION_POINTS
).value
assert cdps == x509.CRLDistributionPoints(
[
x509.DistributionPoint(
full_name=[
x509.UniformResourceIdentifier(
"http://myhost.com/myca.crl"
)
],
relative_name=None,
reasons=frozenset(
[
x509.ReasonFlags.key_compromise,
x509.ReasonFlags.ca_compromise,
]
),
crl_issuer=[
x509.DirectoryName(
x509.Name(
[
x509.NameAttribute(
NameOID.COUNTRY_NAME, "US"
),
x509.NameAttribute(
NameOID.ORGANIZATION_NAME, "PyCA"
),
x509.NameAttribute(
NameOID.COMMON_NAME, "cryptography CA"
),
]
)
)
],
)
]
)
def test_all_reasons(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "cdp_all_reasons.pem"),
x509.load_pem_x509_certificate,
)
cdps = cert.extensions.get_extension_for_oid(
ExtensionOID.CRL_DISTRIBUTION_POINTS
).value
assert cdps == x509.CRLDistributionPoints(
[
x509.DistributionPoint(
full_name=[
x509.UniformResourceIdentifier(
"http://domain.com/some.crl"
)
],
relative_name=None,
reasons=frozenset(
[
x509.ReasonFlags.key_compromise,
x509.ReasonFlags.ca_compromise,
x509.ReasonFlags.affiliation_changed,
x509.ReasonFlags.superseded,
x509.ReasonFlags.privilege_withdrawn,
x509.ReasonFlags.cessation_of_operation,
x509.ReasonFlags.aa_compromise,
x509.ReasonFlags.certificate_hold,
]
),
crl_issuer=None,
)
]
)
def test_single_reason(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "cdp_reason_aa_compromise.pem"),
x509.load_pem_x509_certificate,
)
cdps = cert.extensions.get_extension_for_oid(
ExtensionOID.CRL_DISTRIBUTION_POINTS
).value
assert cdps == x509.CRLDistributionPoints(
[
x509.DistributionPoint(
full_name=[
x509.UniformResourceIdentifier(
"http://domain.com/some.crl"
)
],
relative_name=None,
reasons=frozenset([x509.ReasonFlags.aa_compromise]),
crl_issuer=None,
)
]
)
def test_crl_issuer_only(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "cdp_crl_issuer.pem"),
x509.load_pem_x509_certificate,
)
cdps = cert.extensions.get_extension_for_oid(
ExtensionOID.CRL_DISTRIBUTION_POINTS
).value
assert cdps == x509.CRLDistributionPoints(
[
x509.DistributionPoint(
full_name=None,
relative_name=None,
reasons=None,
crl_issuer=[
x509.DirectoryName(
x509.Name(
[
x509.NameAttribute(
NameOID.COMMON_NAME, "cryptography CA"
),
]
)
)
],
)
]
)
def test_crl_empty_hostname(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "cdp_empty_hostname.pem"),
x509.load_pem_x509_certificate,
)
cdps = cert.extensions.get_extension_for_oid(
ExtensionOID.CRL_DISTRIBUTION_POINTS
).value
assert cdps == x509.CRLDistributionPoints(
[
x509.DistributionPoint(
full_name=[
x509.UniformResourceIdentifier(
"ldap:///CN=A,OU=B,dc=C,DC=D?E?F?G?H=I"
)
],
relative_name=None,
reasons=None,
crl_issuer=None,
)
]
)
def test_public_bytes(self):
ext = x509.CRLDistributionPoints(
[
x509.DistributionPoint(
full_name=[
x509.UniformResourceIdentifier(
"ldap:///CN=A,OU=B,dc=C,DC=D?E?F?G?H=I"
)
],
relative_name=None,
reasons=None,
crl_issuer=None,
)
]
)
assert (
ext.public_bytes()
== b"0-0+\xa0)\xa0'\x86%ldap:///CN=A,OU=B,dc=C,DC=D?E?F?G?H=I"
)
class TestFreshestCRLExtension:
def test_vector(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "freshestcrl.pem"),
x509.load_pem_x509_certificate,
)
fcrl = cert.extensions.get_extension_for_class(x509.FreshestCRL).value
assert fcrl == x509.FreshestCRL(
[
x509.DistributionPoint(
full_name=[
x509.UniformResourceIdentifier(
"http://myhost.com/myca.crl"
),
x509.UniformResourceIdentifier(
"http://backup.myhost.com/myca.crl"
),
],
relative_name=None,
reasons=frozenset(
[
x509.ReasonFlags.ca_compromise,
x509.ReasonFlags.key_compromise,
]
),
crl_issuer=[
x509.DirectoryName(
x509.Name(
[
x509.NameAttribute(
NameOID.COUNTRY_NAME, "US"
),
x509.NameAttribute(
NameOID.COMMON_NAME, "cryptography CA"
),
]
)
)
],
)
]
)
def test_public_bytes(self):
ext = x509.FreshestCRL(
[
x509.DistributionPoint(
full_name=[
x509.UniformResourceIdentifier(
"http://myhost.com/myca.crl"
),
x509.UniformResourceIdentifier(
"http://backup.myhost.com/myca.crl"
),
],
relative_name=None,
reasons=frozenset(
[
x509.ReasonFlags.ca_compromise,
x509.ReasonFlags.key_compromise,
x509.ReasonFlags.aa_compromise,
]
),
crl_issuer=[
x509.DirectoryName(
x509.Name(
[
x509.NameAttribute(
NameOID.COUNTRY_NAME, "US"
),
x509.NameAttribute(
NameOID.COMMON_NAME, "cryptography CA"
),
]
)
)
],
)
]
)
assert (
ext.public_bytes()
== b"0w0u\xa0A\xa0?\x86\x1ahttp://myhost.com/myca.crl\x86!http://"
b"backup.myhost.com/myca.crl\x81\x03\x07`\x80\xa2+\xa4)0'1\x0b0\t"
b"\x06\x03U\x04\x06\x13\x02US1\x180\x16\x06\x03U\x04\x03\x0c\x0fc"
b"ryptography CA"
)
class TestOCSPNoCheckExtension:
def test_nocheck(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "ocsp_nocheck.pem"),
x509.load_pem_x509_certificate,
)
ext = cert.extensions.get_extension_for_oid(ExtensionOID.OCSP_NO_CHECK)
assert isinstance(ext.value, x509.OCSPNoCheck)
def test_eq(self):
onc1 = x509.OCSPNoCheck()
onc2 = x509.OCSPNoCheck()
assert onc1 == onc2
def test_hash(self):
onc1 = x509.OCSPNoCheck()
onc2 = x509.OCSPNoCheck()
assert hash(onc1) == hash(onc2)
def test_ne(self):
onc1 = x509.OCSPNoCheck()
onc2 = x509.OCSPNoCheck()
assert onc1 == onc2
assert (onc1 != onc2) is False
assert onc1 != object()
def test_repr(self):
onc = x509.OCSPNoCheck()
assert repr(onc) == "<OCSPNoCheck()>"
def test_public_bytes(self):
ext = x509.OCSPNoCheck()
assert ext.public_bytes() == b"\x05\x00"
class TestInhibitAnyPolicy:
def test_not_int(self):
with pytest.raises(TypeError):
x509.InhibitAnyPolicy("notint") # type:ignore[arg-type]
def test_negative_int(self):
with pytest.raises(ValueError):
x509.InhibitAnyPolicy(-1)
def test_repr(self):
iap = x509.InhibitAnyPolicy(0)
assert repr(iap) == "<InhibitAnyPolicy(skip_certs=0)>"
def test_eq(self):
iap = x509.InhibitAnyPolicy(1)
iap2 = x509.InhibitAnyPolicy(1)
assert iap == iap2
def test_ne(self):
iap = x509.InhibitAnyPolicy(1)
iap2 = x509.InhibitAnyPolicy(4)
assert iap != iap2
assert iap != object()
def test_hash(self):
iap = x509.InhibitAnyPolicy(1)
iap2 = x509.InhibitAnyPolicy(1)
iap3 = x509.InhibitAnyPolicy(4)
assert hash(iap) == hash(iap2)
assert hash(iap) != hash(iap3)
def test_public_bytes(self):
ext = x509.InhibitAnyPolicy(1)
assert ext.public_bytes() == b"\x02\x01\x01"
class TestInhibitAnyPolicyExtension:
def test_inhibit_any_policy(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "inhibit_any_policy_5.pem"),
x509.load_pem_x509_certificate,
)
iap = cert.extensions.get_extension_for_class(
x509.InhibitAnyPolicy
).value
assert iap.skip_certs == 5
class TestIssuingDistributionPointExtension:
@pytest.mark.parametrize(
("filename", "expected"),
[
(
"crl_idp_fullname_indirect_crl.pem",
x509.IssuingDistributionPoint(
full_name=[
x509.UniformResourceIdentifier(
"http://myhost.com/myca.crl"
)
],
relative_name=None,
only_contains_user_certs=False,
only_contains_ca_certs=False,
only_some_reasons=None,
indirect_crl=True,
only_contains_attribute_certs=False,
),
),
(
"crl_idp_fullname_only.pem",
x509.IssuingDistributionPoint(
full_name=[
x509.UniformResourceIdentifier(
"http://myhost.com/myca.crl"
)
],
relative_name=None,
only_contains_user_certs=False,
only_contains_ca_certs=False,
only_some_reasons=None,
indirect_crl=False,
only_contains_attribute_certs=False,
),
),
(
"crl_idp_fullname_only_aa.pem",
x509.IssuingDistributionPoint(
full_name=[
x509.UniformResourceIdentifier(
"http://myhost.com/myca.crl"
)
],
relative_name=None,
only_contains_user_certs=False,
only_contains_ca_certs=False,
only_some_reasons=None,
indirect_crl=False,
only_contains_attribute_certs=True,
),
),
(
"crl_idp_fullname_only_user.pem",
x509.IssuingDistributionPoint(
full_name=[
x509.UniformResourceIdentifier(
"http://myhost.com/myca.crl"
)
],
relative_name=None,
only_contains_user_certs=True,
only_contains_ca_certs=False,
only_some_reasons=None,
indirect_crl=False,
only_contains_attribute_certs=False,
),
),
(
"crl_idp_only_ca.pem",
x509.IssuingDistributionPoint(
full_name=None,
relative_name=x509.RelativeDistinguishedName(
[
x509.NameAttribute(
oid=x509.NameOID.ORGANIZATION_NAME,
value="PyCA",
)
]
),
only_contains_user_certs=False,
only_contains_ca_certs=True,
only_some_reasons=None,
indirect_crl=False,
only_contains_attribute_certs=False,
),
),
(
"crl_idp_reasons_only.pem",
x509.IssuingDistributionPoint(
full_name=None,
relative_name=None,
only_contains_user_certs=False,
only_contains_ca_certs=False,
only_some_reasons=frozenset(
[x509.ReasonFlags.key_compromise]
),
indirect_crl=False,
only_contains_attribute_certs=False,
),
),
(
"crl_idp_relative_user_all_reasons.pem",
x509.IssuingDistributionPoint(
full_name=None,
relative_name=x509.RelativeDistinguishedName(
[
x509.NameAttribute(
oid=x509.NameOID.ORGANIZATION_NAME,
value="PyCA",
)
]
),
only_contains_user_certs=True,
only_contains_ca_certs=False,
only_some_reasons=frozenset(
[
x509.ReasonFlags.key_compromise,
x509.ReasonFlags.ca_compromise,
x509.ReasonFlags.affiliation_changed,
x509.ReasonFlags.superseded,
x509.ReasonFlags.cessation_of_operation,
x509.ReasonFlags.certificate_hold,
x509.ReasonFlags.privilege_withdrawn,
x509.ReasonFlags.aa_compromise,
]
),
indirect_crl=False,
only_contains_attribute_certs=False,
),
),
(
"crl_idp_relativename_only.pem",
x509.IssuingDistributionPoint(
full_name=None,
relative_name=x509.RelativeDistinguishedName(
[
x509.NameAttribute(
oid=x509.NameOID.ORGANIZATION_NAME,
value="PyCA",
)
]
),
only_contains_user_certs=False,
only_contains_ca_certs=False,
only_some_reasons=None,
indirect_crl=False,
only_contains_attribute_certs=False,
),
),
],
)
def test_vectors(self, filename, expected, backend):
crl = _load_cert(
os.path.join("x509", "custom", filename),
x509.load_pem_x509_crl,
)
idp = crl.extensions.get_extension_for_class(
x509.IssuingDistributionPoint
).value
assert idp == expected
@pytest.mark.parametrize(
(
"error",
"only_contains_user_certs",
"only_contains_ca_certs",
"indirect_crl",
"only_contains_attribute_certs",
"only_some_reasons",
"full_name",
"relative_name",
),
[
(
TypeError,
False,
False,
False,
False,
"notafrozenset",
None,
None,
),
(
TypeError,
False,
False,
False,
False,
frozenset(["bad"]),
None,
None,
),
(
ValueError,
False,
False,
False,
False,
frozenset([x509.ReasonFlags.unspecified]),
None,
None,
),
(
ValueError,
False,
False,
False,
False,
frozenset([x509.ReasonFlags.remove_from_crl]),
None,
None,
),
(TypeError, "notabool", False, False, False, None, None, None),
(TypeError, False, "notabool", False, False, None, None, None),
(TypeError, False, False, "notabool", False, None, None, None),
(TypeError, False, False, False, "notabool", None, None, None),
(ValueError, True, True, False, False, None, None, None),
(ValueError, False, False, False, False, None, None, None),
],
)
def test_invalid_init(
self,
error,
only_contains_user_certs,
only_contains_ca_certs,
indirect_crl,
only_contains_attribute_certs,
only_some_reasons,
full_name,
relative_name,
):
with pytest.raises(error):
x509.IssuingDistributionPoint(
full_name,
relative_name,
only_contains_user_certs,
only_contains_ca_certs,
only_some_reasons,
indirect_crl,
only_contains_attribute_certs,
)
def test_repr(self):
idp = x509.IssuingDistributionPoint(
None,
None,
False,
False,
frozenset([x509.ReasonFlags.key_compromise]),
False,
False,
)
assert repr(idp) == (
"<IssuingDistributionPoint(full_name=None, relative_name=None,"
" only_contains_user_certs=False, only_contains_ca_certs=False"
", only_some_reasons=frozenset({<ReasonFlags.key_compromise: '"
"keyCompromise'>}), indirect_crl=False, only_contains_attribut"
"e_certs=False)>"
)
def test_eq(self):
idp1 = x509.IssuingDistributionPoint(
only_contains_user_certs=False,
only_contains_ca_certs=False,
indirect_crl=False,
only_contains_attribute_certs=False,
only_some_reasons=None,
full_name=None,
relative_name=x509.RelativeDistinguishedName(
[
x509.NameAttribute(
oid=x509.NameOID.ORGANIZATION_NAME, value="PyCA"
)
]
),
)
idp2 = x509.IssuingDistributionPoint(
only_contains_user_certs=False,
only_contains_ca_certs=False,
indirect_crl=False,
only_contains_attribute_certs=False,
only_some_reasons=None,
full_name=None,
relative_name=x509.RelativeDistinguishedName(
[
x509.NameAttribute(
oid=x509.NameOID.ORGANIZATION_NAME, value="PyCA"
)
]
),
)
assert idp1 == idp2
def test_ne(self):
idp1 = x509.IssuingDistributionPoint(
only_contains_user_certs=False,
only_contains_ca_certs=False,
indirect_crl=False,
only_contains_attribute_certs=False,
only_some_reasons=None,
full_name=None,
relative_name=x509.RelativeDistinguishedName(
[
x509.NameAttribute(
oid=x509.NameOID.ORGANIZATION_NAME, value="PyCA"
)
]
),
)
idp2 = x509.IssuingDistributionPoint(
only_contains_user_certs=True,
only_contains_ca_certs=False,
indirect_crl=False,
only_contains_attribute_certs=False,
only_some_reasons=None,
full_name=None,
relative_name=x509.RelativeDistinguishedName(
[
x509.NameAttribute(
oid=x509.NameOID.ORGANIZATION_NAME, value="PyCA"
)
]
),
)
assert idp1 != idp2
assert idp1 != object()
def test_hash(self):
idp1 = x509.IssuingDistributionPoint(
None, None, True, False, None, False, False
)
idp2 = x509.IssuingDistributionPoint(
None, None, True, False, None, False, False
)
idp3 = x509.IssuingDistributionPoint(
None,
x509.RelativeDistinguishedName(
[
x509.NameAttribute(
oid=x509.NameOID.ORGANIZATION_NAME, value="PyCA"
)
]
),
True,
False,
None,
False,
False,
)
assert hash(idp1) == hash(idp2)
assert hash(idp1) != hash(idp3)
@pytest.mark.parametrize(
"idp",
[
x509.IssuingDistributionPoint(
full_name=[
x509.UniformResourceIdentifier(
"http://myhost.com/myca.crl"
)
],
relative_name=None,
only_contains_user_certs=False,
only_contains_ca_certs=False,
only_some_reasons=None,
indirect_crl=True,
only_contains_attribute_certs=False,
),
x509.IssuingDistributionPoint(
full_name=[
x509.UniformResourceIdentifier(
"http://myhost.com/myca.crl"
)
],
relative_name=None,
only_contains_user_certs=False,
only_contains_ca_certs=False,
only_some_reasons=None,
indirect_crl=False,
only_contains_attribute_certs=False,
),
x509.IssuingDistributionPoint(
full_name=[
x509.UniformResourceIdentifier(
"http://myhost.com/myca.crl"
)
],
relative_name=None,
only_contains_user_certs=False,
only_contains_ca_certs=False,
only_some_reasons=None,
indirect_crl=False,
only_contains_attribute_certs=True,
),
x509.IssuingDistributionPoint(
full_name=[
x509.UniformResourceIdentifier(
"http://myhost.com/myca.crl"
)
],
relative_name=None,
only_contains_user_certs=True,
only_contains_ca_certs=False,
only_some_reasons=None,
indirect_crl=False,
only_contains_attribute_certs=False,
),
x509.IssuingDistributionPoint(
full_name=None,
relative_name=x509.RelativeDistinguishedName(
[
x509.NameAttribute(
oid=x509.NameOID.ORGANIZATION_NAME, value="PyCA"
)
]
),
only_contains_user_certs=False,
only_contains_ca_certs=True,
only_some_reasons=None,
indirect_crl=False,
only_contains_attribute_certs=False,
),
x509.IssuingDistributionPoint(
full_name=None,
relative_name=None,
only_contains_user_certs=False,
only_contains_ca_certs=True,
only_some_reasons=frozenset([x509.ReasonFlags.key_compromise]),
indirect_crl=False,
only_contains_attribute_certs=False,
),
x509.IssuingDistributionPoint(
full_name=None,
relative_name=x509.RelativeDistinguishedName(
[
x509.NameAttribute(
oid=x509.NameOID.ORGANIZATION_NAME, value="PyCA"
),
x509.NameAttribute(
oid=x509.NameOID.COMMON_NAME, value="cryptography"
),
]
),
only_contains_user_certs=True,
only_contains_ca_certs=False,
only_some_reasons=frozenset(
[
x509.ReasonFlags.key_compromise,
x509.ReasonFlags.ca_compromise,
x509.ReasonFlags.affiliation_changed,
x509.ReasonFlags.privilege_withdrawn,
x509.ReasonFlags.aa_compromise,
]
),
indirect_crl=False,
only_contains_attribute_certs=False,
),
x509.IssuingDistributionPoint(
full_name=None,
relative_name=x509.RelativeDistinguishedName(
[
x509.NameAttribute(
oid=x509.NameOID.ORGANIZATION_NAME, value="PyCA"
)
]
),
only_contains_user_certs=False,
only_contains_ca_certs=False,
only_some_reasons=None,
indirect_crl=False,
only_contains_attribute_certs=False,
),
],
)
def test_generate(self, rsa_key_2048: rsa.RSAPrivateKey, idp, backend):
key = rsa_key_2048
last_update = datetime.datetime(2002, 1, 1, 12, 1)
next_update = datetime.datetime(2030, 1, 1, 12, 1)
builder = (
x509.CertificateRevocationListBuilder()
.issuer_name(
x509.Name(
[
x509.NameAttribute(
NameOID.COMMON_NAME, "cryptography.io CA"
)
]
)
)
.last_update(last_update)
.next_update(next_update)
.add_extension(idp, True)
)
crl = builder.sign(key, hashes.SHA256(), backend)
ext = crl.extensions.get_extension_for_class(
x509.IssuingDistributionPoint
)
assert ext.critical is True
assert ext.value == idp
def test_public_bytes(self):
ext = x509.IssuingDistributionPoint(
full_name=None,
relative_name=x509.RelativeDistinguishedName(
[
x509.NameAttribute(
oid=x509.NameOID.ORGANIZATION_NAME,
value="PyCA",
)
]
),
only_contains_user_certs=False,
only_contains_ca_certs=False,
only_some_reasons=None,
indirect_crl=False,
only_contains_attribute_certs=False,
)
assert (
ext.public_bytes()
== b"0\x11\xa0\x0f\xa1\r0\x0b\x06\x03U\x04\n\x0c\x04PyCA"
)
class TestPrecertPoisonExtension:
def test_load(self, backend):
cert = _load_cert(
os.path.join("x509", "cryptography.io.precert.pem"),
x509.load_pem_x509_certificate,
)
poison = cert.extensions.get_extension_for_oid(
ExtensionOID.PRECERT_POISON
).value
assert isinstance(poison, x509.PrecertPoison)
poison = cert.extensions.get_extension_for_class(
x509.PrecertPoison
).value
assert isinstance(poison, x509.PrecertPoison)
def test_generate(self, rsa_key_2048: rsa.RSAPrivateKey, backend):
private_key = rsa_key_2048
cert = (
_make_certbuilder(private_key)
.add_extension(x509.PrecertPoison(), critical=True)
.sign(private_key, hashes.SHA256(), backend)
)
poison = cert.extensions.get_extension_for_oid(
ExtensionOID.PRECERT_POISON
).value
assert isinstance(poison, x509.PrecertPoison)
def test_eq(self):
pcp1 = x509.PrecertPoison()
pcp2 = x509.PrecertPoison()
assert pcp1 == pcp2
def test_hash(self):
pcp1 = x509.PrecertPoison()
pcp2 = x509.PrecertPoison()
assert hash(pcp1) == hash(pcp2)
def test_ne(self):
pcp1 = x509.PrecertPoison()
pcp2 = x509.PrecertPoison()
assert pcp1 == pcp2
assert (pcp1 != pcp2) is False
assert pcp1 != object()
def test_repr(self):
pcp = x509.PrecertPoison()
assert repr(pcp) == "<PrecertPoison()>"
def test_public_bytes(self):
ext = x509.PrecertPoison()
assert ext.public_bytes() == b"\x05\x00"
class TestSignedCertificateTimestamps:
def test_eq(self, backend):
sct = (
_load_cert(
os.path.join("x509", "badssl-sct.pem"),
x509.load_pem_x509_certificate,
)
.extensions.get_extension_for_class(
x509.PrecertificateSignedCertificateTimestamps
)
.value[0]
)
sct2 = (
_load_cert(
os.path.join("x509", "badssl-sct.pem"),
x509.load_pem_x509_certificate,
)
.extensions.get_extension_for_class(
x509.PrecertificateSignedCertificateTimestamps
)
.value[0]
)
assert sct == sct2
def test_ne(self, backend):
sct = (
_load_cert(
os.path.join("x509", "badssl-sct.pem"),
x509.load_pem_x509_certificate,
)
.extensions.get_extension_for_class(
x509.PrecertificateSignedCertificateTimestamps
)
.value[0]
)
sct2 = (
_load_cert(
os.path.join("x509", "cryptography-scts.pem"),
x509.load_pem_x509_certificate,
)
.extensions.get_extension_for_class(
x509.PrecertificateSignedCertificateTimestamps
)
.value[0]
)
assert sct != sct2
assert sct != object()
def test_hash(self, backend):
sct = (
_load_cert(
os.path.join("x509", "badssl-sct.pem"),
x509.load_pem_x509_certificate,
)
.extensions.get_extension_for_class(
x509.PrecertificateSignedCertificateTimestamps
)
.value[0]
)
sct2 = (
_load_cert(
os.path.join("x509", "badssl-sct.pem"),
x509.load_pem_x509_certificate,
)
.extensions.get_extension_for_class(
x509.PrecertificateSignedCertificateTimestamps
)
.value[0]
)
sct3 = (
_load_cert(
os.path.join("x509", "cryptography-scts.pem"),
x509.load_pem_x509_certificate,
)
.extensions.get_extension_for_class(
x509.PrecertificateSignedCertificateTimestamps
)
.value[0]
)
assert hash(sct) == hash(sct2)
assert hash(sct) != hash(sct3)
def test_public_bytes(self, backend):
ext = (
load_vectors_from_file(
os.path.join("x509", "ocsp", "resp-sct-extension.der"),
lambda data: ocsp.load_der_ocsp_response(data.read()),
mode="rb",
)
.single_extensions.get_extension_for_class(
x509.SignedCertificateTimestamps
)
.value
)
assert ext.public_bytes() == (
b"\x04\x82\x01\xe6\x01\xe4\x00w\x00D\x94e.\xb0\xee\xce\xaf\xc4"
b"@\x07\xd8\xa8\xfe(\xc0\xda\xe6\x82\xbe\xd8\xcb1\xb5?\xd33"
b"\x96\xb5\xb6\x81\xa8\x00\x00\x01no\xc33h\x00\x00\x04\x03\x00"
b"H0F\x02!\x00\xa0}J\xa7\xb1Y\xb4\x15P\xd7\x95Y\x12\xfb\xa1"
b"\xdfh\x96u\xa3\x0f_\x01\xf2\xfd\xcbMI\x9bt\xe2\xfe\x02!\x00"
b"\x89E\xd7\x86N<>\xe8\x07\xc4\xca\xdbO:\xb7\x9f]E\xbc\x1az"
b"\xe5h\xab%\xdaukT\x8a\xf7\xc1\x00w\x00oSv\xac1\xf01\x19\xd8"
b"\x99\x00\xa4Q\x15\xffw\x15\x1c\x11\xd9\x02\xc1\x00)\x06\x8d"
b"\xb2\x08\x9a7\xd9\x13\x00\x00\x01no\xc33m\x00\x00\x04\x03"
b"\x00H0F\x02!\x00\xd4\xe06\xd2\xed~{\x9fs-E2\xd8\xd2\xb41\xc6"
b"v\x8b3\xf2\tS\x1d\xd8SUe\xe1\xcf\xfc;\x02!\x00\xd9cF[\x8e\xac"
b'4\x02@\xd6\x8a\x10y\x98\x92\xbee\xf4\n\x11L\xbfpI(Y"O\x1al'
b"\xe9g\x00w\x00\xbb\xd9\xdf\xbc\x1f\x8aq\xb5\x93\x94#\x97\xaa"
b"\x92{G8W\x95\n\xabR\xe8\x1a\x90\x96d6\x8e\x1e\xd1\x85\x00"
b"\x00\x01no\xc34g\x00\x00\x04\x03\x00H0F\x02!\x00\xf4:\xec"
b"\x1b\xdeQ\r\xf8S\x9c\xf2\xeee<\xcf\xc5:\x0f\x0f\xeb\x8bv\x9f"
b'8d.z\x9c"K\x9b\x11\x02!\x00\xe7`\xe9Ex\xf7)B<\xf7\xd62b\xfa'
b"\xa2\xc7!\xc4\xbau\xcb\xad\x0ezEZ\x11\x13\xa1+\x89J\x00w\x00"
b"\xeeK\xbd\xb7u\xce`\xba\xe1Bi\x1f\xab\xe1\x9ef\xa3\x0f~_\xb0"
b"r\xd8\x83\x00\xc4{\x89z\xa8\xfd\xcb\x00\x00\x01no\xc32\xdd"
b"\x00\x00\x04\x03\x00H0F\x02!\x00\x95Y\x81\x7f\xa4\xe5\x17o"
b"\x06}\xac\xcdt-\xb0\xb8L\x18H\xecB\xcc-\xe5\x13>\x07\xba\xc0"
b"}\xa3\xe6\x02!\x00\xbf\xc8\x88\x93m\x8d\xc3(GS\xaf=4}\x97"
b"\xe6\xc2\x1djQ\x0e0\x8c\xcc\x9d\xc2\xc7\xc3\xb1\x0f\xec\x98"
)
class TestPrecertificateSignedCertificateTimestampsExtension:
def test_init(self):
with pytest.raises(TypeError):
x509.PrecertificateSignedCertificateTimestamps(
[object()] # type:ignore[list-item]
)
def test_repr(self):
assert repr(x509.PrecertificateSignedCertificateTimestamps([])) == (
"<PrecertificateSignedCertificateTimestamps([])>"
)
def test_eq(self, backend):
psct1 = (
_load_cert(
os.path.join("x509", "badssl-sct.pem"),
x509.load_pem_x509_certificate,
)
.extensions.get_extension_for_class(
x509.PrecertificateSignedCertificateTimestamps
)
.value
)
psct2 = (
_load_cert(
os.path.join("x509", "badssl-sct.pem"),
x509.load_pem_x509_certificate,
)
.extensions.get_extension_for_class(
x509.PrecertificateSignedCertificateTimestamps
)
.value
)
assert psct1 == psct2
def test_ne(self, backend):
psct1 = (
_load_cert(
os.path.join("x509", "cryptography-scts.pem"),
x509.load_pem_x509_certificate,
)
.extensions.get_extension_for_class(
x509.PrecertificateSignedCertificateTimestamps
)
.value
)
psct2 = (
_load_cert(
os.path.join("x509", "badssl-sct.pem"),
x509.load_pem_x509_certificate,
)
.extensions.get_extension_for_class(
x509.PrecertificateSignedCertificateTimestamps
)
.value
)
assert psct1 != psct2
assert psct1 != object()
def test_ordering(self, backend):
psct1 = (
_load_cert(
os.path.join("x509", "cryptography-scts.pem"),
x509.load_pem_x509_certificate,
)
.extensions.get_extension_for_class(
x509.PrecertificateSignedCertificateTimestamps
)
.value
)
psct2 = (
_load_cert(
os.path.join("x509", "badssl-sct.pem"),
x509.load_pem_x509_certificate,
)
.extensions.get_extension_for_class(
x509.PrecertificateSignedCertificateTimestamps
)
.value
)
with pytest.raises(TypeError):
psct1[0] < psct2[0]
def test_hash(self, backend):
psct1 = (
_load_cert(
os.path.join("x509", "badssl-sct.pem"),
x509.load_pem_x509_certificate,
)
.extensions.get_extension_for_class(
x509.PrecertificateSignedCertificateTimestamps
)
.value
)
psct2 = (
_load_cert(
os.path.join("x509", "badssl-sct.pem"),
x509.load_pem_x509_certificate,
)
.extensions.get_extension_for_class(
x509.PrecertificateSignedCertificateTimestamps
)
.value
)
psct3 = (
_load_cert(
os.path.join("x509", "cryptography-scts.pem"),
x509.load_pem_x509_certificate,
)
.extensions.get_extension_for_class(
x509.PrecertificateSignedCertificateTimestamps
)
.value
)
assert hash(psct1) == hash(psct2)
assert hash(psct1) != hash(psct3)
def test_simple(self, backend):
cert = _load_cert(
os.path.join("x509", "badssl-sct.pem"),
x509.load_pem_x509_certificate,
)
scts = cert.extensions.get_extension_for_class(
x509.PrecertificateSignedCertificateTimestamps
).value
assert len(scts) == 1
[sct] = scts
assert scts[0] == sct
assert sct.version == x509.certificate_transparency.Version.v1
assert sct.log_id == (
b"\xa7\xceJNb\x07\xe0\xad\xde\xe5\xfd\xaaK\x1f\x86v\x87g\xb5\xd0"
b"\x02\xa5]G1\x0e~g\n\x95\xea\xb2"
)
assert sct.timestamp == datetime.datetime(
2016, 11, 17, 1, 56, 25, 396000
)
assert (
sct.entry_type
== x509.certificate_transparency.LogEntryType.PRE_CERTIFICATE
)
assert isinstance(sct.signature_hash_algorithm, hashes.SHA256)
assert (
sct.signature_algorithm
== x509.certificate_transparency.SignatureAlgorithm.ECDSA
)
assert sct.signature == (
b"\x30\x45\x02\x21\x00\xb8\x03\xad\x34\xf6\xfc\x0f\x2c\xff\x84\xa0"
b"\x86\xe5\xd7\xcf\x5a\xf0\x0a\x07\x62\x6a\x7f\xb3\xa6\x44\x64\xf1"
b"\x95\xa4\x48\x45\x11\x02\x20\x2f\x61\x8d\x53\x1b\x6f\x4a\xb8\x0a"
b"\x67\xb2\x07\xe1\x8f\x6d\xad\xd1\x04\x4a\x5e\xb3\x89\xef\x7c\x60"
b"\xc2\x68\x53\xf9\x3d\x1f\x6d"
)
assert sct.extension_bytes == b""
def test_generate(self, rsa_key_2048: rsa.RSAPrivateKey, backend):
cert = _load_cert(
os.path.join("x509", "badssl-sct.pem"),
x509.load_pem_x509_certificate,
)
scts = cert.extensions.get_extension_for_class(
x509.PrecertificateSignedCertificateTimestamps
).value
assert len(scts) == 1
[sct] = scts
private_key = rsa_key_2048
builder = _make_certbuilder(private_key).add_extension(
x509.PrecertificateSignedCertificateTimestamps([sct]),
critical=False,
)
cert = builder.sign(private_key, hashes.SHA256(), backend)
ext = cert.extensions.get_extension_for_class(
x509.PrecertificateSignedCertificateTimestamps
).value
assert list(ext) == [sct]
def test_invalid_version(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "invalid-sct-version.der"),
x509.load_der_x509_certificate,
)
with pytest.raises(ValueError):
cert.extensions
def test_invalid_hash_algorithm(self, backend):
cert = _load_cert(
os.path.join("x509", "badssl-sct-none-hash.der"),
x509.load_der_x509_certificate,
)
with pytest.raises(
ValueError, match="Invalid/unsupported hash algorithm for SCT: 0"
):
cert.extensions
def test_invalid_signature_algorithm(self, backend):
cert = _load_cert(
os.path.join("x509", "badssl-sct-anonymous-sig.der"),
x509.load_der_x509_certificate,
)
with pytest.raises(
ValueError,
match="Invalid/unsupported signature algorithm for SCT: 0",
):
cert.extensions
def test_invalid_length(self, backend):
cert = _load_cert(
os.path.join("x509", "custom", "invalid-sct-length.der"),
x509.load_der_x509_certificate,
)
with pytest.raises(ValueError):
cert.extensions
def test_public_bytes(self, backend):
ext = (
_load_cert(
os.path.join("x509", "cryptography-scts.pem"),
x509.load_pem_x509_certificate,
)
.extensions.get_extension_for_class(
x509.PrecertificateSignedCertificateTimestamps
)
.value
)
assert (
ext.public_bytes()
== b"\x04\x81\xf4\x00\xf2\x00w\x00)<Q\x96T\xc89e\xba\xaaP\xfcX"
b"\x07\xd4\xb7o\xbfXz)r\xdc\xa4\xc3\x0c\xf4\xe5EG\xf4x\x00\x00"
b"\x01f\x17\xabJ\xe9\x00\x00\x04\x03\x00H0F\x02!\x00\xa5\xce\xa8|"
b"Pnq\x8c&\xe3H\xbb\xf4\x0b\xc1\x0eu\xe8M}\xe6:\x8bM\x1e~\x89\nr"
b"\xda\xa4@\x02!\x00\xde\xa9\xf1\xd0\xc3S\xfc\xd37\xe1[q_\x80("
b"\x85u\x80]Kw\x02\xc0'\x02\xee\xd8\xf7\x15N|r\x00w\x00oSv\xac1"
b"\xf01\x19\xd8\x99\x00\xa4Q\x15\xffw\x15\x1c\x11\xd9\x02\xc1\x00"
b")\x06\x8d\xb2\x08\x9a7\xd9\x13\x00\x00\x01f\x17\xabKp\x00\x00"
b"\x04\x03\x00H0F\x02!\x00\xa2\xe0\xd9\xfec\x94\x14\xf8\xbd\xcd"
b"\xd7\xf6\x9d\xb0\x90\xd5\xb8\x92\x07\xb4\x80\xc7\x8a\xc2\xc5"
b"\xc4\x0e6\x1e\x92\xa3\xa6\x02!\x00\xbc\xe7\r\xc3\x841\xfa\xfc"
b"\x85\x1f%\xc0#N\\\xdeK\x90d\xe0\x8d<{\xca\xdbdc\xeft\x87g\x10"
)
class TestInvalidExtension:
def test_invalid_certificate_policies_data(self, backend):
# UserNotice OID but CPSURI structure
cert = _load_cert(
os.path.join("x509", "custom", "cp_invalid.pem"),
x509.load_pem_x509_certificate,
)
with pytest.raises(ValueError):
cert.extensions
# CPSURI OID but UserNotice structure
cert = _load_cert(
os.path.join("x509", "custom", "cp_invalid2.der"),
x509.load_der_x509_certificate,
)
with pytest.raises(ValueError):
cert.extensions
class TestOCSPNonce:
def test_non_bytes(self):
with pytest.raises(TypeError):
x509.OCSPNonce(38) # type:ignore[arg-type]
def test_eq(self):
nonce1 = x509.OCSPNonce(b"0" * 5)
nonce2 = x509.OCSPNonce(b"0" * 5)
assert nonce1 == nonce2
def test_ne(self):
nonce1 = x509.OCSPNonce(b"0" * 5)
nonce2 = x509.OCSPNonce(b"0" * 6)
assert nonce1 != nonce2
assert nonce1 != object()
def test_repr(self):
nonce1 = x509.OCSPNonce(b"nonce")
assert repr(nonce1) == "<OCSPNonce(nonce=b'nonce')>"
def test_hash(self):
nonce1 = x509.OCSPNonce(b"0" * 5)
nonce2 = x509.OCSPNonce(b"0" * 5)
nonce3 = x509.OCSPNonce(b"1" * 5)
assert hash(nonce1) == hash(nonce2)
assert hash(nonce1) != hash(nonce3)
def test_public_bytes(self):
ext = x509.OCSPNonce(b"0" * 5)
assert ext.public_bytes() == b"\x04\x0500000"
class TestOCSPAcceptableResponses:
def test_invalid_types(self):
with pytest.raises(TypeError):
x509.OCSPAcceptableResponses(38) # type:ignore[arg-type]
with pytest.raises(TypeError):
x509.OCSPAcceptableResponses([38]) # type:ignore[list-item]
def test_eq(self):
acceptable_responses1 = x509.OCSPAcceptableResponses(
[ObjectIdentifier("1.2.3")]
)
acceptable_responses2 = x509.OCSPAcceptableResponses(
[ObjectIdentifier("1.2.3")]
)
assert acceptable_responses1 == acceptable_responses2
def test_ne(self):
acceptable_responses1 = x509.OCSPAcceptableResponses(
[ObjectIdentifier("1.2.3")]
)
acceptable_responses2 = x509.OCSPAcceptableResponses(
[ObjectIdentifier("1.2.4")]
)
assert acceptable_responses1 != acceptable_responses2
assert acceptable_responses1 != object()
def test_repr(self):
acceptable_responses = x509.OCSPAcceptableResponses([])
assert (
repr(acceptable_responses)
== "<OCSPAcceptableResponses(responses=[])>"
)
def test_hash(self):
acceptable_responses1 = x509.OCSPAcceptableResponses(
[ObjectIdentifier("1.2.3")]
)
acceptable_responses2 = x509.OCSPAcceptableResponses(
[ObjectIdentifier("1.2.3")]
)
acceptable_responses3 = x509.OCSPAcceptableResponses(
[ObjectIdentifier("1.2.4")]
)
assert hash(acceptable_responses1) == hash(acceptable_responses2)
assert hash(acceptable_responses1) != hash(acceptable_responses3)
def test_iter(self):
acceptable_responses1 = x509.OCSPAcceptableResponses(
[ObjectIdentifier("1.2.3")]
)
assert list(acceptable_responses1) == [ObjectIdentifier("1.2.3")]
def test_public_bytes(self):
ext = x509.OCSPAcceptableResponses([])
assert ext.public_bytes() == b"\x30\x00"
ext = x509.OCSPAcceptableResponses(
[ObjectIdentifier("1.3.6.1.5.5.7.48.1.1")]
)
assert (
ext.public_bytes()
== b"\x30\x0b\x06\t+\x06\x01\x05\x05\x07\x30\x01\x01"
)
class TestMSCertificateTemplate:
def test_invalid_type(self):
with pytest.raises(TypeError):
x509.MSCertificateTemplate(
"notanoid", # type:ignore[arg-type]
None,
None,
)
oid = x509.ObjectIdentifier("1.2.3.4")
with pytest.raises(TypeError):
x509.MSCertificateTemplate(
oid,
"notanint", # type:ignore[arg-type]
None,
)
with pytest.raises(TypeError):
x509.MSCertificateTemplate(
oid,
None,
"notanint", # type:ignore[arg-type]
)
def test_eq(self):
template1 = x509.MSCertificateTemplate(
ObjectIdentifier("1.2.3.4"), None, None
)
template2 = x509.MSCertificateTemplate(
ObjectIdentifier("1.2.3.4"), None, None
)
assert template1 == template2
def test_ne(self):
template1 = x509.MSCertificateTemplate(
ObjectIdentifier("1.2.3.4"), None, None
)
template2 = x509.MSCertificateTemplate(
ObjectIdentifier("1.2.3.4"), 1, None
)
template3 = x509.MSCertificateTemplate(
ObjectIdentifier("1.2.3.4"), None, 1
)
template4 = x509.MSCertificateTemplate(
ObjectIdentifier("1.2.3"), None, None
)
assert template1 != template2
assert template1 != template3
assert template1 != template4
assert template1 != object()
def test_repr(self):
template = x509.MSCertificateTemplate(
ObjectIdentifier("1.2.3.4"), None, None
)
assert repr(template) == (
"<MSCertificateTemplate(template_id=<ObjectIdentifier(oid=1.2.3.4,"
" name=Unknown OID)>, major_version=None, minor_version=None)>"
)
def test_hash(self):
template1 = x509.MSCertificateTemplate(
ObjectIdentifier("1.2.3.4"), None, None
)
template2 = x509.MSCertificateTemplate(
ObjectIdentifier("1.2.3.4"), None, None
)
template3 = x509.MSCertificateTemplate(
ObjectIdentifier("1.2.3.4"), None, 1
)
template4 = x509.MSCertificateTemplate(
ObjectIdentifier("1.2.3"), None, None
)
assert hash(template1) == hash(template2)
assert hash(template1) != hash(template3)
assert hash(template1) != hash(template4)
def test_public_bytes(self):
ext = x509.MSCertificateTemplate(
ObjectIdentifier("1.2.3.4"), None, None
)
assert ext.public_bytes() == b"0\x05\x06\x03*\x03\x04"
ext = x509.MSCertificateTemplate(ObjectIdentifier("1.2.3.4"), 1, 0)
assert (
ext.public_bytes()
== b"0\x0b\x06\x03*\x03\x04\x02\x01\x01\x02\x01\x00"
)
class TestNamingAuthority:
def test_invalid_init(self):
with pytest.raises(TypeError):
x509.NamingAuthority(
42, # type:ignore[arg-type]
None,
None,
)
with pytest.raises(TypeError):
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"),
42, # type:ignore[arg-type]
None,
)
with pytest.raises(TypeError):
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"),
"https://example.com",
42, # type:ignore[arg-type]
)
def test_eq(self):
authority1 = x509.NamingAuthority(None, None, None)
authority2 = x509.NamingAuthority(None, None, None)
assert authority1 == authority2
authority1 = x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
)
authority2 = x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
)
assert authority1 == authority2
def test_ne(self):
authority1 = x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
)
authority2 = x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), None, None
)
authority3 = x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", None
)
authority4 = x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), None, "spam"
)
authority5 = x509.NamingAuthority(None, "https://example.com", "spam")
authority6 = x509.NamingAuthority(None, None, "spam")
authority7 = x509.NamingAuthority(None, "https://example.com", None)
authority8 = x509.NamingAuthority(None, None, None)
assert authority1 != authority2
assert authority1 != authority3
assert authority1 != authority4
assert authority1 != authority5
assert authority1 != authority6
assert authority1 != authority7
assert authority1 != authority8
assert authority1 != object()
def test_repr(self):
authority = x509.NamingAuthority(None, None, None)
assert repr(authority) == (
"<NamingAuthority(id=None, url=None, text=None)>"
)
authority = x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
)
assert repr(authority) == (
"<NamingAuthority("
"id=<ObjectIdentifier(oid=1.2.3, name=Unknown OID)>, "
"url=https://example.com, text=spam)>"
)
def test_hash(self):
authority1 = x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
)
authority2 = x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
)
authority3 = x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), None, None
)
authority4 = x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", None
)
authority5 = x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), None, "spam"
)
authority6 = x509.NamingAuthority(None, "https://example.com", "spam")
authority7 = x509.NamingAuthority(None, None, "spam")
authority8 = x509.NamingAuthority(None, "https://example.com", None)
authority9 = x509.NamingAuthority(None, None, None)
assert hash(authority1) == hash(authority2)
assert hash(authority1) != hash(authority3)
assert hash(authority1) != hash(authority4)
assert hash(authority1) != hash(authority5)
assert hash(authority1) != hash(authority6)
assert hash(authority1) != hash(authority7)
assert hash(authority1) != hash(authority8)
assert hash(authority1) != hash(authority9)
class TestProfessionInfo:
def test_invalid_init(self):
with pytest.raises(TypeError):
x509.ProfessionInfo(
None,
None, # type:ignore[arg-type]
None,
None,
None,
)
with pytest.raises(TypeError):
x509.ProfessionInfo(
"spam", # type:ignore[arg-type]
[],
[],
None,
None,
)
with pytest.raises(TypeError):
x509.ProfessionInfo(
None,
[42], # type:ignore[list-item]
[],
None,
None,
)
with pytest.raises(TypeError):
x509.ProfessionInfo(
None,
[],
"spam", # type:ignore[arg-type]
None,
None,
)
with pytest.raises(TypeError):
x509.ProfessionInfo(
None,
[],
[],
42, # type:ignore[arg-type]
None,
)
with pytest.raises(TypeError):
x509.ProfessionInfo(
None,
[],
[],
None,
42, # type:ignore[arg-type]
)
def test_eq(self):
info1 = x509.ProfessionInfo(None, [], [], None, None)
info2 = x509.ProfessionInfo(None, [], [], None, None)
assert info1 == info2
info1 = x509.ProfessionInfo(None, [], None, None, None)
info2 = x509.ProfessionInfo(None, [], None, None, None)
assert info1 == info2
info1 = x509.ProfessionInfo(
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
),
["spam"],
[x509.ObjectIdentifier("1.2.3.4")],
"eggs",
b"\x01\x02\x03",
)
info2 = x509.ProfessionInfo(
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
),
["spam"],
[x509.ObjectIdentifier("1.2.3.4")],
"eggs",
b"\x01\x02\x03",
)
assert info1 == info2
def test_ne(self):
info1 = x509.ProfessionInfo(
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
),
["spam"],
[x509.ObjectIdentifier("1.2.3.4")],
"eggs",
b"\x01\x02\x03",
)
info2 = x509.ProfessionInfo(
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
),
["spam"],
[x509.ObjectIdentifier("1.2.3.4")],
"eggs",
None,
)
info3 = x509.ProfessionInfo(
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
),
["spam"],
[x509.ObjectIdentifier("1.2.3.4")],
None,
None,
)
info4 = x509.ProfessionInfo(
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
),
["spam"],
[],
None,
None,
)
info5 = x509.ProfessionInfo(
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
),
[],
[],
None,
None,
)
info6 = x509.ProfessionInfo(None, ["spam"], [], None, None)
info7 = x509.ProfessionInfo(
None, [], [x509.ObjectIdentifier("1.2.3")], None, None
)
info8 = x509.ProfessionInfo(None, [], [], "spam", None)
info9 = x509.ProfessionInfo(None, [], [], None, b"\x01\x02\x03")
info10 = x509.ProfessionInfo(None, [], [], None, None)
info11 = x509.ProfessionInfo(None, [], None, None, None)
assert info1 != info2
assert info1 != info2
assert info1 != info3
assert info1 != info4
assert info1 != info5
assert info1 != info6
assert info1 != info7
assert info1 != info8
assert info1 != info9
assert info1 != info10
assert info1 != info11
assert info1 != object()
def test_repr(self):
info = x509.ProfessionInfo(None, [], [], None, None)
assert repr(info) == (
"<ProfessionInfo("
"naming_authority=None, "
"profession_items=[], "
"profession_oids=[], "
"registration_number=None, "
"add_profession_info=None)>"
)
info = x509.ProfessionInfo(None, [], None, None, None)
assert repr(info) == (
"<ProfessionInfo("
"naming_authority=None, "
"profession_items=[], "
"profession_oids=None, "
"registration_number=None, "
"add_profession_info=None)>"
)
info = x509.ProfessionInfo(
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
),
["spam"],
[x509.ObjectIdentifier("1.2.3.4")],
"eggs",
b"\x01\x02\x03",
)
assert repr(info) == (
"<ProfessionInfo("
"naming_authority=<NamingAuthority("
"id=<ObjectIdentifier(oid=1.2.3, name=Unknown OID)>, "
"url=https://example.com, text=spam)>, "
"profession_items=['spam'], "
"profession_oids="
"[<ObjectIdentifier(oid=1.2.3.4, name=Unknown OID)>], "
"registration_number=eggs, "
"add_profession_info=b'\\x01\\x02\\x03')>"
)
def test_hash(self):
info1 = x509.ProfessionInfo(
x509.NamingAuthority(None, None, None),
["spam"],
[x509.ObjectIdentifier("1.2.3.4")],
"eggs",
b"\x01\x02\x03",
)
info2 = x509.ProfessionInfo(
x509.NamingAuthority(None, None, None),
["spam"],
[x509.ObjectIdentifier("1.2.3.4")],
"eggs",
b"\x01\x02\x03",
)
info3 = x509.ProfessionInfo(
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
),
["spam"],
[x509.ObjectIdentifier("1.2.3.4")],
"eggs",
b"\x01\x02\x03",
)
info4 = x509.ProfessionInfo(
x509.NamingAuthority(None, None, None),
[],
[x509.ObjectIdentifier("1.2.3.4")],
"eggs",
b"\x01\x02\x03",
)
info5 = x509.ProfessionInfo(
x509.NamingAuthority(None, None, None),
[],
[],
"eggs",
b"\x01\x02\x03",
)
info6 = x509.ProfessionInfo(
x509.NamingAuthority(None, None, None),
[],
[],
None,
b"\x01\x02\x03",
)
info7 = x509.ProfessionInfo(
x509.NamingAuthority(None, None, None), [], [], None, None
)
info8 = x509.ProfessionInfo(
x509.NamingAuthority(None, None, None), [], None, None, None
)
info9 = x509.ProfessionInfo(None, [], None, None, None)
assert hash(info1) == hash(info2)
assert hash(info1) != hash(info3)
assert hash(info1) != hash(info4)
assert hash(info1) != hash(info5)
assert hash(info1) != hash(info6)
assert hash(info1) != hash(info7)
assert hash(info1) != hash(info8)
assert hash(info1) != hash(info9)
class TestAdmission:
def test_invalid_init(self):
with pytest.raises(TypeError):
x509.Admission(
42, # type:ignore[arg-type]
None,
[],
)
with pytest.raises(TypeError):
x509.Admission(
None,
42, # type:ignore[arg-type]
[],
)
with pytest.raises(TypeError):
x509.Admission(
None,
None,
42, # type:ignore[arg-type]
)
with pytest.raises(TypeError):
x509.Admission(
None,
None,
[42], # type:ignore[list-item]
)
def test_eq(self):
admission1 = x509.Admission(None, None, [])
admission2 = x509.Admission(None, None, [])
assert admission1 == admission2
admission1 = x509.Admission(
x509.OtherName(
type_id=x509.oid.NameOID.COUNTRY_NAME,
value=b"\x04\x04\x13\x02DE",
),
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
),
[
x509.ProfessionInfo(
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3.4"),
"https://example.org",
"eggs",
),
["bacon"],
[x509.ObjectIdentifier("1.2.3.4.5")],
"sausage",
b"\x01\x02\x03",
)
],
)
admission2 = x509.Admission(
x509.OtherName(
type_id=x509.oid.NameOID.COUNTRY_NAME,
value=b"\x04\x04\x13\x02DE",
),
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
),
[
x509.ProfessionInfo(
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3.4"),
"https://example.org",
"eggs",
),
["bacon"],
[x509.ObjectIdentifier("1.2.3.4.5")],
"sausage",
b"\x01\x02\x03",
)
],
)
assert admission1 == admission2
def test_ne(self):
admission1 = x509.Admission(
x509.OtherName(
type_id=x509.oid.NameOID.COUNTRY_NAME,
value=b"\x04\x04\x13\x02DE",
),
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
),
[
x509.ProfessionInfo(
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3.4"),
"https://example.org",
"eggs",
),
["bacon"],
[x509.ObjectIdentifier("1.2.3.4.5")],
"sausage",
b"\x01\x02\x03",
)
],
)
admission2 = x509.Admission(
x509.OtherName(
type_id=x509.oid.NameOID.COUNTRY_NAME,
value=b"\x04\x04\x13\x02DE",
),
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
),
[],
)
admission3 = x509.Admission(
x509.OtherName(
type_id=x509.oid.NameOID.COUNTRY_NAME,
value=b"\x04\x04\x13\x02DE",
),
None,
[
x509.ProfessionInfo(
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3.4"),
"https://example.org",
"eggs",
),
["bacon"],
[x509.ObjectIdentifier("1.2.3.4.5")],
"sausage",
b"\x01\x02\x03",
)
],
)
admission4 = x509.Admission(
None,
None,
[
x509.ProfessionInfo(
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3.4"),
"https://example.org",
"eggs",
),
["bacon"],
[x509.ObjectIdentifier("1.2.3.4.5")],
"sausage",
b"\x01\x02\x03",
)
],
)
admission5 = x509.Admission(
x509.OtherName(
type_id=x509.oid.NameOID.COUNTRY_NAME,
value=b"\x04\x04\x13\x02DE",
),
None,
[],
)
admission6 = x509.Admission(
None,
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
),
[],
)
admission7 = x509.Admission(None, None, [])
assert admission1 != admission2
assert admission1 != admission3
assert admission1 != admission4
assert admission1 != admission5
assert admission1 != admission6
assert admission1 != admission7
assert admission1 != object()
def test_repr(self):
admission = x509.Admission(None, None, [])
assert repr(admission) == (
"<Admission("
"admission_authority=None, "
"naming_authority=None, "
"profession_infos=[])>"
)
admission = x509.Admission(
x509.OtherName(
type_id=x509.oid.NameOID.COUNTRY_NAME,
value=b"\x04\x04\x13\x02DE",
),
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
),
[
x509.ProfessionInfo(
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3.4"),
"https://example.org",
"eggs",
),
["bacon"],
[x509.ObjectIdentifier("1.2.3.4.5")],
"sausage",
b"\x01\x02\x03",
)
],
)
assert repr(admission) == (
"<Admission("
"admission_authority=<OtherName("
"type_id=<ObjectIdentifier("
"oid=2.5.4.6, name=countryName)>, "
"value=b'\\x04\\x04\\x13\\x02DE')>, "
"naming_authority=<NamingAuthority("
"id=<ObjectIdentifier(oid=1.2.3, name=Unknown OID)>, "
"url=https://example.com, text=spam)>, "
"profession_infos=[<ProfessionInfo("
"naming_authority=<NamingAuthority("
"id=<ObjectIdentifier(oid=1.2.3.4, name=Unknown OID)>, "
"url=https://example.org, text=eggs)>, "
"profession_items=['bacon'], "
"profession_oids=[<ObjectIdentifier("
"oid=1.2.3.4.5, name=Unknown OID)>], "
"registration_number=sausage, "
"add_profession_info=b'\\x01\\x02\\x03')>])>"
)
def test_hash(self):
admission1 = x509.Admission(
x509.OtherName(
type_id=x509.oid.NameOID.COUNTRY_NAME,
value=b"\x04\x04\x13\x02DE",
),
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
),
[
x509.ProfessionInfo(
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3.4"),
"https://example.org",
"eggs",
),
["bacon"],
[x509.ObjectIdentifier("1.2.3.4.5")],
"sausage",
b"\x01\x02\x03",
)
],
)
admission2 = x509.Admission(
x509.OtherName(
type_id=x509.oid.NameOID.COUNTRY_NAME,
value=b"\x04\x04\x13\x02DE",
),
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
),
[
x509.ProfessionInfo(
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3.4"),
"https://example.org",
"eggs",
),
["bacon"],
[x509.ObjectIdentifier("1.2.3.4.5")],
"sausage",
b"\x01\x02\x03",
)
],
)
admission3 = x509.Admission(
x509.UniformResourceIdentifier(value="https://www.example.de"),
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
),
[
x509.ProfessionInfo(
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3.4"),
"https://example.org",
"eggs",
),
["bacon"],
[x509.ObjectIdentifier("1.2.3.4.5")],
"sausage",
b"\x01\x02\x03",
)
],
)
admission4 = x509.Admission(
x509.OtherName(
type_id=x509.oid.NameOID.COUNTRY_NAME,
value=b"\x04\x04\x13\x02DE",
),
x509.NamingAuthority(None, None, None),
[
x509.ProfessionInfo(
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3.4"),
"https://example.org",
"eggs",
),
["bacon"],
[x509.ObjectIdentifier("1.2.3.4.5")],
"sausage",
b"\x01\x02\x03",
)
],
)
admission5 = x509.Admission(
x509.OtherName(
type_id=x509.oid.NameOID.COUNTRY_NAME,
value=b"\x04\x04\x13\x02DE",
),
x509.NamingAuthority(
x509.ObjectIdentifier("1.2.3"), "https://example.com", "spam"
),
[],
)
admission6 = x509.Admission(None, None, [])
assert hash(admission1) == hash(admission2)
assert hash(admission1) != hash(admission3)
assert hash(admission1) != hash(admission4)
assert hash(admission1) != hash(admission5)
assert hash(admission1) != hash(admission6)
class TestAdmissions:
def test_invalid_init(self):
with pytest.raises(TypeError):
x509.Admissions(
42, # type:ignore[arg-type]
[],
)
with pytest.raises(TypeError):
x509.Admissions(
None,
42, # type:ignore[arg-type]
)
with pytest.raises(TypeError):
x509.Admissions(
None,
[42], # type:ignore[list-item]
)
with pytest.raises(TypeError):
x509.Admissions(
None,
[None], # type:ignore[list-item]
)
def test_eq(self):
admissions1 = x509.Admissions(None, [])
admissions2 = x509.Admissions(None, [])
assert admissions1 == admissions2
admissions1 = x509.Admissions(
x509.UniformResourceIdentifier(value="https://www.example.de"),
[x509.Admission(None, None, [])],
)
admissions2 = x509.Admissions(
x509.UniformResourceIdentifier(value="https://www.example.de"),
[x509.Admission(None, None, [])],
)
assert admissions1 == admissions2
def test_ne(self):
admissions1 = x509.Admissions(
x509.UniformResourceIdentifier(value="https://www.example.de"),
[x509.Admission(None, None, [])],
)
admissions2 = x509.Admissions(
x509.UniformResourceIdentifier(value="https://www.example.de"), []
)
admissions3 = x509.Admissions(
None,
[x509.Admission(None, None, [])],
)
admissions4 = x509.Admissions(None, [])
assert admissions1 != admissions2
assert admissions1 != admissions3
assert admissions1 != admissions4
assert admissions1 != object()
def test_repr(self):
admissions = x509.Admissions(None, [])
assert repr(admissions) == (
"<Admissions(authority=None, admissions=[])>"
)
admissions = x509.Admissions(
x509.UniformResourceIdentifier(value="https://www.example.de"),
[x509.Admission(None, None, [])],
)
assert repr(admissions) == (
"<Admissions("
"authority=<UniformResourceIdentifier("
"value='https://www.example.de')>, "
"admissions=[<Admission("
"admission_authority=None, "
"naming_authority=None, "
"profession_infos=[])>])>"
)
def test_hash(self):
admissions1 = x509.Admissions(
x509.UniformResourceIdentifier(value="https://www.example.de"),
[x509.Admission(None, None, [])],
)
admissions2 = x509.Admissions(
x509.UniformResourceIdentifier(value="https://www.example.de"),
[x509.Admission(None, None, [])],
)
admissions3 = x509.Admissions(
x509.UniformResourceIdentifier(value="https://www.example.de"), []
)
admissions4 = x509.Admissions(
None,
[x509.Admission(None, None, [])],
)
admissions5 = x509.Admissions(None, [])
assert hash(admissions1) == hash(admissions2)
assert hash(admissions1) != hash(admissions3)
assert hash(admissions1) != hash(admissions4)
assert hash(admissions1) != hash(admissions5)
def test_public_bytes(self):
ext = x509.Admissions(None, [])
assert ext.public_bytes() == b"0\x020\x00"
ext = x509.Admissions(
x509.UniformResourceIdentifier(value="https://www.example.com/"),
[],
)
assert (
ext.public_bytes() == b"0\x1c\x86\x18https://www.example.com/0\x00"
)
# test for encoding none values
ext = x509.Admissions(
None,
[
x509.Admission(
None,
x509.NamingAuthority(None, None, None),
[x509.ProfessionInfo(None, [], [], None, None)],
),
x509.Admission(
None,
None,
[
x509.ProfessionInfo(
x509.NamingAuthority(None, None, None),
[],
[],
None,
None,
)
],
),
],
)
assert ext.public_bytes() == (
b"0\x1e0\x1c0\x0c\xa1\x020\x000\x060\x040\x000\x000\x0c0\n0\x08\xa0\x020\x000\x000\x00"
)
# example values taken from https://gemspec.gematik.de/downloads/gemSpec/gemSpec_OID/gemSpec_OID_V3.17.0.pdf
ext = x509.Admissions(
authority=x509.DirectoryName(
value=x509.Name(
[
x509.NameAttribute(
x509.oid.NameOID.COUNTRY_NAME, "DE"
),
x509.NameAttribute(
x509.NameOID.ORGANIZATIONAL_UNIT_NAME,
"Elektronisches Gesundheitsberuferegister",
),
]
)
),
admissions=[
x509.Admission(
admission_authority=x509.DNSName("gematik.de"),
naming_authority=x509.NamingAuthority(
x509.ObjectIdentifier("1.2.276.0.76.3.1.91"),
"https://gematik.de/",
(
"Gesellschaft für Telematikanwendungen "
"der Gesundheitskarte mbH"
),
),
profession_infos=[
x509.ProfessionInfo(
naming_authority=x509.NamingAuthority(
x509.ObjectIdentifier("1.2.276.0.76.3.1.1"),
"https://www.kbv.de/",
"KBV Kassenärztliche Bundesvereinigung",
),
registration_number="123456789",
profession_items=[
"Ärztin/Arzt",
(
"Orthopädieschuhmacher/-in "
"und Orthopädietechniker/-in"
),
],
profession_oids=[
x509.ObjectIdentifier("1.2.276.0.76.4.30"),
x509.ObjectIdentifier("1.2.276.0.76.4.305"),
],
# DER-encoded:
# `OtherName(
# type_id=ObjectIdentifier('1.2.276.0.76.4.60'),
# value=b'\x0c\x1dProbe-Client Broker-Betreiber'
# )`
add_profession_info=(
b"\xa0*\x06\x07*\x82\x14\x00L\x04<\xa0\x1f"
b"\x0c\x1dProbe-Client Broker-Betreiber"
),
)
],
),
],
)
assert ext.public_bytes() == (
b"0\x82\x01\xa6\xa4B0@1\x0b0\t\x06\x03U\x04\x06\x13\x02DE110/\x06"
b"\x03U\x04\x0b\x0c(Elektronisches Gesundheitsberuferegister0\x82"
b"\x01^0\x82\x01Z\xa0\x0c\x82\ngematik.de\xa1b0`\x06\x08*\x82\x14"
b"\x00L\x03\x01[\x16\x13https://gematik.de/\x0c?Gesellschaft f\xc3"
b"\xbcr Telematikanwendungen der Gesundheitskarte mbH0\x81\xe50"
b"\x81\xe2\xa0I0G\x06\x08*\x82\x14\x00L\x03\x01\x01\x16\x13https://www."
b"kbv.de/\x0c&KBV Kassen\xc3\xa4rztliche Bundesvereinigung0G\x0c"
b"\x0c\xc3\x84rztin/Arzt\x0c7Orthop\xc3\xa4dieschuhmacher/-in und "
b"Orthop\xc3\xa4dietechniker/-in0\x13\x06\x07*\x82\x14\x00L\x04\x1e"
b"\x06\x08*\x82\x14\x00L\x04\x821\x13\t123456789\x04,\xa0*\x06"
b"\x07*\x82\x14\x00L\x04<\xa0\x1f\x0c\x1dProbe-Client Broker-"
b"Betreiber"
)
# test for non-ascii url value in naming authority
ext = x509.Admissions(
None,
[
x509.Admission(
None,
x509.NamingAuthority(None, "😄", None),
[],
),
],
)
with pytest.raises(ValueError):
ext.public_bytes()
# test for non-ascii registration number value in profession info
ext = x509.Admissions(
None,
[
x509.Admission(
None,
None,
[x509.ProfessionInfo(None, [], [], "\x00", None)],
),
],
)
with pytest.raises(ValueError):
ext.public_bytes()
# test that none passed for `profession_oids` is encoded as none
ext = x509.Admissions(
None,
[
x509.Admission(
None,
None,
[x509.ProfessionInfo(None, [], None, None, None)],
),
],
)
assert ext.public_bytes() == b"0\n0\x080\x060\x040\x020\x00"
def test_all_extension_oid_members_have_names_defined():
for oid in dir(ExtensionOID):
if oid.startswith("__"):
continue
assert getattr(ExtensionOID, oid) in _OID_NAMES
def test_unknown_extension():
class MyExtension(ExtensionType):
oid = x509.ObjectIdentifier("1.2.3.4")
with pytest.raises(NotImplementedError):
MyExtension().public_bytes()
with pytest.raises(NotImplementedError):
rust_x509.encode_extension_value(MyExtension())