Skip to content

Instantly share code, notes, and snippets.

@kalloc
Last active August 29, 2015 13:56
Show Gist options
  • Save kalloc/9226971 to your computer and use it in GitHub Desktop.
Save kalloc/9226971 to your computer and use it in GitHub Desktop.
from OpenSSL.crypto import (
X509Extension, PKey, X509
)
from OpenSSL.crypto import (
TYPE_RSA, FILETYPE_PEM
)
from OpenSSL.crypto import (
dump_privatekey, dump_certificate,
load_privatekey, load_certificate
)
from time import time
from socket import gethostname
from os.path import exists
import argparse
def set_common_names(cert, name):
cert.get_subject().C = "US"
cert.get_subject().ST = "Minnesota"
cert.get_subject().L = "Minnetonka"
cert.get_subject().O = "my company"
cert.get_subject().OU = "my organization"
cert.get_subject().CN = name
return cert
def create_server_cert(args, ca_cert, ca_key):
print '[I] generate new certificate for', args.hostname
# create a key pair
k = PKey()
k.generate_key(TYPE_RSA, 4096)
cert = X509()
cert.set_serial_number(int(time()))
cert.gmtime_adj_notBefore(0)
cert.gmtime_adj_notAfter(1 * 365 * 24 * 60 * 60)
cert.set_issuer(ca_cert.get_subject())
cert.set_pubkey(k)
set_common_names(cert, args.hostname)
ext = []
ext.append(X509Extension('basicConstraints', True, 'CA:FALSE'))
ext.append(X509Extension('nsCertType', True,
'server, email, objsign'))
ext.append(X509Extension('extendedKeyUsage', True, 'serverAuth'))
ext.append(X509Extension('subjectKeyIdentifier', False, 'hash', cert))
ext.append(X509Extension('authorityKeyIdentifier', False,
'keyid, issuer:always', issuer=ca_cert))
ext.append(X509Extension(
'keyUsage', True,
'nonRepudiation, digitalSignature, keyEncipherment'))
cert.add_extensions(ext)
cert.sign(ca_key, 'sha1')
open(args.cert, "w").write(
dump_certificate(FILETYPE_PEM, cert))
open(args.cert, "a").write(
dump_certificate(FILETYPE_PEM, ca_cert))
open(args.cert, "a").write(
dump_privatekey(FILETYPE_PEM, k))
return [cert, k]
def create_self_signed_cert(args):
if not exists(args.ca):
print '[W] unable to found exists CA'
print '[I] generate new CA certificate'
# create a key pair
k = PKey()
k.generate_key(TYPE_RSA, 4096)
# create a self-signed cert
cert = X509()
set_common_names(cert, gethostname())
cert.set_serial_number(1000)
cert.gmtime_adj_notBefore(0)
cert.gmtime_adj_notAfter(10 * 365 * 24 * 60 * 60)
cert.set_issuer(cert.get_subject())
cert.set_pubkey(k)
cert_extensions = (
('nsCertType', False, 'sslCA, emailCA'),
('basicConstraints', True, 'CA:TRUE'),
('subjectKeyIdentifier', False, 'hash', cert),
('keyUsage', True, 'keyCertSign,cRLSign')
)
ext = map(lambda e: X509Extension(*e), cert_extensions)
cert.add_extensions(ext)
cert.sign(k, 'sha1')
open(args.ca, "w").write(
dump_certificate(FILETYPE_PEM, cert))
if args.ca_cert:
open(args.ca_cert, "w").write(
dump_certificate(FILETYPE_PEM, cert))
open(args.ca, "a").write(
dump_privatekey(FILETYPE_PEM, k))
return [cert, k]
else:
print '[I] CA exists'
ca_cert = load_certificate(FILETYPE_PEM, open(args.ca).read())
ca_key = load_privatekey(FILETYPE_PEM, open(args.ca).read())
return [ca_cert, ca_key]
if __name__ == '__main__':
"""
python ssl_for_web.py --ca ca.pem --ca-cert ca.crt --cert cert.pem --hostname *.ssl.ru
[W] I can't found an existing CA
[I] generate the new CA certificate
[I] generate the new certificate for *.ssl.ru
[I] done
openssl verify -verbose -CAfile ca.pem -purpose sslserver cert.pem
cert.pem: OK
"""
parser = argparse.ArgumentParser(
description='Create SSL certificate for the web server')
parser.add_argument('--ca', required=True, help='path to the CA pem')
parser.add_argument('--ca-cert', required=False, help='path to the CA cert pem')
parser.add_argument('--cert', required=True, help='path to a webserver pem')
parser.add_argument('--hostname', required=True, help='a host name')
args = parser.parse_args()
create_server_cert(args, *create_self_signed_cert(args))
print '[I] done'
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment