from cryptography import x509
from cryptography.hazmat.backends import default_backend
from cryptography.hazmat.primitives import hashes
from cryptography.hazmat.primitives.asymmetric import ec
from cryptography.x509.oid import NameOID
import datetime
8.4 OPENSSL TO PYTHON AND BACK
EXERCISE 8.4: OPENSSL TO PYTHON AND BACK
Generate a CSR with Python and sign it with Openssl.
Generate a CSR with Openssl, open it in Python, and create a self-signed certificate from it.
Let’s first create a root-certificate for yilkalandnoah.com
. Then we will use this root certificate to perform the operations listed inside of the question.
= datetime.timedelta(days=365)
one_year = datetime.timedelta(days=1) one_day
from cryptography.hazmat.primitives.serialization import Encoding,PrivateFormat, NoEncryption
= ec.generate_private_key(
private_key =ec.SECP256K1(),
curve=default_backend(),
backend )
= private_key.private_bytes(
private_bytes
Encoding.PEM, format=PrivateFormat.TraditionalOpenSSL,
=NoEncryption(),
encryption_algorithm
)
with open('data53_private_key.pem', 'wb') as f:
f.write(private_bytes)
print(private_bytes.decode())
-----BEGIN EC PRIVATE KEY-----
MHQCAQEEIJIvqQRCLySfM8W7RDyQB/QQnZsd85FtuGU3dtzqu727oAcGBSuBBAAK
oUQDQgAEyfWWuYkPirJb7yiTd0K5mDWpYKKfwnar71oeFUcphMWHk2/DxpyTVNZL
t9gOn54P7Ht8zqK7NuTDV26NI9lkHg==
-----END EC PRIVATE KEY-----
from cryptography.hazmat.primitives.serialization import PublicFormat
= private_key.public_key()
public_key = public_key.public_bytes(Encoding.PEM, PublicFormat.SubjectPublicKeyInfo)
public_bytes
with open('data53_public_key.pem', 'wb') as f:
f.write(public_bytes)
print(public_bytes.decode())
-----BEGIN PUBLIC KEY-----
MFYwEAYHKoZIzj0CAQYFK4EEAAoDQgAEyfWWuYkPirJb7yiTd0K5mDWpYKKfwnar
71oeFUcphMWHk2/DxpyTVNZLt9gOn54P7Ht8zqK7NuTDV26NI9lkHg==
-----END PUBLIC KEY-----
= x509.CertificateBuilder(
certificate =x509.Name([x509.NameAttribute(NameOID.COMMON_NAME, 'yilkalandnoah.com')]),
subject_name=x509.Name([x509.NameAttribute(NameOID.COMMON_NAME, 'yilkalandnoah.com')]),
issuer_name=datetime.datetime.today() - one_day,
not_valid_before=datetime.datetime.today() + (one_year * 30),
not_valid_after=x509.random_serial_number(),
serial_number=public_key,
public_key
).sign(=private_key,
private_key=hashes.SHA256(),
algorithm=default_backend(),
backend )
= certificate.public_bytes(Encoding.PEM)
certificate_bytes
with open('data53_root_cert.crt', 'wb') as f:
f.write(certificate_bytes)
print(certificate_bytes.decode())
-----BEGIN CERTIFICATE-----
MIIBNTCB3aADAgECAhQUJTEt0N0BcNzd6W9KKOVr8YRLYTAKBggqhkjOPQQDAjAc
MRowGAYDVQQDDBF5aWxrYWxhbmRub2FoLmNvbTAgFw0yNDEwMjgwNzI5MjhaGA8y
MDU0MTAyMjA3MjkyOFowHDEaMBgGA1UEAwwReWlsa2FsYW5kbm9haC5jb20wVjAQ
BgcqhkjOPQIBBgUrgQQACgNCAATJ9Za5iQ+KslvvKJN3QrmYNalgop/CdqvvWh4V
RymExYeTb8PGnJNU1ku32A6fng/se3zOors25MNXbo0j2WQeMAoGCCqGSM49BAMC
A0cAMEQCIA5IV1lzECrC+ypZXS0++YEtLkYdqLqKsEk5e4cLT1vTAiB0wVg5OI2/
4lYYxPa9KWQYOrCE6Gb0qhVPlXlv7932nw==
-----END CERTIFICATE-----
Running: openssl x509 -in data53_root_cert.crt -text
gives us:
Certificate:
Data:
Version: 3 (0x2)
Serial Number:
14:25:31:2d:d0:dd:01:70:dc:dd:e9:6f:4a:28:e5:6b:f1:84:4b:61
Signature Algorithm: ecdsa-with-SHA256
Issuer: CN = yilkalandnoah.com
Validity
Not Before: Oct 28 07:29:28 2024 GMT
Not After : Oct 22 07:29:28 2054 GMT
Subject: CN = yilkalandnoah.com
Subject Public Key Info:
Public Key Algorithm: id-ecPublicKey
Public-Key: (256 bit)
pub:
04:c9:f5:96:b9:89:0f:8a:b2:5b:ef:28:93:77:42:
b9:98:35:a9:60:a2:9f:c2:76:ab:ef:5a:1e:15:47:
29:84:c5:87:93:6f:c3:c6:9c:93:54:d6:4b:b7:d8:
0e:9f:9e:0f:ec:7b:7c:ce:a2:bb:36:e4:c3:57:6e:
8d:23:d9:64:1e
ASN1 OID: secp256k1
Signature Algorithm: ecdsa-with-SHA256
Signature Value:
30:44:02:20:0e:48:57:59:73:10:2a:c2:fb:2a:59:5d:2d:3e:
f9:81:2d:2e:46:1d:a8:ba:8a:b0:49:39:7b:87:0b:4f:5b:d3:
02:20:74:c1:58:39:38:8d:bf:e2:56:18:c4:f6:bd:29:64:18:
3a:b0:84:e8:66:f4:aa:15:4f:95:79:6f:ef:dd:f6:9f
-----BEGIN CERTIFICATE-----
MIIBNTCB3aADAgECAhQUJTEt0N0BcNzd6W9KKOVr8YRLYTAKBggqhkjOPQQDAjAc
MRowGAYDVQQDDBF5aWxrYWxhbmRub2FoLmNvbTAgFw0yNDEwMjgwNzI5MjhaGA8y
MDU0MTAyMjA3MjkyOFowHDEaMBgGA1UEAwwReWlsa2FsYW5kbm9haC5jb20wVjAQ
BgcqhkjOPQIBBgUrgQQACgNCAATJ9Za5iQ+KslvvKJN3QrmYNalgop/CdqvvWh4V
RymExYeTb8PGnJNU1ku32A6fng/se3zOors25MNXbo0j2WQeMAoGCCqGSM49BAMC
A0cAMEQCIA5IV1lzECrC+ypZXS0++YEtLkYdqLqKsEk5e4cLT1vTAiB0wVg5OI2/
4lYYxPa9KWQYOrCE6Gb0qhVPlXlv7932nw==
-----END CERTIFICATE-----
Part 1 of the question
Generate a CSR with Python and sign it with Openssl.
Step 1: Generate a CSR with Python
= x509.CertificateSigningRequestBuilder()
builder = builder.subject_name(
builder =x509.Name([
name'solar.yilkalandnoah.com'),
x509.NameAttribute(NameOID.COMMON_NAME,
])
)= builder.add_extension(
builder =False, path_length=None),
x509.BasicConstraints(ca=True,
critical )
= ec.generate_private_key(
private_key2 =ec.SECP256K1(),
curve=default_backend(),
backend )
= builder.sign(
csr =private_key2,
private_key=hashes.SHA256(),
algorithm=default_backend(),
backend )
with open('solar_yn.csr', 'wb') as f:
f.write(csr.public_bytes(Encoding.PEM))
Step 2: Sign the CSR with Openssl
I signed it with the following command:
openssl x509 -req\
-days 365\
-in solar_yn.csr\
-CAkey data53_private_key.pem\
-CA data53_root_cert.crt\
-out solar_yn.crt\
-set_serial 123456789\
-extfile v3.ext
Running the command: openssl x509 -in solar_yn.crt -text
, will give us the following output:
Certificate:
Data:
Version: 3 (0x2)
Serial Number: 123456789 (0x75bcd15)
Signature Algorithm: ecdsa-with-SHA256
Issuer: CN = yilkalandnoah.com
Validity
Not Before: Oct 29 05:56:21 2024 GMT
Not After : Oct 29 05:56:21 2025 GMT
Subject: CN = solar.yilkalandnoah.com
Subject Public Key Info:
Public Key Algorithm: id-ecPublicKey
Public-Key: (256 bit)
pub:
04:e5:8b:c1:37:34:ce:27:54:ba:db:27:a8:21:13:
6c:ee:70:e3:97:18:08:2e:f6:da:e7:e3:e2:34:6d:
eb:2d:32:11:05:db:db:b2:8b:00:85:12:66:e9:c7:
80:8c:06:d2:80:11:26:93:1d:19:e9:d8:55:74:38:
63:c8:cd:48:b9
ASN1 OID: secp256k1
X509v3 extensions:
X509v3 Key Usage:
Digital Signature
X509v3 Basic Constraints:
CA:FALSE
X509v3 Subject Key Identifier:
89:88:EF:B5:BE:95:86:04:97:A9:E7:74:6A:FD:64:52:37:F2:86:83
X509v3 Authority Key Identifier:
DirName:/CN=yilkalandnoah.com
serial:14:25:31:2D:D0:DD:01:70:DC:DD:E9:6F:4A:28:E5:6B:F1:84:4B:61
Signature Algorithm: ecdsa-with-SHA256
Signature Value:
30:45:02:21:00:96:2e:95:6e:5e:f8:2f:d1:e9:f1:75:f0:a2:
be:46:da:bb:c1:c6:ea:02:7d:5a:a2:e0:7a:25:56:e1:90:ef:
6a:02:20:23:12:49:32:66:0d:23:7e:4e:b6:02:c9:15:6e:e5:
d6:02:ef:48:61:2f:dd:3c:30:02:3b:55:8c:b7:d5:91:36
-----BEGIN CERTIFICATE-----
MIIBqTCCAU+gAwIBAgIEB1vNFTAKBggqhkjOPQQDAjAcMRowGAYDVQQDDBF5aWxr
YWxhbmRub2FoLmNvbTAeFw0yNDEwMjkwNTU2MjFaFw0yNTEwMjkwNTU2MjFaMCIx
IDAeBgNVBAMMF3NvbGFyLnlpbGthbGFuZG5vYWguY29tMFYwEAYHKoZIzj0CAQYF
K4EEAAoDQgAE5YvBNzTOJ1S62yeoIRNs7nDjlxgILvba5+PiNG3rLTIRBdvbsosA
hRJm6ceAjAbSgBEmkx0Z6dhVdDhjyM1IuaN8MHowCwYDVR0PBAQDAgeAMAkGA1Ud
EwQCMAAwHQYDVR0OBBYEFImI77W+lYYEl6nndGr9ZFI38oaDMEEGA1UdIwQ6MDih
IKQeMBwxGjAYBgNVBAMMEXlpbGthbGFuZG5vYWguY29tghQUJTEt0N0BcNzd6W9K
KOVr8YRLYTAKBggqhkjOPQQDAgNIADBFAiEAli6Vbl74L9Hp8XXwor5G2rvBxuoC
fVqi4HolVuGQ72oCICMSSTJmDSN+TrYCyRVu5dYC70hhL908MAI7VYy31ZE2
-----END CERTIFICATE-----
Part 2 of the question
Generate a CSR with Openssl, open it in Python, and create a self-signed certificate from it.
Step 1: Generate the CSR with openssl
I created the CSR by using the following script:
# file: create_csr_using_openssl.sh
# generate the key first
openssl genpkey -algorithm RSA -out research_key.pem -pkeyopt rsa_keygen_bits:2048
# create a csr from the key
openssl req -new -key research_key.pem -out research_yn.csr
Step 2: create a CSR object in python
with open('research_yn.csr', 'rb') as f:
= f.read()
csr_bytes
= x509.load_pem_x509_csr(csr_bytes, default_backend()) csr
Step 3: create a certificate from the CSR
= x509.CertificateBuilder(
research_cert_builder =csr.subject,
subject_name=certificate.subject,
issuer_name=datetime.datetime.today() - one_day,
not_valid_before=datetime.datetime.today() + (one_day * 30),
not_valid_after=1122,
serial_number=csr.public_key(),
public_key )
= research_cert_builder.add_extension(extval=x509.BasicConstraints(ca=False, path_length=None), critical=True)
research_cert_builder = research_cert_builder.sign(
research_cert =private_key,
private_key=hashes.SHA256(),
algorithm=default_backend(),
backend )
= research_cert.public_bytes(Encoding.PEM)
research_cert_bytes
with open('research_cert.crt', 'wb') as f:
f.write(research_cert_bytes)
Running the command: openssl x509 -in research_cert.crt -text
, will give us the following output:
Certificate:
Data:
Version: 3 (0x2)
Serial Number: 1122 (0x462)
Signature Algorithm: ecdsa-with-SHA256
Issuer: CN = yilkalandnoah.com
Validity
Not Before: Oct 28 09:23:15 2024 GMT
Not After : Nov 28 09:23:15 2024 GMT
Subject: C = ET, ST = Addis Ababa, O = Data53's Energy Company, CN = research.yilkalandnoah.com, emailAddress = research@yilkalandnoah.com
Subject Public Key Info:
Public Key Algorithm: rsaEncryption
Public-Key: (2048 bit)
Modulus:
00:a8:e0:1e:a3:63:0b:07:5a:a0:d1:78:e0:71:8c:
45:32:b5:4c:35:cb:55:ee:8c:31:51:a5:84:af:70:
f5:de:bf:d3:48:9f:0d:0f:91:09:1a:8e:a5:f5:53:
2e:05:ff:19:5f:62:08:2a:dd:50:8c:25:38:87:08:
ac:f0:b0:ba:74:34:cf:02:70:d4:b5:ae:24:c6:25:
db:3b:c8:a9:46:75:b6:61:2d:f2:b2:42:56:ab:d6:
82:28:d4:c1:14:8b:a0:bf:1e:ac:18:14:0a:14:4e:
1e:8b:6f:dd:ec:78:13:fd:6d:a4:7f:88:b0:7f:09:
95:99:1d:3a:fc:00:b7:d3:a3:56:6b:73:eb:e5:09:
85:06:10:ee:17:e6:3b:3e:a2:b0:3a:92:fb:67:0f:
02:cb:8d:17:73:36:35:6f:af:80:9d:71:57:b3:57:
f6:e2:e6:f8:60:aa:ae:28:9d:de:ae:dd:dc:76:c6:
17:e9:08:e3:b6:6e:97:f8:54:54:cc:e8:b4:8c:43:
69:8e:6f:0f:03:73:18:77:e1:11:f4:7f:13:01:22:
d7:d3:fe:b3:49:17:cc:58:e8:e0:21:ab:b0:52:01:
b6:79:53:67:5b:63:89:3f:b7:67:01:e1:a8:25:d4:
a7:20:69:71:df:7a:4f:56:30:e2:88:0a:19:f7:29:
da:7f
Exponent: 65537 (0x10001)
X509v3 extensions:
X509v3 Basic Constraints: critical
CA:FALSE
Signature Algorithm: ecdsa-with-SHA256
Signature Value:
30:44:02:20:48:3c:34:b9:76:d8:4d:d6:6e:34:4e:65:34:ab:
7d:9b:47:a7:29:b5:42:f6:f6:b3:91:cb:d2:b4:2e:60:f3:a3:
02:20:21:f6:c9:ef:e7:0d:26:21:ca:8b:3e:3f:55:aa:10:e6:
7b:4f:a1:fd:4a:17:30:85:a2:9e:a2:e8:5f:0e:c4:34
-----BEGIN CERTIFICATE-----
MIICfDCCAiOgAwIBAgICBGIwCgYIKoZIzj0EAwIwHDEaMBgGA1UEAwwReWlsa2Fs
YW5kbm9haC5jb20wHhcNMjQxMDI4MDkyMzE1WhcNMjQxMTI4MDkyMzE1WjCBlTEL
MAkGA1UEBhMCRVQxFDASBgNVBAgMC0FkZGlzIEFiYWJhMSAwHgYDVQQKDBdEYXRh
NTMncyBFbmVyZ3kgQ29tcGFueTEjMCEGA1UEAwwacmVzZWFyY2gueWlsa2FsYW5k
bm9haC5jb20xKTAnBgkqhkiG9w0BCQEWGnJlc2VhcmNoQHlpbGthbGFuZG5vYWgu
Y29tMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAqOAeo2MLB1qg0Xjg
cYxFMrVMNctV7owxUaWEr3D13r/TSJ8ND5EJGo6l9VMuBf8ZX2IIKt1QjCU4hwis
8LC6dDTPAnDUta4kxiXbO8ipRnW2YS3yskJWq9aCKNTBFIugvx6sGBQKFE4ei2/d
7HgT/W2kf4iwfwmVmR06/AC306NWa3Pr5QmFBhDuF+Y7PqKwOpL7Zw8Cy40XczY1
b6+AnXFXs1f24ub4YKquKJ3ert3cdsYX6Qjjtm6X+FRUzOi0jENpjm8PA3MYd+ER
9H8TASLX0/6zSRfMWOjgIauwUgG2eVNnW2OJP7dnAeGoJdSnIGlx33pPVjDiiAoZ
9ynafwIDAQABoxAwDjAMBgNVHRMBAf8EAjAAMAoGCCqGSM49BAMCA0cAMEQCIEg8
NLl22E3WbjROZTSrfZtHpym1Qvb2s5HL0rQuYPOjAiAh9snv5w0mIcqLPj9VqhDm
e0+h/UoXMIWinqLoXw7ENA==
-----END CERTIFICATE-----