我这样创建了一个类似CA的东西:
openssl genrsa -out ca.key 4096
openssl req -new -x509 -days 3650 -key ca.key -out ca.cert
这给了我两个PEM文件。
然后调用此函数,其中cert_authority
和private_key
是上面生成的数据字符串。
def create_cert(cert_authority, private_key):
one_day = datetime.timedelta(1, 0, 0)
# Use our private key to generate a public key
private_key = serialization.load_pem_private_key(
private_key.encode("ascii"), password=None, backend=default_backend()
)
public_key = private_key.public_key()
ca = x509.load_pem_x509_certificate(
cert_authority.encode("ascii"), default_backend()
)
builder = x509.CertificateBuilder()
builder = builder.subject_name(
x509.Name([x509.NameAttribute(NameOID.COMMON_NAME, u"cryptography.io")])
)
builder = builder.issuer_name(ca.issuer)
builder = builder.not_valid_before(datetime.datetime.today() - one_day)
builder = builder.not_valid_after(datetime.datetime.today() + (one_day * 30))
builder = builder.serial_number(x509.random_serial_number())
builder = builder.public_key(public_key)
cert = builder.sign(
private_key=private_key, algorithm=hashes.SHA256(), backend=default_backend()
)
print(cert.public_bytes(serialization.Encoding.PEM))
接着会生成一个看似证书的东西,不过当我将数据复制并粘贴到文件中(并且按照http://srdevspot.blogspot.com/2011/08/openssl-error0906d064pem.html的方法每64行进行一次换行符转换),在验证时出现了以下错误:
$ openssl verify -CAfile ca.crt -untrusted phone.crt
unable to load certificates
希望只是因为我还不熟悉这些内容而已,有简单的解决方法。
最后我想指出,如果cryptography不是最好的选择,我也愿意尝试使用另一个加密库。
编辑:
根据Paul非常有帮助的回复,我现在正在使用它。
def create_cert(cert_authority, private_key):
one_day = datetime.timedelta(1, 0, 0)
# Use our private key to generate a public key
root_key = serialization.load_pem_private_key(
private_key.encode("ascii"), password=None, backend=default_backend()
)
root_cert = x509.load_pem_x509_certificate(
cert_authority.encode("ascii"), default_backend()
)
# Now we want to generate a cert from that root
cert_key = rsa.generate_private_key(
public_exponent=65537, key_size=2048, backend=default_backend()
)
new_subject = x509.Name(
[
x509.NameAttribute(NameOID.COUNTRY_NAME, u"US"),
x509.NameAttribute(NameOID.STATE_OR_PROVINCE_NAME, u"Texas"),
x509.NameAttribute(NameOID.LOCALITY_NAME, u"Austin"),
x509.NameAttribute(NameOID.ORGANIZATION_NAME, u"New Org Name!"),
]
)
cert = (
x509.CertificateBuilder()
.subject_name(new_subject)
.issuer_name(root_cert.issuer)
.public_key(cert_key.public_key())
.serial_number(x509.random_serial_number())
.not_valid_before(datetime.datetime.utcnow())
.not_valid_after(datetime.datetime.utcnow() + datetime.timedelta(days=30))
.add_extension(
x509.SubjectAlternativeName([x509.DNSName(u"somedomain.com")]),
critical=False,
)
.sign(root_key, hashes.SHA256(), default_backend())
)
# Dump to scratch
with open("scratch/phone_cert.pem", "wb") as f:
f.write(cert.public_bytes(encoding=serialization.Encoding.PEM))
# Return PEM
cert_pem = cert.public_bytes(encoding=serialization.Encoding.PEM)
cert_key_pem = cert_key.private_bytes(
encoding=serialization.Encoding.PEM,
format=serialization.PrivateFormat.TraditionalOpenSSL,
encryption_algorithm=serialization.NoEncryption(),
)
return cert_pem, cert_key_pem
这样保存文件并返回创建的证书和私钥的PEM字符串是否正确?
我还发现当我尝试使用openssl verify -verbose -CAfile ca.crt -untrusted phone_cert.pem
命令验证已创建的证书时,该命令从未返回--可能是另一个问题,但我会感谢任何想法。