Ejemplo n.º 1
0
 def teardown(self):
     env.clear() # In case tests set env vars that didn't exist previously
     env.update(self.previous_env)
     output.update(self.previous_output)
     shutil.rmtree(self.tmpdir)
     # Clear Fudge mock expectations...again
     clear_expectations()
Ejemplo n.º 2
0
def deploy():
    for index, conf in enumerate(SERVER_CONFIGS):
        print("%d: %s" % (index + 1, conf["url"]))

    prompt("Which instance of the application would you like to deploy to?",
           key="instance_number")
    instance = int(env.instance_number) - 1
    env.update(SERVER_CONFIGS[instance])
    new_path = env.conda_env_path + "/bin:$PATH"
    with shell_env(
            PATH=new_path,
            CONDA_ENV_PATH=env.conda_env_path,
    ):
        with cd(env.directory):
            sudo("git pull origin master", user=env.user_running_chembiohub)
            sudo("git submodule foreach git pull origin master",
                 user=env.user_running_chembiohub)
            # sudo("conda install -y --file anaconda_requirements.txt" , user=env.user_running_chembiohub)
            sudo("pip install -r pip_requirements.txt",
                 user=env.user_running_chembiohub)
            sudo("python manage.py migrate", user=env.user_running_chembiohub)

        with cd(env.directory + "/src/ng-chem"):
            sudo("bower install", user=env.user_running_chembiohub)
        with cd(env.directory):
            sudo("python manage.py collectstatic --noinput",
                 user=env.user_running_chembiohub)
        with cd(env.directory):
            sudo("python manage.py log_all_users_out",
                 user=env.user_running_chembiohub)
        sudo("supervisorctl reload")
Ejemplo n.º 3
0
 def teardown(self):
     env.clear()  # In case tests set env vars that didn't exist previously
     env.update(self.previous_env)
     output.update(self.previous_output)
     shutil.rmtree(self.tmpdir)
     # Clear Fudge mock expectations...again
     clear_expectations()
Ejemplo n.º 4
0
 def setUp(self):
    # Set up default networking for test server
     # we don't actually use this, but if we don't do it, tests ask questions on the command line
     env.disable_known_hosts = True
     env.update(to_dict('%s@%s:%s' % (USER, HOST, PORT)))
     env.password = PASSWORDS[USER]
     env.use_shell = False
Ejemplo n.º 5
0
 def host_prompting_wrapper(*args, **kwargs):
     while not env.get('host_string', False):
         handle_prompt_abort("the target host connection string")
         host_string = raw_input("No hosts found. Please specify (single)"
                                 " host string for connection: ")
         env.update(to_dict(host_string))
     return func(*args, **kwargs)
Ejemplo n.º 6
0
 def env_setup(self):
     # Set up default networking for test server
     env.disable_known_hosts = True
     env.update(to_dict('%s@%s:%s' % (USER, HOST, PORT)))
     env.password = PASSWORDS[USER]
     # Command response mocking is easier without having to account for
     # shell wrapping everywhere.
     env.use_shell = False
Ejemplo n.º 7
0
 def env_setup(self):
     # Set up default networking for test server
     env.disable_known_hosts = True
     env.update(to_dict('%s@%s:%s' % (USER, HOST, PORT)))
     env.password = PASSWORDS[USER]
     # Command response mocking is easier without having to account for
     # shell wrapping everywhere.
     env.use_shell = False
Ejemplo n.º 8
0
 def setup(self):
     conf = self._service.config
     env.user = conf["user"]
     env.key_filename = conf["identity_file"]
     if "fabric" in conf:
         env.update(conf["fabric"])
     for name, func in load_fabfile(conf["fabfile"])[1].items():
         setattr(self, name, lambda *a, **kw: execute(func, hosts=self._service.hosts, *a, **kw))
Ejemplo n.º 9
0
def bind_hosts(fabric_root, select_env, parallel=False, machine_config=None):
    """
    bind hosts from file
    :param fabric_root:
    :param select_env:
    :param parallel:
    :param machine_config:
    :return:
    """

    machine_config = machine_config or os.path.join(fabric_root,
                                                    select_env + '.conf')

    if not os.path.exists(machine_config):
        raise OSError("%s not exist." % machine_config)

    if not os.access(machine_config, os.R_OK):
        raise OSError("access %s permission denied." % machine_config)

    inner_options = ['-P'] if parallel else []

    parser, options, arguments = parse_options(inner_options)

    # Handle regular args vs -- args
    arguments = parser.largs
    remainder_arguments = parser.rargs

    for option in env_options:
        env[option.dest] = getattr(options, option.dest)

    env.hosts, env.host_names = parse_hosts(machine_config)
    env.use_ssh_config = True
    env.roledefs[select_env] = env.hosts

    for key in ['hosts', 'roles', 'exclude_hosts']:
        if key in env and isinstance(env[key], basestring):
            env[key] = env[key].split(',')

    # Handle output control level show/hide
    update_output_levels(show=options.show, hide=options.hide)
    env.update(load_settings(env.rcfile))

    for v in env.hosts:
        flag_postion = v.find('@')

        if flag_postion > -1:
            host = v[flag_postion + 1:]
        else:
            host = v
            pass
        known_host(host, local_mode=True, clean=False)
        pass

    return machine_config
Ejemplo n.º 10
0
def update_env(*args, **kwargs):
    env.wordpress_path = "public_html"
    env.backup_prefix = "%Y%m%d-%H%m%S"
    env.backup_path = "backups"

    env.update(kwargs)

    if 'local_base_dir' not in env:
        env.local_base_dir = get_local_base_dir()

    if env.backup_prefix:
        env.backup_prefix = datetime.now().strftime(env.backup_prefix)
Ejemplo n.º 11
0
def update_env(*args, **kwargs):
    env.wordpress_path = "public_html"
    env.backup_prefix = "%Y%m%d-%H%m%S"
    env.backup_path = "backups"

    env.update(kwargs)

    if 'local_base_dir' not in env:
        env.local_base_dir = get_local_base_dir()

    if env.backup_prefix:
        env.backup_prefix = datetime.now().strftime(env.backup_prefix)
Ejemplo n.º 12
0
    def __init__(self, experiment):
        # merge env vars
        env = experiment.cmd.env.copy() if experiment.cmd else {}
        env.update(experiment.env)
        env = {k: str(v) for k, v in env.items()}

        experiment = attr.evolve(experiment, env=env, experiment_scratch_dir=experiment.experiment_scratch_dir)

        super(ExperimentScript, self).__init__(template_filename=self.DEFAULT_SLURM_EXPERIMENT_SCRIPT_TEMPLATE,
                                               experiment=experiment)
        self.experiment = experiment
        self.path.chmod('a+x')
Ejemplo n.º 13
0
def _setenv(**kwargs):
    """
    Context manager temporarily overriding ``env`` with given key/value pairs.

    This context manager is used internally by `settings` and is not intended
    to be used directly.
    """
    previous = {}
    for key, value in kwargs.iteritems():
        previous[key] = env[key]
        env[key] = value
    yield
    env.update(previous)
Ejemplo n.º 14
0
def _setenv(**kwargs):
    """
    Context manager temporarily overriding ``env`` with given key/value pairs.

    This context manager is used internally by `settings` and is not intended
    to be used directly.
    """
    previous = {}
    for key, value in kwargs.iteritems():
        previous[key] = env[key]
        env[key] = value
    yield
    env.update(previous)
Ejemplo n.º 15
0
 def host_prompting_wrapper(*args, **kwargs):
     while not env.get('host_string', False):
         handle_prompt_abort("the target host connection string")
         prompt = "No hosts found. Please specify (single) " \
             "host string for connection: "
         # WARNING: do not use six.moves.input, because test cases to not
         # overwrite that method with a faked method from Fudge
         if six.PY3 is True:
             host_string = input(prompt)
         else:
             host_string = raw_input(prompt)
         env.update(to_dict(host_string))
     return func(*args, **kwargs)
Ejemplo n.º 16
0
 def host_prompting_wrapper(*args, **kwargs):
     while not env.get('host_string', False):
         handle_prompt_abort("the target host connection string")
         prompt = "No hosts found. Please specify (single) " \
             "host string for connection: "
         # WARNING: do not use six.moves.input, because test cases to not
         # overwrite that method with a faked method from Fudge
         if six.PY3 is True:
             host_string = input(prompt)
         else:
             host_string = raw_input(prompt)
         env.update(to_dict(host_string))
     return func(*args, **kwargs)
Ejemplo n.º 17
0
def update_env_settings(env_settings_dict={}):
    if type(env_settings_dict) is not dict:
        return
    '''
        env = _AttributeDict({
            'all_hosts': [],
            'colorize_errors': False,
            'command': None,
            'command_prefixes': [],
            'cwd': '',  # Must be empty string, not None, for concatenation purposes
            'dedupe_hosts': True,
            'default_port': default_port,
            'eagerly_disconnect': False,
            'echo_stdin': True,
            'exclude_hosts': [],
            'gateway': None,
            'host': None,
            'host_string': None,
            'lcwd': '',  # Must be empty string, not None, for concatenation purposes
            'local_user': _get_system_username(),
            'output_prefix': True,
            'passwords': {},
            'path': '',
            'path_behavior': 'append',
            'port': default_port,
            'real_fabfile': None,
            'remote_interrupt': None,
            'roles': [],
            'roledefs': {},
            'shell_env': {},
            'skip_bad_hosts': False,
            'ssh_config_path': default_ssh_config_path,
            'ok_ret_codes': [0],     # a list of return codes that indicate success
            # -S so sudo accepts passwd via stdin, -p with our known-value prompt for
            # later detection (thus %s -- gets filled with env.sudo_prompt at runtime)
            'sudo_prefix': "sudo -S -p '%(sudo_prompt)s' ",
            'sudo_prompt': 'sudo password:'******'sudo_user': None,
            'tasks': [],
            'use_exceptions_for': {'network': False},
            'use_shell': True,
            'use_ssh_config': False,
            'user': None,
            'version': get_version('short')
        })
    '''
    env.update(env_settings_dict)
Ejemplo n.º 18
0
def update_env_settings(env_settings_dict={}):
    if type(env_settings_dict) is not dict:
        return
    '''
        env = _AttributeDict({
            'all_hosts': [],
            'colorize_errors': False,
            'command': None,
            'command_prefixes': [],
            'cwd': '',  # Must be empty string, not None, for concatenation purposes
            'dedupe_hosts': True,
            'default_port': default_port,
            'eagerly_disconnect': False,
            'echo_stdin': True,
            'exclude_hosts': [],
            'gateway': None,
            'host': None,
            'host_string': None,
            'lcwd': '',  # Must be empty string, not None, for concatenation purposes
            'local_user': _get_system_username(),
            'output_prefix': True,
            'passwords': {},
            'path': '',
            'path_behavior': 'append',
            'port': default_port,
            'real_fabfile': None,
            'remote_interrupt': None,
            'roles': [],
            'roledefs': {},
            'shell_env': {},
            'skip_bad_hosts': False,
            'ssh_config_path': default_ssh_config_path,
            'ok_ret_codes': [0],     # a list of return codes that indicate success
            # -S so sudo accepts passwd via stdin, -p with our known-value prompt for
            # later detection (thus %s -- gets filled with env.sudo_prompt at runtime)
            'sudo_prefix': "sudo -S -p '%(sudo_prompt)s' ",
            'sudo_prompt': 'sudo password:'******'sudo_user': None,
            'tasks': [],
            'use_exceptions_for': {'network': False},
            'use_shell': True,
            'use_ssh_config': False,
            'user': None,
            'version': get_version('short')
        })
    '''
    env.update(env_settings_dict)
Ejemplo n.º 19
0
 def setup(self):
     # Clear Fudge mock expectations
     clear_expectations()
     # Copy env, output for restoration in teardown
     self.previous_env = copy.deepcopy(env)
     # Deepcopy doesn't work well on AliasDicts; but they're only one layer
     # deep anyways, so...
     self.previous_output = output.items()
     # Set up default networking for test server
     env.disable_known_hosts = True
     env.update(to_dict('%s@%s:%s' % (USER, HOST, PORT)))
     env.password = PASSWORDS[USER]
     # Command response mocking is easier without having to account for
     # shell wrapping everywhere.
     env.use_shell = False
     # Temporary local file dir
     self.tmpdir = tempfile.mkdtemp()
Ejemplo n.º 20
0
 def setup(self):
     # Clear Fudge mock expectations
     clear_expectations()
     # Copy env, output for restoration in teardown
     self.previous_env = copy.deepcopy(env)
     # Deepcopy doesn't work well on AliasDicts; but they're only one layer
     # deep anyways, so...
     self.previous_output = output.items()
     # Set up default networking for test server
     env.disable_known_hosts = True
     env.update(to_dict('%s@%s:%s' % (USER, HOST, PORT)))
     env.password = PASSWORDS[USER]
     # Command response mocking is easier without having to account for
     # shell wrapping everywhere.
     env.use_shell = False
     # Temporary local file dir
     self.tmpdir = tempfile.mkdtemp()
Ejemplo n.º 21
0
def configure_env(env_file=module_config.env_conf):
    """Configure environment from YAML file

    :param env_file: path to config file
    :type env_file: string
    :return: :class:`fabric.state.env` object
    :rtype: :class:`fabric.state.env`
    """
    puts("Use {0} for configure environment".format(env_file))
    if not os.path.exists(env_file):
        abort("Deploy configuration file doesn't exists")

    config_file = open(env_file, 'r')
    config = load(config_file.read(), Loader=Loader)
    config_file.close()
    env.update(config)
    return env
Ejemplo n.º 22
0
    def __init__(self, experiment):
        # merge env vars
        env = experiment.cmd.env.copy() if experiment.cmd else {}
        env.update(experiment.env)
        env = {k: str(v) for k, v in env.items()}

        if NEPTUNE_LOCAL_VERSION.version[0] == 2:
            env['HOME'] = '$(pwd)'  # neptune shall loads token local copy of .neptune_tokens|.neptune/tokens

        experiment = attr.evolve(
            experiment,
            env=env,
            experiment_scratch_dir=experiment.experiment_scratch_dir)

        super(ExperimentScript, self).__init__(
            template_filename=self.DEFAULT_SLURM_EXPERIMENT_SCRIPT_TEMPLATE,
            experiment=experiment)
        self.experiment = experiment
        self.path.chmod('a+x')
Ejemplo n.º 23
0
def _setenv(**kwargs):
    """
    Context manager temporarily overriding ``env`` with given key/value pairs.

    This context manager is used internally by `settings` and is not intended
    to be used directly.
    """
    previous = {}
    new = []
    for key, value in kwargs.iteritems():
        if key in env:
            previous[key] = env[key]
        else:
            new.append(key)
        env[key] = value
    try:
        yield
    finally:
        env.update(previous)
        for key in new:
            del env[key]
