2013-10-16 16:26:39 -04:00
|
|
|
#!/usr/bin/env python
|
|
|
|
|
|
|
|
'''Deploy docker-ci report container on Digital Ocean.
|
|
|
|
Usage:
|
|
|
|
export CONFIG_JSON='
|
|
|
|
{ "DROPLET_NAME": "Digital_Ocean_dropplet_name",
|
|
|
|
"DO_CLIENT_ID": "Digital_Ocean_client_id",
|
|
|
|
"DO_API_KEY": "Digital_Ocean_api_key",
|
|
|
|
"DOCKER_KEY_ID": "Digital_Ocean_ssh_key_id",
|
|
|
|
"DOCKER_CI_KEY_PATH": "docker-ci_private_key_path",
|
|
|
|
"DOCKER_CI_PUB": "$(cat docker-ci_ssh_public_key.pub)",
|
|
|
|
"DOCKER_CI_ADDRESS" "user@docker-ci_fqdn_server",
|
|
|
|
"SMTP_USER": "SMTP_server_user",
|
|
|
|
"SMTP_PWD": "SMTP_server_password",
|
|
|
|
"EMAIL_SENDER": "Buildbot_mailing_sender",
|
|
|
|
"EMAIL_RCP": "Buildbot_mailing_receipient" }'
|
|
|
|
python deployment.py
|
|
|
|
'''
|
|
|
|
|
|
|
|
import re, json, requests, base64
|
|
|
|
from fabric import api
|
|
|
|
from fabric.api import cd, run, put, sudo
|
|
|
|
from os import environ as env
|
|
|
|
from time import sleep
|
|
|
|
from datetime import datetime
|
|
|
|
|
|
|
|
# Populate environment variables
|
|
|
|
CONFIG = json.loads(env['CONFIG_JSON'])
|
|
|
|
for key in CONFIG:
|
|
|
|
env[key] = CONFIG[key]
|
|
|
|
|
|
|
|
# Load DOCKER_CI_KEY
|
|
|
|
env['DOCKER_CI_KEY'] = open(env['DOCKER_CI_KEY_PATH']).read()
|
|
|
|
|
|
|
|
DROPLET_NAME = env.get('DROPLET_NAME','report')
|
|
|
|
TIMEOUT = 120 # Seconds before timeout droplet creation
|
2013-11-06 23:05:26 -05:00
|
|
|
IMAGE_ID = 1004145 # Docker on Ubuntu 13.04
|
2013-10-16 16:26:39 -04:00
|
|
|
REGION_ID = 4 # New York 2
|
|
|
|
SIZE_ID = 66 # memory 512MB
|
|
|
|
DO_IMAGE_USER = 'root' # Image user on Digital Ocean
|
|
|
|
API_URL = 'https://api.digitalocean.com/'
|
|
|
|
|
|
|
|
|
|
|
|
class digital_ocean():
|
|
|
|
|
|
|
|
def __init__(self, key, client):
|
|
|
|
'''Set default API parameters'''
|
|
|
|
self.key = key
|
|
|
|
self.client = client
|
|
|
|
self.api_url = API_URL
|
|
|
|
|
|
|
|
def api(self, cmd_path, api_arg={}):
|
|
|
|
'''Make api call'''
|
|
|
|
api_arg.update({'api_key':self.key, 'client_id':self.client})
|
|
|
|
resp = requests.get(self.api_url + cmd_path, params=api_arg).text
|
|
|
|
resp = json.loads(resp)
|
|
|
|
if resp['status'] != 'OK':
|
|
|
|
raise Exception(resp['error_message'])
|
|
|
|
return resp
|
|
|
|
|
|
|
|
def droplet_data(self, name):
|
|
|
|
'''Get droplet data'''
|
|
|
|
data = self.api('droplets')
|
|
|
|
data = [droplet for droplet in data['droplets']
|
|
|
|
if droplet['name'] == name]
|
|
|
|
return data[0] if data else {}
|
|
|
|
|
|
|
|
def json_fmt(data):
|
|
|
|
'''Format json output'''
|
|
|
|
return json.dumps(data, sort_keys = True, indent = 2)
|
|
|
|
|
|
|
|
|
|
|
|
do = digital_ocean(env['DO_API_KEY'], env['DO_CLIENT_ID'])
|
|
|
|
|
|
|
|
# Get DROPLET_NAME data
|
|
|
|
data = do.droplet_data(DROPLET_NAME)
|
|
|
|
|
|
|
|
# Stop processing if DROPLET_NAME exists on Digital Ocean
|
|
|
|
if data:
|
|
|
|
print ('Droplet: {} already deployed. Not further processing.'
|
|
|
|
.format(DROPLET_NAME))
|
|
|
|
exit(1)
|
|
|
|
|
|
|
|
# Create droplet
|
|
|
|
do.api('droplets/new', {'name':DROPLET_NAME, 'region_id':REGION_ID,
|
|
|
|
'image_id':IMAGE_ID, 'size_id':SIZE_ID,
|
|
|
|
'ssh_key_ids':[env['DOCKER_KEY_ID']]})
|
|
|
|
|
|
|
|
# Wait for droplet to be created.
|
|
|
|
start_time = datetime.now()
|
|
|
|
while (data.get('status','') != 'active' and (
|
|
|
|
datetime.now()-start_time).seconds < TIMEOUT):
|
|
|
|
data = do.droplet_data(DROPLET_NAME)
|
|
|
|
print data['status']
|
|
|
|
sleep(3)
|
|
|
|
|
|
|
|
# Wait for the machine to boot
|
|
|
|
sleep(15)
|
|
|
|
|
|
|
|
# Get droplet IP
|
|
|
|
ip = str(data['ip_address'])
|
|
|
|
print 'droplet: {} ip: {}'.format(DROPLET_NAME, ip)
|
|
|
|
|
|
|
|
api.env.host_string = ip
|
|
|
|
api.env.user = DO_IMAGE_USER
|
|
|
|
api.env.key_filename = env['DOCKER_CI_KEY_PATH']
|
|
|
|
|
|
|
|
# Correct timezone
|
|
|
|
sudo('echo "America/Los_Angeles" >/etc/timezone')
|
|
|
|
sudo('dpkg-reconfigure --frontend noninteractive tzdata')
|
|
|
|
|
|
|
|
# Load JSON_CONFIG environment for Dockerfile
|
|
|
|
CONFIG_JSON= base64.b64encode(
|
|
|
|
'{{"DOCKER_CI_PUB": "{DOCKER_CI_PUB}",'
|
|
|
|
' "DOCKER_CI_KEY": "{DOCKER_CI_KEY}",'
|
|
|
|
' "DOCKER_CI_ADDRESS": "{DOCKER_CI_ADDRESS}",'
|
|
|
|
' "SMTP_USER": "{SMTP_USER}",'
|
|
|
|
' "SMTP_PWD": "{SMTP_PWD}",'
|
|
|
|
' "EMAIL_SENDER": "{EMAIL_SENDER}",'
|
|
|
|
' "EMAIL_RCP": "{EMAIL_RCP}"}}'.format(**env))
|
|
|
|
|
|
|
|
run('mkdir -p /data/report')
|
|
|
|
put('./', '/data/report')
|
|
|
|
with cd('/data/report'):
|
|
|
|
run('chmod 700 report.py')
|
|
|
|
run('echo "{}" > credentials.json'.format(CONFIG_JSON))
|
|
|
|
run('docker build -t report .')
|
|
|
|
run('rm credentials.json')
|
|
|
|
run("echo -e '30 09 * * * /usr/bin/docker run report\n' |"
|
|
|
|
" /usr/bin/crontab -")
|