easy_install 6.11 KB
Newer Older
Matt Wright committed
1
#!/usr/bin/python
2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20
# -*- coding: utf-8 -*-

# (c) 2012, Matt Wright <matt@nobien.net>
#
# This file is part of Ansible
#
# Ansible is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ansible is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
#
Matt Wright committed
21

22
import tempfile
23 24
import os.path

25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44
DOCUMENTATION = '''
---
module: easy_install
short_description: Installs Python libraries
description:
     - Installs Python libraries, optionally in a I(virtualenv)
version_added: "0.7"
options:
  name:
    description:
      - A Python library name
    required: true
    default: null
    aliases: []
  virtualenv:
    description:
      - an optional I(virtualenv) directory path to install into. If the
        I(virtualenv) does not exist, it is created automatically
    required: false
    default: null
45
  virtualenv_site_packages:
46
    version_added: "1.1"
47 48 49 50 51 52 53
    description:
      - Whether the virtual environment will inherit packages from the
        global site-packages directory.  Note that if this setting is
        changed on an already existing virtual environment it will not
        have any effect, the environment must be deleted and newly
        created.
    required: false
54 55
    default: "no"
    choices: [ "yes", "no" ]
56
  virtualenv_command:
57
    version_added: "1.1"
58 59 60 61 62
    description:
      - The command to create the virtual environment with. For example
        C(pyvenv), C(virtualenv), C(virtualenv2).
    required: false
    default: virtualenv
63 64 65 66 67 68 69
  executable:
    description:
      - The explicit executable or a pathname to the executable to be used to
        run easy_install for a specific version of Python installed in the
        system. For example C(easy_install-3.3), if there are both Python 2.7
        and 3.3 installations in the system and you want to run easy_install
        for the Python 3.3 installation.
70
    version_added: "1.3"
71 72
    required: false
    default: null
73
notes:
74
    - Please note that the M(easy_install) module can only install Python
75 76 77 78 79 80 81 82 83
      libraries. Thus this module is not able to remove libraries. It is
      generally recommended to use the M(pip) module which you can first install
      using M(easy_install).
    - Also note that I(virtualenv) must be installed on the remote host if the
      C(virtualenv) parameter is specified.
requirements: [ "virtualenv" ]
author: Matt Wright
'''

84 85 86 87
EXAMPLES = '''
# Examples from Ansible Playbooks
- easy_install: name=pip

88 89
# Install Bottle into the specified virtualenv.
- easy_install: name=bottle virtualenv=/webapps/myapp/venv
90 91
'''

92
def _is_package_installed(module, name, easy_install):
93
    cmd = '%s --dry-run %s' % (easy_install, name)
94
    rc, status_stdout, status_stderr = module.run_command(cmd)
Matt Wright committed
95 96 97
    return not ('Reading' in status_stdout or 'Downloading' in status_stdout)


98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123
def _get_easy_install(module, env=None, executable=None):
    candidate_easy_inst_basenames = ['easy_install']
    easy_install = None
    if executable is not None:
        if os.path.isabs(executable):
            easy_install = executable
        else:
            candidate_easy_inst_basenames.insert(0, executable)
    if easy_install is None:
        if env is None:
            opt_dirs = []
        else:
            # Try easy_install with the virtualenv directory first.
            opt_dirs = ['%s/bin' % env]
        for basename in candidate_easy_inst_basenames:
            easy_install = module.get_bin_path(basename, False, opt_dirs)
            if easy_install is not None:
                break
    # easy_install should have been found by now.  The final call to
    # get_bin_path will trigger fail_json.
    if easy_install is None:
        basename = candidate_easy_inst_basenames[0]
        easy_install = module.get_bin_path(basename, True, opt_dirs)
    return easy_install


Matt Wright committed
124 125 126
def main():
    arg_spec = dict(
        name=dict(required=True),
127
        virtualenv=dict(default=None, required=False),
128
        virtualenv_site_packages=dict(default='no', type='bool'),
129
        virtualenv_command=dict(default='virtualenv', required=False),
130
        executable=dict(default='easy_install', required=False),
Matt Wright committed
131 132
    )

133
    module = AnsibleModule(argument_spec=arg_spec, supports_check_mode=True)
Matt Wright committed
134 135

    name = module.params['name']
136
    env = module.params['virtualenv']
137
    executable = module.params['executable']
138
    site_packages = module.params['virtualenv_site_packages']
139
    virtualenv_command = module.params['virtualenv_command']
Matt Wright committed
140 141 142 143 144

    rc = 0
    err = ''
    out = ''

145
    if env:
146
        virtualenv = module.get_bin_path(virtualenv_command, True)
147

148
        if not os.path.exists(os.path.join(env, 'bin', 'activate')):
149 150
            if module.check_mode:
                module.exit_json(changed=True)
151 152 153
            command = '%s %s' % (virtualenv, env)
            if site_packages:
                command += ' --system-site-packages'
154 155
            cwd = tempfile.gettempdir()
            rc_venv, out_venv, err_venv = module.run_command(command, cwd=cwd)
Matt Wright committed
156

157 158 159
            rc += rc_venv
            out += out_venv
            err += err_venv
Matt Wright committed
160

161 162
    easy_install = _get_easy_install(module, env, executable)

Matt Wright committed
163 164
    cmd = None
    changed = False
165
    installed = _is_package_installed(module, name, easy_install)
Matt Wright committed
166 167

    if not installed:
168 169
        if module.check_mode:
            module.exit_json(changed=True)
170
        cmd = '%s %s' % (easy_install, name)
171
        rc_easy_inst, out_easy_inst, err_easy_inst = module.run_command(cmd)
Matt Wright committed
172

173 174 175
        rc += rc_easy_inst
        out += out_easy_inst
        err += err_easy_inst
Matt Wright committed
176 177 178 179 180 181

        changed = True

    if rc != 0:
        module.fail_json(msg=err, cmd=cmd)

182 183
    module.exit_json(changed=changed, binary=easy_install,
                     name=name, virtualenv=env)
Matt Wright committed
184

185
# import module snippets
186
from ansible.module_utils.basic import *
Matt Wright committed
187 188

main()