Ejemplo n.º 24
0
def _setenv(**kwargs):
    """
    Context manager temporarily overriding ``env`` with given key/value pairs.

    This context manager is used internally by `settings` and is not intended
    to be used directly.
    """
    previous = {}
    new = []
    for key, value in kwargs.iteritems():
        if key in env:
            previous[key] = env[key]
        else:
            new.append(key)
        env[key] = value
    try:
        yield
    finally:
        env.update(previous)
        for key in new:
            del env[key]
Ejemplo n.º 25
0
def update_env(*args, **kwargs):
    env.local_path = "public_html"
    env.update(kwargs)

    if 'local_base_dir' not in env:
        env.local_base_dir = get_local_base_dir()
Ejemplo n.º 26
0
 def set_network(self):
     env.update(to_dict('%s@%s:%s' % (USER, HOST, PORT)))
Ejemplo n.º 27
0
def set_env(settings=None, setup_dir=''):
    """
    Used in management commands or at the module level of a fabfile to
    integrate woven project django.conf settings into fabric, and set the local current
    working directory to the distribution root (where setup.py lives).
    
    ``settings`` is your django settings module to pass in
    if you want to call this from a fabric script.
    
    ``setup_dir`` is an optional path to the directory containing setup.py
    This would be used in instances where setup.py was not above the cwd
    
    This function is used to set the environment for all hosts
   
    """

    #switch the working directory to the distribution root where setup.py is
    if hasattr(env, 'setup_path') and env.setup_path:
        setup_path = env.setup_path
    else:
        with fab_settings(fabfile='setup.py'):
            if setup_dir:
                setup_path = os.path.join(setup_dir, 'setup.py')
            else:
                setup_path = find_fabfile()
            if not setup_path:
                print 'Error: You must have a setup.py file in the current or a parent folder'
                sys.exit(1)

    local_working_dir = os.path.split(setup_path)[0]
    os.chdir(local_working_dir)

    setup = run_setup('setup.py', stop_after="init")

    if setup.get_name() == 'UNKNOWN' or setup.get_version(
    ) == '0.0.0' or not setup.packages:
        print "ERROR: You must define a minimum of name, version and packages in your setup.py"
        sys.exit(1)

    #project env variables for deployment
    env.project_name = setup.get_name()  #project_name()
    env.project_full_version = setup.get_version(
    )  #local('python setup.py --version').rstrip()
    env.project_version = _parse_project_version(env.project_full_version)
    env.project_fullname = '-'.join([env.project_name, env.project_version])
    env.project_package_name = setup.packages[0]
    env.patch = False

    #django settings are passed in by the command
    #We'll assume that if the settings aren't passed in we're running from a fabfile
    if not settings:
        sys.path.insert(0, local_working_dir)

        #import global settings
        project_settings = import_module(env.project_name + '.settings')
    else:

        project_settings = settings
    #If sqlite is used we can manage the database on first deployment
    env.DEFAULT_DATABASE_ENGINE = project_settings.DATABASES['default'][
        'ENGINE']
    env.DEFAULT_DATABASE_NAME = project_settings.DATABASES['default']['NAME']

    #overwrite with main sitesettings module
    #just for MEDIA_URL, ADMIN_MEDIA_PREFIX, and STATIC_URL
    #if this settings file exists
    try:
        site_settings = import_module('.'.join(
            [env.project_name, 'sitesettings.settings']))
        project_settings.MEDIA_URL = site_settings.MEDIA_URL
        project_settings.ADMIN_MEDIA_PREFIX = site_settings.ADMIN_MEDIA_PREFIX
        project_settings.DATABASES = site_settings.DATABASES
        if hasattr(site_settings, 'STATIC_URL'):
            project_settings.STATIC_URL = site_settings.STATIC_URL
        else:
            project_settings.STATIC_URL = project_settings.ADMIN_MEDIA_PREFIX
    except ImportError:
        pass

    #update woven_env from project_settings
    local_settings = dir(project_settings)
    #only get settings that woven uses
    for setting in local_settings:
        if setting.isupper() and hasattr(woven_env, setting):
            s = getattr(project_settings, setting, '')
            woven_env[setting] = s

    #upate the fabric env with all the woven settings
    env.update(woven_env)

    #set any user/password defaults if they are not supplied
    #Fabric would get the user from the options by default as the system user
    #We will overwrite that
    if woven_env.HOST_USER:
        env.user = woven_env.HOST_USER
    env.password = woven_env.HOST_PASSWORD

    #set the hosts if they aren't already
    if not env.hosts: env.hosts = woven_env.HOSTS
    if not env.roledefs: env.roledefs = woven_env.ROLEDEFS

    #reverse_lookup hosts to roles
    role_lookup = {}
    for role in env.roles:
        r_hosts = env.roledefs[role]
        for host in r_hosts:
            #since port is not handled by fabric.main.normalize we'll do it ourselves
            role_lookup['%s:%s' % (host, str(woven_env.HOST_SSH_PORT))] = role
    #now add any hosts that aren't already defined in roles
    for host in env.hosts:
        host_string = '%s:%s' % (host, str(woven_env.HOST_SSH_PORT))
        if host_string not in role_lookup.keys():
            role_lookup[host_string] = ''
    env.role_lookup = role_lookup
    env.hosts = role_lookup.keys()

    #remove any unneeded db adaptors - except sqlite
    remove_backends = ['postgresql_psycopg2', 'mysql']
    for db in project_settings.DATABASES:
        engine = project_settings.DATABASES[db]['ENGINE'].split('.')[-1]
        if engine in remove_backends: remove_backends.remove(engine)
    for backend in remove_backends:
        if backend == 'postgresql_psycopg2': rm = 'python-psycopg2'
        elif backend == 'mysql': rm = 'python-mysqldb'
        env.HOST_BASE_PACKAGES.remove(rm)

    #packages can be just the base + extra packages
    #or role dependent we need to just map out the packages to hosts and roles here
    packages = {}
    all_packages = set([])
    for role in env.roles:
        packages[role] = env.ROLE_PACKAGES.get(role, [])
        if not packages[role]:
            packages[role] = env.HOST_BASE_PACKAGES + env.HOST_EXTRA_PACKAGES
        all_packages = set(packages[role]) | all_packages

    #no role
    packages[''] = env.HOST_BASE_PACKAGES + env.HOST_EXTRA_PACKAGES
    all_packages = set(packages['']) | all_packages

    #conveniently add gunicorn ppa
    if 'gunicorn' in all_packages:
        if 'ppa:bchesneau/gunicorn' not in env.LINUX_PACKAGE_REPOSITORIES:
            env.LINUX_PACKAGE_REPOSITORIES.append('ppa:bchesneau/gunicorn')

    env.packages = packages

    #sanity check for unwanted combinations in the empty role
    u = set(packages[''])
    wsgi = u & set(['gunicorn', 'uwsgi'])
    if wsgi and 'apache2' in u:
        u = u - set(['apache2', 'libapache2-mod-wsgi'])

    #Used to detect certain apps eg South, static_builder
    env.INSTALLED_APPS = project_settings.INSTALLED_APPS

    env.packages[''] = list(u)

    #per host
    env.installed_packages = {}
    env.uninstalled_packages = {}

    #UFW firewall rules
    firewall_rules = {}
    for role in env.roles:
        firewall_rules[role] = env.ROLE_UFW_RULES.get(role, [])
    firewall_rules[''] = env.UFW_RULES
    env.firewall_rules = firewall_rules

    #Now update the env with any settings that are not defined by woven but may
    #be used by woven or fabric
    env.MEDIA_ROOT = project_settings.MEDIA_ROOT
    env.MEDIA_URL = project_settings.MEDIA_URL
    env.ADMIN_MEDIA_PREFIX = project_settings.ADMIN_MEDIA_PREFIX
    if not env.STATIC_URL: env.STATIC_URL = project_settings.ADMIN_MEDIA_PREFIX
    env.TEMPLATE_DIRS = project_settings.TEMPLATE_DIRS

    #Set the server /etc/timezone
    env.TIME_ZONE = project_settings.TIME_ZONE
    #Used to detect certain apps eg South, static_builder
    env.INSTALLED_APPS = project_settings.INSTALLED_APPS

    #SSH key
    if env.SSH_KEY_FILENAME: env.KEY_FILENAME = env.SSH_KEY_FILENAME
    else: env.KEY_FILENAME = ''

    #noinput
    if not hasattr(env, 'INTERACTIVE'): env.INTERACTIVE = True
    if not hasattr(env, 'verbosity'): env.verbosity = 1

    #overwrite existing settings
    if not hasattr(env, 'overwrite'): env.overwrite = False

    #South integration defaults
    env.nomigration = False
    env.manualmigration = False
    env.migration = ''

    env.root_disabled = False

    #Sites
    env.sites = {}
    env.shell = '/bin/bash --noprofile -l -c'
