Skip to content

Instantly share code, notes, and snippets.

@sebslomski
Created January 15, 2013 11:47
Show Gist options
  • Save sebslomski/4538088 to your computer and use it in GitHub Desktop.
Save sebslomski/4538088 to your computer and use it in GitHub Desktop.
# My backup script. Requires gmvault for gmail backup.
# config.json.sample:
# {
# "files": {
# "Work": [
# "~/Devel/Work/Foo-App",
# "~/Devel/Work/Foo-API"
# ],
# "Dropbox": [
# "~/Dropbox/public",
# "~/Dropbox/Camera Uploads"
# ]
# },
# "github": [
# "gaubert/gmvault"
# ]
# }
#
# Decrypt script:
# #!/usr/bin/env python
#
# import os
# import struct
# import hashlib
#
# from Crypto.Cipher import AES
#
#
# def decrypt_file(file_name):
# unhashed_key = raw_input('Enter key:')
# key = hashlib.sha256(unhashed_key).digest()
# out_filename = os.path.splitext(file_name)[0]
# chunksize = 64*1024
#
# with open(file_name, 'rb') as in_file:
# origsize = struct.unpack('<Q', in_file.read(struct.calcsize('Q')))[0]
# iv = in_file.read(16)
# decryptor = AES.new(key, AES.MODE_CBC, iv)
#
# with open(out_filename, 'wb') as out_file:
# while True:
# chunk = in_file.read(chunksize)
# if len(chunk) == 0:
# break
# out_file.write(decryptor.decrypt(chunk))
#
#
# if __name__ == '__main__':
# DIRNAME = os.path.normpath(os.path.dirname(__file__))
# ls = os.listdir(DIRNAME)
# file_name = filter(lambda x: x.endswith('.enc'), ls)[0]
# decrypt_file(file_name)
#!/usr/bin/env python
import os
import shutil
import subprocess
import json
import hashlib
import urllib
import random
import struct
from Crypto.Cipher import AES
from datetime import datetime
DIRNAME = os.path.normpath(os.path.dirname(__file__))
created_on = datetime.now().strftime('%d-%m-%Y')
BACKUP_DIR = os.path.join(DIRNAME, created_on)
BACKUP_ZIP = BACKUP_DIR + '.zip'
def encrypt_file(file_name):
unhashed_key = str(random.getrandbits(256))
key = hashlib.sha256(unhashed_key).digest()
mode = AES.MODE_CBC
iv = ''.join(chr(random.randint(0, 0xFF)) for i in range(16))
encryptor = AES.new(key, mode, iv)
file_size = os.path.getsize(file_name)
with open(file_name, 'rb') as in_file:
with open(file_name + '.enc', 'wb') as out_file:
out_file.write(struct.pack('<Q', file_size))
out_file.write(iv)
while True:
chunk = in_file.read(64*1024)
if len(chunk) == 0:
break
elif len(chunk) % 16 != 0:
chunk += ' ' * (16 - len(chunk) % 16)
out_file.write(encryptor.encrypt(chunk))
return unhashed_key
def main():
with open('config.json', 'rb') as f:
config = json.loads(f.read())
print 'Creating backup folder', created_on
os.mkdir(BACKUP_DIR)
try:
print 'Downloading Gmail mails'
pd = subprocess.Popen(
['gmvault', 'sync', config['gmail'],
'-p', '-d', os.path.join(BACKUP_DIR, 'gmvault-db')],
stdout=subprocess.PIPE,
stderr=subprocess.PIPE
)
stdout, stderr = pd.communicate()
if stderr:
print stderr
print 'Continue? (Y/N)'
answer = raw_input()
if answer not in ['Y', 'y']:
raise Exception(stderr)
print 'Copying files to backup folder'
for dest, folders in config['files'].items():
print 'Creating folder', created_on + '/' + dest
dest = os.path.join(BACKUP_DIR, dest)
os.makedirs(dest)
for src in folders:
src_name = os.path.split(src)[-1]
print '\tCopying folder', src_name
shutil.copytree(
os.path.expanduser(src),
os.path.join(dest, src_name)
)
if len(config['github']):
os.mkdir(os.path.join(BACKUP_DIR, 'github'))
for repo_name in config['github']:
print 'Copying github repo ', repo_name
url = 'https://github.com/%s/archive/master.zip' % repo_name
user_name, repo_name = repo_name.split('/')
dest = os.path.join(BACKUP_DIR, 'github', user_name)
if not os.path.exists(dest):
os.mkdir(dest)
web_file = urllib.urlopen(url)
with open(os.path.join(dest, repo_name + '.zip'), 'wb') as f:
f.write(web_file.read())
web_file.close()
print 'Creating zip file', created_on + '.zip'
pd = subprocess.Popen(
['/usr/bin/zip', '-r', BACKUP_ZIP, BACKUP_DIR],
stdout=subprocess.PIPE,
stderr=subprocess.PIPE
)
stdout, stderr = pd.communicate()
if stderr:
print stderr
print 'Continue? (Y/N)'
answer = raw_input()
if answer not in ['Y', 'y']:
raise Exception(stderr)
print stdout
print 'Encrypting zip file'
key = encrypt_file(BACKUP_ZIP)
print 'Encryption key'
print '*' * 80
print key
print '*' * 80
finally:
print 'Deleting backup folder', created_on
if os.path.exists(BACKUP_ZIP):
os.unlink(BACKUP_ZIP)
shutil.rmtree(BACKUP_DIR)
if __name__ == '__main__':
main()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment