Add configuration option into Fabric deployment.

This commit is contained in:
Dorian 2014-01-15 18:30:10 -05:00
parent 719a3c1e46
commit 596e05b05b
1 changed files with 107 additions and 27 deletions

134
vagrant/fabfile.py vendored
View File

@ -1,13 +1,30 @@
from fabric.context_managers import env, lcd, cd, prefix
from fabric.operations import local, run, put
# TODO Turn into configurable setup.
DEPLOYABLE_PKG = 'rookeries-deployable.tar.bz2'
VIRTUALENV = 'rookeries'
TARGET_FOLDER = '/var/www'
WEBAPP_PERM_GROUP = 'www-data'
UWSGI_LOG = '/tmp/rookeries-uwsgi.log'
UWSGI_SOCKET = ':8001'
# Default values used by the Vagrant setup.
DEFAULT_VIRTUALENV = 'rookeries'
DEFAULT_DEST_DIR = '/var/www'
DEFAULT_WEBAPP_GROUP_PERMISSIONS = 'www-data'
DEFAULT_UWSGI_LOG = '/tmp/rookeries-uwsgi.log'
DEFAULT_UWSGI_SOCKET = ':8001'
VAGRANT_SYS_NAME = 'vagrant'
# This is a sample configuration that can be used for deployments.
VAGRANT_CONFIG = {
'system_name': VAGRANT_SYS_NAME,
'virtualenv': DEFAULT_VIRTUALENV,
'dest': DEFAULT_DEST_DIR,
'permissions': {
'group': DEFAULT_WEBAPP_GROUP_PERMISSIONS,
},
'uwsgi': {
'log': DEFAULT_UWSGI_LOG,
'socket': DEFAULT_UWSGI_SOCKET,
},
}
def vagrant():
@ -28,31 +45,94 @@ def prepare_pkg():
local('tar jchf {pkg} rookeries requirements*'.format(pkg=DEPLOYABLE_PKG))
def deploy(recreate_virtual_env=False):
"""Deploy a ready-built package for deployment."""
# TODO Break out into separate tasks.
put(local_path='../{pkg}'.format(pkg=DEPLOYABLE_PKG), remote_path=TARGET_FOLDER)
put(local_path='requirements-vagrant.txt', remote_path=TARGET_FOLDER)
def deploy(recreate_virtual_env=False, config=VAGRANT_CONFIG):
"""
Deploy a ready-built package for deployment.
:param recreate_virtual_env: Flag determining whether to recreate the virtualenv on the remote system.
:param config: The configuration used as part of the deployment.
"""
upload_pkg(config=config)
if recreate_virtual_env:
with prefix('source virtualenvwrapper.sh'):
available_envs = run('lsvirtualenv -b', warn_only=True)
if not available_envs and VIRTUALENV in available_envs.split():
run('rmvirtualenv {env}'.format(env=VIRTUALENV))
create_remote_virtualenv(virtual_env=config['virtualenv'])
extract_pkg(config=config)
install_requirements(config=config)
if 'uwsgi' in config:
start_uwsgi(config=config)
if 'touch_file' in config:
touch_file_to_restart(config=config)
run('mkvirtualenv {env}'.format(env=VIRTUALENV))
def upload_pkg(config=VAGRANT_CONFIG):
"""
Upload the deployable package.
:param config: The configuration used as part of the deployment.
"""
put(local_path='../{pkg}'.format(pkg=DEPLOYABLE_PKG), remote_path=config['dest'])
extra_requirements = 'requirements-{system}.txt'.format(system=config['system_name'])
put(local_path=extra_requirements, remote_path=config['dest'])
def create_remote_virtualenv(virtual_env=DEFAULT_VIRTUALENV):
with prefix('source virtualenvwrapper.sh'):
with cd(TARGET_FOLDER):
run('tar jxf {pkg}'.format(pkg=DEPLOYABLE_PKG))
run('chgrp {env} rookeries'.format(env=WEBAPP_PERM_GROUP))
available_envs = run('lsvirtualenv -b', warn_only=True)
if not available_envs and virtual_env in available_envs.split():
run('rmvirtualenv {venv}'.format(venv=virtual_env))
with cd(TARGET_FOLDER):
with prefix('workon {env}'.format(env=VIRTUALENV)):
run('mkvirtualenv {venv}'.format(venv=virtual_env))
def extract_pkg(config=VAGRANT_CONFIG):
"""
Extract the uploaded deployable package.
:param config: The configuration used as part of the deployment.
"""
with cd(config['dest']):
run('tar jxf {pkg}'.format(pkg=DEPLOYABLE_PKG))
group_permissions = config['permissions']['group']
run('chgrp {group} rookeries'.format(group=group_permissions))
run('chgrp -R {group} *'.format(group=group_permissions))
run('chmod -R ug+rwx *')
def install_requirements(config=VAGRANT_CONFIG):
"""
Install the necessary package requirements.
:param config: The configuration used as part of the deployment.
"""
with prefix('source virtualenvwrapper.sh'):
with cd(config['dest']):
virtual_env = config['virtualenv']
with prefix('workon {venv}'.format(venv=virtual_env)):
run('pip install -r requirements.txt')
run('pip install -r requirements-vagrant.txt') # TODO Find better way of distributing sys requirements.
run('chgrp -R {group} *'.format(group=WEBAPP_PERM_GROUP))
run('chmod -R ug+rwx *')
run('uwsgi --socket {socket} -w rookeries:app --daemonize {log} --master'.format(socket=UWSGI_SOCKET,
log=UWSGI_LOG))
run('pip install -r requirements-{system}.txt'.format(system=config['system_name']))
def start_uwsgi(config=VAGRANT_CONFIG):
"""
Extract the uploaded deployable package.
:param config: The configuration used as part of the deployment.
"""
with prefix('source virtualenvwrapper.sh'):
with cd(config['dest']):
virtual_env = config['virtualenv']
uwsgi_socket = config['uwsgi']['socket']
uwsgi_log = config['uwsgi']['log']
with prefix('workon {venv}'.format(venv=virtual_env)):
run('uwsgi --socket {socket} -w rookeries:app --daemonize {log} --master'.format(socket=uwsgi_socket,
log=uwsgi_log))
def touch_file_to_restart(config=VAGRANT_CONFIG):
"""
Touch a specific file as part of the deployment. Usually used in conjuction to working with Passenger WSGI.
:param config: The configuration used as part of the deployment.
"""
with cd(config['dest']):
touch_file = config['touch_file']
run('touch {file}'.format(file=touch_file))