Ejemplo n.º 28
0
from fabric.state import env
from fabric.colors import green, red
from cuisine import package_ensure, dir_ensure, file_write
from distutils.util import strtobool

env.disable_known_hosts = True

PATH = os.path.dirname(os.path.abspath(__file__))
RPM_COMPONENTS = ['base', 'updates', 'extras']
RPM_ARCHS = ['i386', 'x86_64']

CONFIG_FILE = os.path.expanduser('~/.config/package-build.yaml')
if not os.path.isfile(CONFIG_FILE):
    abort('config file {} not found, aborting here'.format(CONFIG_FILE))
with open(CONFIG_FILE, 'r') as config_file:
    env.update(yaml.load(config_file)['env'])

PACKAGE_FORMAT = {}
for package_format, dists in env.dists.iteritems():
    for dist in dists:
        PACKAGE_FORMAT[dist] = package_format


def atoi(text):
    return (int(text) if text.isdigit() else text)


def natural_keys(text):
    '''
    alist.sort(key=natural_keys) sorts in human order
    http://nedbatchelder.com/blog/200712/human_sorting.html
Ejemplo n.º 29
0
def set_env(settings=None, setup_dir=''):
    """
    Used in management commands or at the module level of a fabfile to
    integrate woven project django.conf settings into fabric, and set
    the local current working directory to the distribution root
    (where setup.py lives).

    ``settings`` is your django settings module to pass in if you want
    to call this from a fabric script.

    ``setup_dir`` is an optional path to the directory containing
    setup.py This would be used in instances where setup.py was not
    above the CWD.

    This function is used to set the environment for all hosts.
    """

    # Switch the working directory to the distribution root where
    # setup.py is.
    if hasattr(env, 'setup_path') and env.setup_path:
        setup_path = env.setup_path
    else:
        with fab_settings(fabfile='setup.py'):
            if setup_dir:
                setup_path = os.path.join(setup_dir, 'setup.py')
            else:
                setup_path = find_fabfile()
            if not setup_path:
                print 'Error: You must have a setup.py file in ' \
                    'the current or a parent folder'
                sys.exit(1)

    local_working_dir = os.path.split(setup_path)[0]
    os.chdir(local_working_dir)

    setup = run_setup('setup.py', stop_after="init")

    if (setup.get_name() == 'UNKNOWN' or
            setup.get_version() == '0.0.0' or
            not setup.packages):
        print "ERROR: You must define a minimum of name, version " \
            "and packages in your setup.py"
        sys.exit(1)

    # Project env variables for deployment.
    # Project_name().
    env.project_name = setup.get_name()
    #local('python setup.py --version').rstrip()
    env.project_full_version = setup.get_version()
    env.project_version = _parse_project_version(env.project_full_version)
    env.project_fullname = '-'.join([env.project_name, env.project_version])
    env.project_package_name = setup.packages[0]
    env.patch = False

    # Django settings are passed in by the command. We'll assume that
    # if the settings aren't passed in we're running from a fabfile.
    if not settings:
        sys.path.insert(0, local_working_dir)

        # Import global settings.
        project_settings = import_module(env.project_name + '.settings')
    else:

        project_settings = settings
    # If SQLite is used we can manage the database on first
    # deployment.
    env.DEFAULT_DATABASE_ENGINE = \
        project_settings.DATABASES['default']['ENGINE']
    env.DEFAULT_DATABASE_NAME = \
        project_settings.DATABASES['default']['NAME']

    # Overwrite with main sitesettings module just for MEDIA_URL,
    # ADMIN_MEDIA_PREFIX, and STATIC_URL if this settings file exists.
    try:
        site_settings = import_module(
                '.'.join([env.project_name, 'sitesettings.settings']))
        project_settings.MEDIA_URL = site_settings.MEDIA_URL
        project_settings.ADMIN_MEDIA_PREFIX = site_settings.ADMIN_MEDIA_PREFIX
        project_settings.DATABASES = site_settings.DATABASES
        if hasattr(site_settings, 'STATIC_URL'):
            project_settings.STATIC_URL = site_settings.STATIC_URL
        else:
            project_settings.STATIC_URL = project_settings.ADMIN_MEDIA_PREFIX
    except ImportError:
        pass

    # Update woven_env from project_settings.
    local_settings = dir(project_settings)
    # Only get settings that woven uses.
    for setting in local_settings:
        if setting.isupper() and hasattr(woven_env, setting):
            s = getattr(project_settings, setting, '')
            woven_env[setting] = s

    # Upate the fabric env with all the woven settings.
    env.update(woven_env)

    # Set any user/password defaults if they are not supplied.
    # Fabric would get the user from the options by default as the
    # system user. We will overwrite that.
    if woven_env.HOST_USER:
        env.user = woven_env.HOST_USER
    env.password = woven_env.HOST_PASSWORD

    # Set the hosts if they aren't already.
    if not env.hosts:
        env.hosts = woven_env.HOSTS
    if not env.roledefs:
        env.roledefs = woven_env.ROLEDEFS

    # Reverse_lookup hosts to roles.
    role_lookup = {}
    for role in env.roles:
        r_hosts = env.roledefs[role]
        for host in r_hosts:
            # Since port is not handled by fabric.main.normalize we'll
            # do it ourselves.
            role_lookup['%s:%s' % (host, str(woven_env.HOST_SSH_PORT))] = role
    # Now add any hosts that aren't already defined in roles.
    for host in env.hosts:
        host_string = '%s:%s' % (host, str(woven_env.HOST_SSH_PORT))
        if host_string not in role_lookup.keys():
            role_lookup[host_string] = ''
    env.role_lookup = role_lookup
    env.hosts = role_lookup.keys()

    # Remove any unneeded db adaptors - except sqlite.
    remove_backends = ['postgresql_psycopg2', 'mysql']
    for db in project_settings.DATABASES:
        engine = project_settings.DATABASES[db]['ENGINE'].split('.')[-1]
        if engine in remove_backends:
            remove_backends.remove(engine)
    for backend in remove_backends:
        if backend == 'postgresql_psycopg2':
            rm = 'python-psycopg2'
        elif backend == 'mysql':
            rm = 'python-mysqldb'
        env.HOST_BASE_PACKAGES.remove(rm)

    # Packages can be just the base + extra packages or role-
    # dependent. We need to just map out the packages to hosts and
    # roles here.
    packages = {}
    all_packages = set([])
    for role in env.roles:
        packages[role] = env.ROLE_PACKAGES.get(role, [])
        if not packages[role]:
            packages[role] = env.HOST_BASE_PACKAGES + env.HOST_EXTRA_PACKAGES
        all_packages = set(packages[role]) | all_packages

    # No role.
    packages[''] = env.HOST_BASE_PACKAGES + env.HOST_EXTRA_PACKAGES
    all_packages = set(packages['']) | all_packages

    # Conveniently add gunicorn ppa.
    if 'gunicorn' in all_packages:
        if 'ppa:bchesneau/gunicorn' not in env.LINUX_PACKAGE_REPOSITORIES:
            env.LINUX_PACKAGE_REPOSITORIES.append('ppa:bchesneau/gunicorn')

    env.packages = packages

    # Sanity-check for unwanted combinations in the empty role.
    u = set(packages[''])
    wsgi = u & set(['gunicorn', 'uwsgi'])
    if wsgi and 'apache2' in u:
        u = u - set(['apache2', 'libapache2-mod-wsgi'])

    # Used to detect certain apps eg. South, static_builder.
    env.INSTALLED_APPS = project_settings.INSTALLED_APPS

    env.packages[''] = list(u)

    # Per host.
    env.installed_packages = {}
    env.uninstalled_packages = {}

    # UFW firewall rules.
    firewall_rules = {}
    for role in env.roles:
        firewall_rules[role] = env.ROLE_UFW_RULES.get(role, [])
    firewall_rules[''] = env.UFW_RULES
    env.firewall_rules = firewall_rules

    # Now update the env with any settings that are not defined by
    # woven but may be used by woven or fabric.
    env.MEDIA_ROOT = project_settings.MEDIA_ROOT
    env.MEDIA_URL = project_settings.MEDIA_URL
    try:
        env.ADMIN_MEDIA_PREFIX = project_settings.ADMIN_MEDIA_PREFIX
    except AttributeError:
        env.ADMIN_MEDIA_PREFIX = ''
    if not env.STATIC_URL:
        env.STATIC_URL = project_settings.ADMIN_MEDIA_PREFIX
    env.TEMPLATE_DIRS = project_settings.TEMPLATE_DIRS

    # Set the server /etc/timezone.
    env.TIME_ZONE = project_settings.TIME_ZONE
    # Used to detect certain apps eg. South, static_builder.
    env.INSTALLED_APPS = project_settings.INSTALLED_APPS

    # SSH key.
    if (not hasattr(env, 'key_filename') and
            not env.key_filename and
            env.SSH_KEY_FILENAME):
        env.key_filename = env.SSH_KEY_FILENAME
    elif not hasattr(env, 'key_filename'):
        env.key_filename = None

    # Noinput.
    if not hasattr(env, 'INTERACTIVE'):
        env.INTERACTIVE = True
    if not hasattr(env, 'verbosity'):
        env.verbosity = 1

    # Overwrite existing settings.
    if not hasattr(env, 'overwrite'):
        env.overwrite = False

    # South integration defaults.
    env.nomigration = False
    env.manualmigration = False
    env.migration = ''

    env.root_disabled = False

    # Sites.
    env.sites = {}
    env.shell = '/bin/bash --noprofile -l -c'
Ejemplo n.º 30
0
def main():
    """
    Main command-line execution loop.
    """
    try:
        # Parse command line options
        parser, options, arguments = parse_options()

        # Handle regular args vs -- args
        arguments = parser.largs
        remainder_arguments = parser.rargs

        # Update env with any overridden option values
        # NOTE: This needs to remain the first thing that occurs
        # post-parsing, since so many things hinge on the values in env.
        for option in env_options:
            env[option.dest] = getattr(options, option.dest)

        # Handle --hosts, --roles (comma separated string => list)
        for key in ['hosts', 'roles']:
            if key in env and isinstance(env[key], str):
                env[key] = env[key].split(',')

        # Handle output control level show/hide
        update_output_levels(show=options.show, hide=options.hide)

        # Handle version number option
        if options.show_version:
            print("Fabric %s" % env.version)
            sys.exit(0)

        # Load settings from user settings file, into shared env dict.
        env.update(load_settings(env.rcfile))

        # Find local fabfile path or abort
        fabfile = find_fabfile()
        if not fabfile and not remainder_arguments:
            abort("Couldn't find any fabfiles!")

        # Store absolute path to fabfile in case anyone needs it
        env.real_fabfile = fabfile

        # Load fabfile (which calls its module-level code, including
        # tweaks to env values) and put its commands in the shared commands
        # dict
        if fabfile:
            docstring, callables = load_fabfile(fabfile)
            commands.update(callables)

        # Autocompletion support
        autocomplete_items = [cmd.replace('_', '-') for cmd in commands]
        if 'autocomplete' in env:
            autocomplete_items += env.autocomplete

        autocomplete(parser, ListCompleter(autocomplete_items))

        # Handle hooks related options
        _disable_hooks = options.disable_hooks
        _enable_hooks = options.enable_hooks

        if _disable_hooks:
            for _hook in _disable_hooks.strip().split():
                DISABLED_HOOKS.append(_hook.strip())

        if _enable_hooks:
            for _hook in _enable_hooks.strip().split():
                ENABLED_HOOKS.append(_hook.strip())

        # Handle the non-execution flow
        if not arguments and not remainder_arguments:

            # Non-verbose command list
            if options.shortlist:
                shortlist()

            # Handle show (command-specific help) option
            if options.display:
                display_command(options.display)

            # Else, show the list of commands and exit
            list_commands(docstring)

        # Now that we're settled on a fabfile, inform user.
        if output.debug:
            if fabfile:
                print("Using fabfile '%s'" % fabfile)
            else:
                print("No fabfile loaded -- remainder command only")

        # Parse arguments into commands to run (plus args/kwargs/hosts)
        commands_to_run, env_update = parse_arguments(arguments)
        env.update(env_update)

        # Parse remainders into a faux "command" to execute
        remainder_command = parse_remainder(remainder_arguments)

        # Figure out if any specified task names are invalid
        unknown_commands = []
        for tup in commands_to_run:
            if tup[0] not in commands:
                unknown_commands.append(tup[0])

        # Abort if any unknown commands were specified
        if unknown_commands:
            abort("Command(s) not found:\n%s" \
                % indent(unknown_commands))

        # Generate remainder command and insert into commands, commands_to_run
        if remainder_command:
            r = '<remainder>'
            commands[r] = lambda: api.run(remainder_command)
            commands_to_run.append((r, [], {}, [], []))

        if output.debug:
            names = ", ".join(x[0] for x in commands_to_run)
            print("Commands to run: %s" % names)

        call_hooks('commands.before', commands, commands_to_run)

        # Initialse context runner
        env()

        # Initialise the default stage if none are given as the first command.
        if 'stages' in env:
            if commands_to_run[0][0] not in env.stages:
                execute_command(
                    (env.stages[0], (), {}, None, None, None), commands
                    )
            else:
                execute_command(commands_to_run.pop(0), commands)

        if env.config_file:
            config_path = realpath(expanduser(env.config_file))
            config_path = join(dirname(fabfile), config_path)
            config_file = open(config_path, 'rb')
            config = load_yaml(config_file.read())
            if not config:
                env.config = AttributeDict()
            elif not isinstance(config, dict):
                abort("Invalid config file found at %s" % config_path)
            else:
                env.config = AttributeDict(config)
            config_file.close()

        call_hooks('config.loaded')
        first_time_env_call = 1

        # At this point all commands must exist, so execute them in order.
        for spec in commands_to_run:
            execute_command(spec, commands)

        # If we got here, no errors occurred, so print a final note.
        if output.status:
            msg = "\nDone."
            if env.colors:
                msg = env.color_settings['finish'](msg)
            print(msg)

    except SystemExit:
        # a number of internal functions might raise this one.
        raise
    except KeyboardInterrupt:
        if output.status:
            msg = "\nStopped."
            if env.colors:
                msg = env.color_settings['finish'](msg)
            print >> sys.stderr, msg
        sys.exit(1)
    except:
        sys.excepthook(*sys.exc_info())
        # we might leave stale threads if we don't explicitly exit()
        sys.exit(1)
    finally:
        call_hooks('commands.after')
        disconnect_all()
    sys.exit(0)
Ejemplo n.º 31
0
 def tearDown(self):
     self.restore_stdout_stderr()
     env.clear()
     env.update(self.env_vars)
     logging.disable(logging.NOTSET)
     self.restore_log_and_delete_temp_dir()
Ejemplo n.º 32
0
 def teardown(self):
     env.update(self.previous_env)
     output.update(self.previous_output)
     shutil.rmtree(self.tmpdir)
Ejemplo n.º 33
0
 def teardown(self):
     env.update(self.previous_env)
     output.update(self.previous_output)
     shutil.rmtree(self.tmpdir)
Ejemplo n.º 34
0
 def tearDown(self):
     self.restore_stdout_stderr()
     env.clear()
     env.update(self.env_vars)
     logging.disable(logging.NOTSET)
     self.restore_log_and_delete_temp_dir()
Ejemplo n.º 35
0
def update_env(*args, **kwargs):
    env.local_path = "public_html"
    env.update(kwargs)

    if 'local_base_dir' not in env:
        env.local_base_dir = get_local_base_dir()
Ejemplo n.º 36
0
def set_env(settings=None, setup_dir=""):
    """
    Used in management commands or at the module level of a fabfile to
    integrate woven project django.conf settings into fabric, and set the local current
    working directory to the distribution root (where setup.py lives).
    
    ``settings`` is your optional django.conf imported settings.
    
    ``setup_dir`` is an optional path to the directory containing setup.py
    This would be used in instances where setup.py was not above the cwd
    
    This function is used to set the environment for all hosts

    """
    # switch the working directory to the distribution root where setup.py is
    original_fabfile = env.fabfile
    env.fabfile = "setup.py"
    if setup_dir:
        fabfile_path = os.path.join(setup_dir, "setup.py")
    else:
        fabfile_path = find_fabfile()
    if not fabfile_path:
        print "Error: You must have a setup.py file above your project directory"
        sys.exit(1)

    local_working_dir = os.path.split(fabfile_path)[0]
    env.fabfile = original_fabfile
    os.chdir(local_working_dir)

    # project env variables for deployment
    env.project_name = project_name()
    env.project_full_version = local("python setup.py --version").rstrip()
    env.project_version = _parse_project_version(env.project_full_version)
    env.project_fullname = "-".join([env.project_name, env.project_version])
    env.patch = False

    # We'll assume that if the settings aren't passed in we're running from a fabfile
    if not settings:
        sys.path.insert(0, local_working_dir)

        # import global settings
        project_settings = import_module(env.project_name + ".settings")
    else:
        project_settings = settings

    # overwrite with main sitesettings module
    # just for MEDIA_URL, ADMIN_MEDIA_PREFIX, and STATIC_URL
    # if this settings file exists
    try:
        site_settings = import_module(".".join([env.project_name, "sitesettings.settings"]))
        project_settings.MEDIA_URL = site_settings.MEDIA_URL
        project_settings.ADMIN_MEDIA_PREFIX = site_settings.ADMIN_MEDIA_PREFIX
        if hasattr(site_settings, "STATIC_URL"):
            project_settings.STATIC_URL = site_settings.STATIC_URL
    except ImportError:
        pass

    # update woven_env from project_settings
    local_settings = dir(project_settings)
    # only get settings that woven uses
    for setting in local_settings:
        if setting.isupper() and hasattr(woven_env, setting):
            s = getattr(project_settings, setting, "")
            woven_env[setting] = s

    # upate the fabric env with all the woven settings
    env.update(woven_env)

    # set any user/password defaults if they are not supplied
    # Fabric would get the user from the options by default as the system user
    # We will overwrite that
    if woven_env.HOST_USER:
        env.user = woven_env.HOST_USER
    env.password = woven_env.HOST_PASSWORD

    # set the hosts
    if not env.hosts:
        env.hosts = woven_env.HOSTS
    if not env.roledefs:
        env.roledefs = woven_env.ROLEDEFS

    # since port is not handled by fabric.main.normalize we'll do it ourselves
    host_list = []
    if "hosts" in env and isinstance(env["hosts"], list):
        for host_string in env.hosts:
            if not ":" in host_string:
                host_string += ":%s" % str(woven_env.HOST_SSH_PORT)
            # not sure that this is necessary but it seems clearer to make full
            # hoststrings with the correct user
            if not "@" in host_string:
                host_string = env.user + "@" + host_string
            host_list.append(host_string)
            env.hosts = host_list

    # Now update the env with any settings that are not defined by woven but may
    # be used by woven or fabric
    env.MEDIA_ROOT = project_settings.MEDIA_ROOT
    env.MEDIA_URL = project_settings.MEDIA_URL
    env.ADMIN_MEDIA_PREFIX = project_settings.ADMIN_MEDIA_PREFIX
    env.TEMPLATE_DIRS = project_settings.TEMPLATE_DIRS

    # If sqlite is used we can manage the database on deployment
    env.DEFAULT_DATABASE_ENGINE = project_settings.DATABASES["default"]["ENGINE"]
    env.DEFAULT_DATABASE_NAME = project_settings.DATABASES["default"]["NAME"]

    # Set the server /etc/timezone
    env.TIME_ZONE = project_settings.TIME_ZONE
    # Used to detect certain apps eg South, static_builder
    env.INSTALLED_APPS = project_settings.INSTALLED_APPS

    # noinput
    if not hasattr(env, "INTERACTIVE"):
        env.INTERACTIVE = True

    # South integration defaults
    env.nomigration = False
    env.manualmigration = False
    env.migration = ""

    # Sites
    env.sites = {}
    env.shell = "/bin/bash --noprofile -l -c"
Ejemplo n.º 37
0
 def teardown(self):
     env.update(self.previous_env)
     output.update(self.previous_output)
     shutil.rmtree(self.tmpdir)
     # Clear Fudge mock expectations...again
     clear_expectations()
Ejemplo n.º 38
0
PATH = os.path.dirname(os.path.abspath(__file__))
RPM_COMPONENTS = ['base', 'updates', 'extras']
RPM_ARCHS = ['i386', 'x86_64']
PACKAGE_FORMAT = {
    'centos6': 'rpm',
    'debian7': 'deb',
    'ubuntu12.04': 'deb',
    'ubuntu14.04': 'deb',
}

CONFIG_FILE = os.path.expanduser('~/.config/package-build.yaml')
if not os.path.isfile(CONFIG_FILE):
    abort('config file {} not found, aborting here'.format(CONFIG_FILE))
with open(CONFIG_FILE, 'r') as config_file:
    env.update(yaml.load(config_file)['env'])


def atoi(text):
    return (int(text) if text.isdigit() else text)


def natural_keys(text):
    '''
    alist.sort(key=natural_keys) sorts in human order
    http://nedbatchelder.com/blog/200712/human_sorting.html
    (See Toothy's implementation in the comments)
    '''

    return [atoi(c) for c in re.split('(\d+)', text)]
Ejemplo n.º 39
0
 def teardown(self):
     env.update(self.previous_env)
     output.update(self.previous_output)
Ejemplo n.º 40
0
 def teardown(self):
     env.update(self.previous_env)
     output.update(self.previous_output)
     shutil.rmtree(self.tmpdir)
     # Clear Fudge mock expectations...again
     clear_expectations()
Ejemplo n.º 41
0
def main():
    """
    Main command-line execution loop.
    """
    try:
        # Parse command line options
        parser, options, arguments = parse_options()

        # Handle regular args vs -- args
        arguments = parser.largs
        remainder_arguments = parser.rargs

        # Update env with any overridden option values
        # NOTE: This needs to remain the first thing that occurs
        # post-parsing, since so many things hinge on the values in env.
        for option in env_options:
            env[option.dest] = getattr(options, option.dest)

        # Handle --hosts, --roles (comma separated string => list)
        for key in ['hosts', 'roles']:
            if key in env and isinstance(env[key], str):
                env[key] = env[key].split(',')

        # Handle output control level show/hide
        update_output_levels(show=options.show, hide=options.hide)

        # Handle version number option
        if options.show_version:
            print("Fabric %s" % env.version)
            sys.exit(0)

        # Load settings from user settings file, into shared env dict.
        env.update(load_settings(env.rcfile))

        # Find local fabfile path or abort
        fabfile = find_fabfile()
        if not fabfile and not remainder_arguments:
            abort("Couldn't find any fabfiles!")

        # Store absolute path to fabfile in case anyone needs it
        env.real_fabfile = fabfile

        # Load fabfile (which calls its module-level code, including
        # tweaks to env values) and put its commands in the shared commands
        # dict
        if fabfile:
            docstring, callables = load_fabfile(fabfile)
            commands.update(callables)

        # Autocompletion support
        autocomplete_items = [cmd.replace('_', '-') for cmd in commands]
        if 'autocomplete' in env:
            autocomplete_items += env.autocomplete

        autocomplete(parser, ListCompleter(autocomplete_items))

        # Handle hooks related options
        _disable_hooks = options.disable_hooks
        _enable_hooks = options.enable_hooks

        if _disable_hooks:
            for _hook in _disable_hooks.strip().split():
                DISABLED_HOOKS.append(_hook.strip())

        if _enable_hooks:
            for _hook in _enable_hooks.strip().split():
                ENABLED_HOOKS.append(_hook.strip())

        # Handle the non-execution flow
        if not arguments and not remainder_arguments:

            # Non-verbose command list
            if options.shortlist:
                shortlist()

            # Handle show (command-specific help) option
            if options.display:
                display_command(options.display)

            # Else, show the list of commands and exit
            list_commands(docstring)

        # Now that we're settled on a fabfile, inform user.
        if output.debug:
            if fabfile:
                print("Using fabfile '%s'" % fabfile)
            else:
                print("No fabfile loaded -- remainder command only")

        # Parse arguments into commands to run (plus args/kwargs/hosts)
        commands_to_run, env_update = parse_arguments(arguments)
        env.update(env_update)

        # Parse remainders into a faux "command" to execute
        remainder_command = parse_remainder(remainder_arguments)

        # Figure out if any specified task names are invalid
        unknown_commands = []
        for tup in commands_to_run:
            if tup[0] not in commands:
                unknown_commands.append(tup[0])

        # Abort if any unknown commands were specified
        if unknown_commands:
            abort("Command(s) not found:\n%s" \
                % indent(unknown_commands))

        # Generate remainder command and insert into commands, commands_to_run
        if remainder_command:
            r = '<remainder>'
            commands[r] = lambda: api.run(remainder_command)
            commands_to_run.append((r, [], {}, [], []))

        if output.debug:
            names = ", ".join(x[0] for x in commands_to_run)
            print("Commands to run: %s" % names)

        call_hooks('commands.before', commands, commands_to_run)

        # Initialse context runner
        env()

        # Initialise the default stage if none are given as the first command.
        if 'stages' in env:
            if commands_to_run[0][0] not in env.stages:
                execute_command(
                    (env.stages[0], (), {}, None, None, None), commands
                    )
            else:
                execute_command(commands_to_run.pop(0), commands)

        if env.config_file:
            config_path = realpath(expanduser(env.config_file))
            config_path = join(dirname(fabfile), config_path)
            config_file = open(config_path, 'rb')
            config = load_yaml(config_file.read())
            if not config:
                env.config = AttributeDict()
            elif not isinstance(config, dict):
                abort("Invalid config file found at %s" % config_path)
            else:
                env.config = AttributeDict(config)
            config_file.close()

        call_hooks('config.loaded')
        first_time_env_call = 1

        # At this point all commands must exist, so execute them in order.
        for spec in commands_to_run:
            execute_command(spec, commands)

        # If we got here, no errors occurred, so print a final note.
        if output.status:
            msg = "\nDone."
            if env.colors:
                msg = env.color_settings['finish'](msg)
            print(msg)

    except SystemExit:
        # a number of internal functions might raise this one.
        raise
    except KeyboardInterrupt:
        if output.status:
            msg = "\nStopped."
            if env.colors:
                msg = env.color_settings['finish'](msg)
            print >> sys.stderr, msg
        sys.exit(1)
    except:
        sys.excepthook(*sys.exc_info())
        # we might leave stale threads if we don't explicitly exit()
        sys.exit(1)
    finally:
        call_hooks('commands.after')
        disconnect_all()
    sys.exit(0)
Ejemplo n.º 42
0
def set_env(settings=None, setup_dir=""):
    """
    Used in management commands or at the module level of a fabfile to
    integrate woven project django.conf settings into fabric, and set the local current
    working directory to the distribution root (where setup.py lives).
    
    ``settings`` is your django settings module to pass in
    if you want to call this from a fabric script.
    
    ``setup_dir`` is an optional path to the directory containing setup.py
    This would be used in instances where setup.py was not above the cwd
    
    This function is used to set the environment for all hosts
   
    """

    # switch the working directory to the distribution root where setup.py is
    original_fabfile = env.fabfile
    env.fabfile = "setup.py"
    if setup_dir:
        fabfile_path = os.path.join(setup_dir, "setup.py")
    else:
        fabfile_path = find_fabfile()
    if not fabfile_path:
        print "Error: You must create a setup.py file in your distribution"
        sys.exit(1)

    local_working_dir = os.path.split(fabfile_path)[0]
    env.fabfile = original_fabfile
    os.chdir(local_working_dir)

    setup = run_setup("setup.py", stop_after="init")

    if setup.get_name() == "UNKNOWN" or setup.get_version() == "0.0.0" or not setup.packages:
        print "ERROR: You must define a minimum of name, version and packages in your setup.py"
        sys.exit(1)

    # project env variables for deployment
    env.project_name = setup.get_name()  # project_name()
    env.project_full_version = setup.get_version()  # local('python setup.py --version').rstrip()
    env.project_version = _parse_project_version(env.project_full_version)
    env.project_fullname = "-".join([env.project_name, env.project_version])
    env.project_package_name = setup.packages[0]
    env.patch = False

    # django settings are passed in by the command
    # We'll assume that if the settings aren't passed in we're running from a fabfile
    if not settings:
        sys.path.insert(0, local_working_dir)

        # import global settings
        project_settings = import_module(env.project_name + ".settings")
    else:

        project_settings = settings
    # If sqlite is used we can manage the database on first deployment
    env.DEFAULT_DATABASE_ENGINE = project_settings.DATABASES["default"]["ENGINE"]
    env.DEFAULT_DATABASE_NAME = project_settings.DATABASES["default"]["NAME"]

    # overwrite with main sitesettings module
    # just for MEDIA_URL, ADMIN_MEDIA_PREFIX, and STATIC_URL
    # if this settings file exists
    try:
        site_settings = import_module(".".join([env.project_name, "sitesettings.settings"]))
        project_settings.MEDIA_URL = site_settings.MEDIA_URL
        project_settings.ADMIN_MEDIA_PREFIX = site_settings.ADMIN_MEDIA_PREFIX
        project_settings.DATABASES = site_settings.DATABASES
        if hasattr(site_settings, "STATIC_URL"):
            project_settings.STATIC_URL = site_settings.STATIC_URL
        else:
            project_settings.STATIC_URL = project_settings.ADMIN_MEDIA_PREFIX
    except ImportError:
        pass

    # update woven_env from project_settings
    local_settings = dir(project_settings)
    # only get settings that woven uses
    for setting in local_settings:
        if setting.isupper() and hasattr(woven_env, setting):
            s = getattr(project_settings, setting, "")
            woven_env[setting] = s

    # upate the fabric env with all the woven settings
    env.update(woven_env)

    # set any user/password defaults if they are not supplied
    # Fabric would get the user from the options by default as the system user
    # We will overwrite that
    if woven_env.HOST_USER:
        env.user = woven_env.HOST_USER
    env.password = woven_env.HOST_PASSWORD

    # set the hosts if they aren't already
    if not env.hosts:
        env.hosts = woven_env.HOSTS
    if not env.roledefs:
        env.roledefs = woven_env.ROLEDEFS

    # reverse_lookup hosts to roles
    role_lookup = {}
    for role in env.roles:
        r_hosts = env.roledefs[role]
        for host in r_hosts:
            # since port is not handled by fabric.main.normalize we'll do it ourselves
            role_lookup["%s:%s" % (host, str(woven_env.HOST_SSH_PORT))] = role
    # now add any hosts that aren't already defined in roles
    for host in env.hosts:
        host_string = "%s:%s" % (host, str(woven_env.HOST_SSH_PORT))
        if host_string not in role_lookup.keys():
            role_lookup[host_string] = ""
    env.role_lookup = role_lookup
    env.hosts = role_lookup.keys()

    # remove any unneeded db adaptors - except sqlite
    remove_backends = ["postgresql_psycopg2", "mysql"]
    for db in project_settings.DATABASES:
        engine = project_settings.DATABASES[db]["ENGINE"].split(".")[-1]
        if engine in remove_backends:
            remove_backends.remove(engine)
    for backend in remove_backends:
        if backend == "postgresql_psycopg2":
            rm = "python-psycopg2"
        elif backend == "mysql":
            rm = "python-mysqldb"
        env.HOST_BASE_PACKAGES.remove(rm)

    # packages can be just the base + extra packages
    # or role dependent we need to just map out the packages to hosts and roles here
    packages = {}
    all_packages = set([])
    for role in env.roles:
        packages[role] = env.ROLE_PACKAGES.get(role, [])
        if not packages[role]:
            packages[role] = env.HOST_BASE_PACKAGES + env.HOST_EXTRA_PACKAGES
        all_packages = set(packages[role]) | all_packages

    # no role
    packages[""] = env.HOST_BASE_PACKAGES + env.HOST_EXTRA_PACKAGES
    all_packages = set(packages[""]) | all_packages

    # conveniently add gunicorn ppa
    if "gunicorn" in all_packages:
        if "ppa:bchesneau/gunicorn" not in env.LINUX_PACKAGE_REPOSITORIES:
            env.LINUX_PACKAGE_REPOSITORIES.append("ppa:bchesneau/gunicorn")

    env.packages = packages

    # sanity check for unwanted combinations in the empty role
    u = set(packages[""])
    wsgi = u & set(["gunicorn", "uwsgi"])
    if wsgi and "apache2" in u:
        u = u - set(["apache2", "libapache2-mod-wsgi"])
    env.packages[""] = list(u)

    # per host
    env.installed_packages = {}
    env.uninstalled_packages = {}

    # UFW firewall rules
    firewall_rules = {}
    for role in env.roles:
        firewall_rules[role] = env.ROLE_UFW_RULES.get(role, [])
    firewall_rules[""] = env.UFW_RULES
    env.firewall_rules = firewall_rules

    # Now update the env with any settings that are not defined by woven but may
    # be used by woven or fabric
    env.MEDIA_ROOT = project_settings.MEDIA_ROOT
    env.MEDIA_URL = project_settings.MEDIA_URL
    env.ADMIN_MEDIA_PREFIX = project_settings.ADMIN_MEDIA_PREFIX
    if not env.STATIC_URL:
        env.STATIC_URL = project_settings.ADMIN_MEDIA_PREFIX
    env.TEMPLATE_DIRS = project_settings.TEMPLATE_DIRS

    # Set the server /etc/timezone
    env.TIME_ZONE = project_settings.TIME_ZONE
    # Used to detect certain apps eg South, static_builder
    env.INSTALLED_APPS = project_settings.INSTALLED_APPS

    # SSH key
    if env.SSH_KEY_FILENAME:
        env.KEY_FILENAME = env.SSH_KEY_FILENAME
    else:
        env.KEY_FILENAME = ""

    # noinput
    if not hasattr(env, "INTERACTIVE"):
        env.INTERACTIVE = True
    if not hasattr(env, "verbosity"):
        env.verbosity = 1

    # overwrite existing settings
    if not hasattr(env, "overwrite"):
        env.overwrite = False

    # South integration defaults
    env.nomigration = False
    env.manualmigration = False
    env.migration = ""

    env.root_disabled = False

    # Sites
    env.sites = {}
    env.shell = "/bin/bash --noprofile -l -c"
Ejemplo n.º 43
0
 def set_network(self):
     env.update(to_dict('%s@%s:%s' % (USER, HOST, PORT)))
Ejemplo n.º 44
0
 def teardown(self):
     env.update(self.previous_env)
     output.update(self.previous_output)
Ejemplo n.º 45
0
import os

from fabric.context_managers import cd
from fabric.contrib.files import upload_template
from fabric.decorators import task
from fabric.operations import put, run
from fabric.state import env

env.update({
    'home': '/Users/franhp',
    'containers': '/Users/franhp/containers',
    'uid': '501',  # franhp
    'gid': '20',  # staff
    'mysql_root_pwd': 'empty'
})


@task
def deploy():
    apps()
    setup_nginx()
    docker_compose_yml()
    restart()


@task
def apps():
    mkdir(inside_containers('manager'))
    mkdir(inside_containers('transmission'))
    mkdir(inside_containers('headphones'))
    mkdir(inside_containers('jackett'))