From 9701cb92196679f07c4f94432eff33a574d747df Mon Sep 17 00:00:00 2001 From: Daniel Huisman Date: Tue, 22 May 2018 02:56:26 +0200 Subject: [PATCH 1/2] Start implementing ACME v2 support --- extractor.py | 17 ++++++++++------- 1 file changed, 10 insertions(+), 7 deletions(-) diff --git a/extractor.py b/extractor.py index 3779633..fb89899 100644 --- a/extractor.py +++ b/extractor.py @@ -21,19 +21,22 @@ class Handler(FileSystemEventHandler): # Read JSON file data = json.loads(open(event.src_path).read()) - certs = data['DomainsCertificate']['Certs'] + is_v2 = 'acme-v02' in data['Account']['Registration']['uri'] + certs = data['Certificates'] if is_v2 else data['DomainsCertificate']['Certs'] # Loop over all certificates for c in certs: + name = c['Domain']['Main'] if is_v2 else c['Certificate']['Domain'] + # Decode private key, certificate and chain - privatekey = b64decode(c['Certificate']['PrivateKey']).decode('utf-8') - fullchain = b64decode(c['Certificate']['Certificate']).decode('utf-8') + privatekey = b64decode(c['Key'] if is_v2 else c['Certificate']['PrivateKey']).decode('utf-8') + fullchain = b64decode(c['Certificate'] if is_v2 else c['Certificate']['Certificate']).decode('utf-8') start = fullchain.find('-----BEGIN CERTIFICATE-----', 1) cert = fullchain[0:start] chain = fullchain[start:] # Create domain directory if it doesn't exist - directory = 'certs/' + c['Certificate']['Domain'] + '/' + directory = 'certs/' + name + '/' try: os.makedirs(directory) except OSError as error: @@ -56,11 +59,11 @@ class Handler(FileSystemEventHandler): # Write private key, certificate and chain to flat files directory = 'certs_flat/' - with open(directory + c['Certificate']['Domain'] + '.key', 'w') as f: + with open(directory + name + '.key', 'w') as f: f.write(privatekey) - with open(directory + c['Certificate']['Domain'] + '.crt', 'w') as f: + with open(directory + name + '.crt', 'w') as f: f.write(fullchain) - with open(directory + c['Certificate']['Domain'] + '.chain.pem', 'w') as f: + with open(directory + name + '.chain.pem', 'w') as f: f.write(chain) if c['Domains']['SANs']: From 7842e09181c4038d3448e842369a2dd56990d6c0 Mon Sep 17 00:00:00 2001 From: Daniel Huisman Date: Wed, 6 Jun 2018 12:56:08 +0200 Subject: [PATCH 2/2] Improve the code I wrote when hungover, thanks to #7, closes #6 --- extractor.py | 32 ++++++++++++++++++++++++-------- 1 file changed, 24 insertions(+), 8 deletions(-) diff --git a/extractor.py b/extractor.py index fb89899..0b69194 100644 --- a/extractor.py +++ b/extractor.py @@ -21,16 +21,32 @@ class Handler(FileSystemEventHandler): # Read JSON file data = json.loads(open(event.src_path).read()) - is_v2 = 'acme-v02' in data['Account']['Registration']['uri'] - certs = data['Certificates'] if is_v2 else data['DomainsCertificate']['Certs'] + + # Determine ACME version + acme_version = 2 if 'acme-v02' in data['Account']['Registration']['uri'] else 1 + + # Find certificates + if acme_version == 1: + certs = data['DomainsCertificate']['Certs'] + elif acme_version == 2: + certs = data['Certificates'] # Loop over all certificates for c in certs: - name = c['Domain']['Main'] if is_v2 else c['Certificate']['Domain'] + if acme_version == 1: + name = c['Certificate']['Domain'] + privatekey = c['Certificate']['PrivateKey'] + fullchain = c['Certificate']['Certificate'] + sans = c['Domains']['SANs'] + elif acme_version == 2: + name = c['Domain']['Main'] + privatekey = c['Key'] + fullchain = c['Certificate'] + sans = c['Domains']['SANs'] # Decode private key, certificate and chain - privatekey = b64decode(c['Key'] if is_v2 else c['Certificate']['PrivateKey']).decode('utf-8') - fullchain = b64decode(c['Certificate'] if is_v2 else c['Certificate']['Certificate']).decode('utf-8') + privatekey = b64decode(privatekey).decode('utf-8') + fullchain = b64decode(fullchain).decode('utf-8') start = fullchain.find('-----BEGIN CERTIFICATE-----', 1) cert = fullchain[0:start] chain = fullchain[start:] @@ -66,8 +82,8 @@ class Handler(FileSystemEventHandler): with open(directory + name + '.chain.pem', 'w') as f: f.write(chain) - if c['Domains']['SANs']: - for name in c['Domains']['SANs']: + if sans: + for name in sans: with open(directory + name + '.key', 'w') as f: f.write(privatekey) with open(directory + name + '.crt', 'w') as f: @@ -75,7 +91,7 @@ class Handler(FileSystemEventHandler): with open(directory + name + '.chain.pem', 'w') as f: f.write(chain) - print('Extracted certificate for: ' + c['Domains']['Main'] + (', ' + ', '.join(c['Domains']['SANs']) if c['Domains']['SANs'] else '')) + print('Extracted certificate for: ' + name + (', ' + ', '.join(sans) if sans else '')) if __name__ == "__main__": # Determine path to watch