def fetch_file(self, in_path, out_path):
     ''' save a remote file to the specified path '''
     vvv("FETCH %s TO %s" % (in_path, out_path), host=self.host)
     try:
         self.sftp = self._connect_sftp()
     except Exception, e:
         raise errors.AnsibleError("failed to open a SFTP connection (%s)", e)
Beispiel #2
0
    def fetch_file(self, in_path, out_path):
        ''' fetch a file from zone to local '''

        in_path = self._normalize_path(in_path, self.get_zone_path())
        vvv("FETCH %s TO %s" % (in_path, out_path), host=self.zone)

        self._copy_file(in_path, out_path)
Beispiel #3
0
    def put_file(self, in_path, out_path):
        """ transfer a file from local to remote """
        vvv("PUT %s TO %s" % (in_path, out_path), host=self.host)
        if not os.path.exists(in_path):
            raise errors.AnsibleFileNotFound("file or module does not exist: %s" % in_path)
        cmd = self._password_cmd()

        host = self.host
        if self.ipv6:
            host = "[%s]" % host

        if C.DEFAULT_SCP_IF_SSH:
            cmd += ["scp"] + self.common_args
            cmd += [in_path, host + ":" + pipes.quote(out_path)]
            indata = None
        else:
            cmd += ["sftp"] + self.common_args + [host]
            indata = "put %s %s\n" % (pipes.quote(in_path), pipes.quote(out_path))

        (p, stdin) = self._run(cmd, indata)

        self._send_password()

        (returncode, stdout, stderr) = self._communicate(p, stdin, indata)

        if returncode != 0:
            raise errors.AnsibleError("failed to transfer file to %s:\n%s\n%s" % (out_path, stdout, stderr))
    def fetch_file(self, in_path, out_path):
        vvv("FETCH %s TO %s" % (in_path, out_path), host=self.host)
        cmd = self._password_cmd()

        host = self.host
        if self.ipv6:
            host = '[%s]' % host

        remote_cmd, prompt, success_key = self._su_sudo_cmd(
            self._lxc_cmd('cat %s' % pipes.quote(in_path))
        )

        cmd  = self._password_cmd()
        cmd += ['ssh'] + self.common_args + [host, remote_cmd]

        (p, stdin) = self._run(cmd, True)
        self._send_password()
        if (self.runner.sudo and self.runner.sudo_pass) or \
                (self.runner.su and self.runner.su_pass):
            (no_prompt_out, no_prompt_err) = self.send_su_sudo_password(p, stdin, success_key,
                                                                        True, prompt)

        try:
            outfile = open(out_path, 'w')
        except IOError as e:
            raise errors.AnsibleError('could not open destination file %s: %s' % (out_path, e))

        com = self.FetchCommCB(self.runner, None, su=True, sudoable=True, prompt=prompt, outfile=outfile)
        returncode = self._communicate(p, stdin, callbacks=(com.stdin_cb, com.stdout_cb, com.stderr_cb))
        outfile.close()

        if p.returncode != 0:
            raise errors.AnsibleError("failed to transfer file from %s:\n%s\n%s" % (in_path, com.stdout, com.stderr))
Beispiel #5
0
    def put_file(self, in_path, out_path):
        ''' transfer a file from local to zone '''

        out_path = self._normalize_path(out_path, self.get_zone_path())
        vvv("PUT %s TO %s" % (in_path, out_path), host=self.zone)

        self._copy_file(in_path, out_path)
    def exec_command(self, cmd, tmp_path, sudo_user=None, sudoable=False,
                     executable='/bin/sh', in_data=None, become=None,
                     become_user=None):

        """ Run a command on the local host """

        # Don't currently support su
        # if su or su_user:
        #     raise errors.AnsibleError("Internal Error: this module does not "
        #                               "support running commands via su")

        if in_data:
            raise errors.AnsibleError("Internal Error: this module does not "
                                      "support optimized module pipelining")

        # if sudoable and sudo_user:
        #     raise errors.AnsibleError("Internal Error: this module does not "
        #                               "support running commands via sudo")

        if executable:
            local_cmd = [self.docker_cmd, "exec", self.host, executable,
                         '-c', cmd]
        else:
            local_cmd = '%s exec "%s" %s' % (self.docker_cmd, self.host, cmd)

        vvv("EXEC %s" % (local_cmd), host=self.host)
        p = subprocess.Popen(local_cmd,
                             shell=isinstance(local_cmd, basestring),
                             cwd=self.runner.basedir,
                             stdin=subprocess.PIPE,
                             stdout=subprocess.PIPE, stderr=subprocess.PIPE)

        stdout, stderr = p.communicate()
        return (p.returncode, '', stdout, stderr)
Beispiel #7
0
    def fetch_file(self, in_path, out_path):
        ''' fetch a file from VM to local '''

        if not in_path.startswith(os.path.sep):
            in_path = os.path.join(os.path.sep, in_path)
        normpath = os.path.normpath(in_path)
        in_path = os.path.join("/", normpath[1:])

        vvv("FETCH %s TO %s" % (in_path, out_path), host=self.chroot)
        f = pipes.quote(in_path)
        cmd = self.produce_command("test -f %s && cat %s || exit 7" % (f,f))
        try:
          p = subprocess.Popen(
            cmd,
            stdout = subprocess.PIPE
          )
          out, err = p.communicate("")
          retval = p.wait()
          if retval == 7:
            raise errors.AnsibleFileNotFound("file or module does not exist: %s" % in_path)
          elif retval != 0:
            raise subprocess.CalledProcessError(retval, cmd)
          file(out_path, "wb").write(out)
        except subprocess.CalledProcessError:
            traceback.print_exc()
            raise errors.AnsibleError("failed to transfer file to %s" % out_path)
        except IOError:
            traceback.print_exc()
            raise errors.AnsibleError("failed to transfer file to %s" % out_path)
Beispiel #8
0
    def put_file(self, in_path, out_path):
        ''' transfer a file from local to VM '''

        if not out_path.startswith(os.path.sep):
            out_path = os.path.join(os.path.sep, out_path)
        normpath = os.path.normpath(out_path)
        out_path = os.path.join("/", normpath[1:])

        vvv("PUT %s TO %s" % (in_path, out_path), host=self.chroot)
        if not os.path.exists(in_path):
            raise errors.AnsibleFileNotFound("file or module does not exist: %s" % in_path)
        cmd = self.produce_command("cat > %s" % pipes.quote(out_path))
        try:
          p = subprocess.Popen(
            cmd,
            stdin=subprocess.PIPE,
            stdout=subprocess.PIPE,
            stderr=subprocess.STDOUT,
          )
          out, _ = p.communicate(file(in_path).read())
          retval = p.wait()
          if retval != 0:
            raise QubesRPCError(retval, cmd, out)
        except subprocess.CalledProcessError:
            traceback.print_exc()
            raise errors.AnsibleError("failed to transfer file to %s" % out_path)
Beispiel #9
0
    def put_file(self, in_path, out_path):
        ''' transfer a file from local to remote '''
        vvv("PUT %s TO %s" % (in_path, out_path), host=self.host)
        if not os.path.exists(in_path):
            raise errors.AnsibleFileNotFound("file or module does not exist: %s" % in_path)
        cmd = self._password_cmd()

        host = self.host
        if self.ipv6:
            host = '[%s]' % host

        if C.DEFAULT_SCP_IF_SSH:
            cmd += ["scp"] + self.common_args
            cmd += [in_path,host + ":" + pipes.quote(out_path)]
            indata = None
        else:
            cmd += ["sftp"] + self.common_args + [host]
            indata = "put %s %s\n" % (pipes.quote(in_path), pipes.quote(out_path))

        p = subprocess.Popen(cmd, stdin=subprocess.PIPE,
                             stdout=subprocess.PIPE, stderr=subprocess.PIPE)
        self._send_password()
        stdout, stderr = p.communicate(indata)

        if p.returncode != 0:
            raise errors.AnsibleError("failed to transfer file to %s:\n%s\n%s" % (out_path, stdout, stderr))
Beispiel #10
0
    def connect(self):
        ''' activates the connection object '''

        if not HAVE_PARAMIKO:
            raise errors.AnsibleError("paramiko is not installed")

        user = self.runner.remote_user

        vvv("ESTABLISH CONNECTION FOR USER: %s" % user, host=self.host)

        ssh = paramiko.SSHClient()
        ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())

        allow_agent = True
        if self.runner.remote_pass is not None:
            allow_agent = False
        try:
            ssh.connect(self.host, username=user, allow_agent=allow_agent, look_for_keys=True,
                key_filename=self.runner.private_key_file, password=self.runner.remote_pass,
                timeout=self.runner.timeout, port=self.port)
        except Exception, e:
            msg = str(e)
            if "PID check failed" in msg:
                raise errors.AnsibleError("paramiko version issue, please upgrade paramiko on the machine running ansible")
            elif "Private key file is encrypted" in msg:
                msg = 'ssh %s@%s:%s : %s\nTo connect as a different user, use -u <username>.' % (
                    user, self.host, self.port, msg)
                raise errors.AnsibleConnectionFailed(msg)
            else:
                raise errors.AnsibleConnectionFailed(msg)
Beispiel #11
0
    def put_file(self, in_path, out_path):
        ''' transfer a file from local to chroot '''

        out_path = self._normalize_path(out_path, self.get_jail_path())
        vvv("PUT %s TO %s" % (in_path, out_path), host=self.jail)

        self._copy_file(in_path, out_path)
Beispiel #12
0
    def fetch_file(self, in_path, out_path):
        ''' fetch a file from chroot to local '''

        in_path = self._normalize_path(in_path, self.get_jail_path())
        vvv("FETCH %s TO %s" % (in_path, out_path), host=self.jail)

        self._copy_file(in_path, out_path)
Beispiel #13
0
    def _buffered_exec_command(self, cmd, tmp_path, become_user=None, sudoable=False, executable='/bin/sh', in_data=None, stdin=subprocess.PIPE):
        ''' run a command on the chroot.  This is only needed for implementing
        put_file() get_file() so that we don't have to read the whole file
        into memory.

        compared to exec_command() it looses some niceties like being able to
        return the process's exit code immediately.
        '''

        if sudoable and self.runner.become and self.runner.become_method not in self.become_methods_supported:
            raise errors.AnsibleError("Internal Error: this module does not support running commands via %s" % self.runner.become_method)

        if in_data:
            raise errors.AnsibleError("Internal Error: this module does not support optimized module pipelining")

        # We enter zone as root so we ignore privilege escalation (probably need to fix in case we have to become a specific used [ex: postgres admin])?
        local_cmd = self._generate_cmd(executable, cmd)

        vvv("EXEC %s" % (local_cmd), host=self.chroot)
        p = subprocess.Popen(local_cmd, shell=False,
                             cwd=self.runner.basedir,
                             stdin=stdin,
                             stdout=subprocess.PIPE, stderr=subprocess.PIPE)

        return p
    def put_file(self, in_path, out_path):
        vvv("PUT %s TO %s" % (in_path, out_path), host=self.host)
        if not os.path.exists(in_path):
            raise errors.AnsibleFileNotFound("file or module does not exist: %s" % in_path)

        host = self.host
        if self.ipv6:
            host = '[%s]' % host

        remote_cmd, prompt, success_key = self._su_sudo_cmd(
            self._lxc_cmd('cat > %s; echo -n done' % pipes.quote(out_path))
        )

        cmd  = self._password_cmd()
        cmd += ['ssh'] + self.common_args + [host, remote_cmd]

        (p, stdin) = self._run(cmd, True)
        self._send_password()
        if (self.runner.sudo and self.runner.sudo_pass) or \
                (self.runner.su and self.runner.su_pass):
            (no_prompt_out, no_prompt_err) = self.send_su_sudo_password(p, stdin, success_key,
                                                                        True, prompt)

        com = self.CommunicateCallbacks(self.runner, open(in_path, 'r'),
                                        su=True, sudoable=True, prompt=prompt)
        returncode = self._communicate(p, stdin, callbacks=(com.stdin_cb, com.stdout_cb, com.stderr_cb))

        if com.stdout[-4:] != 'done':
            raise errors.AnsibleError("failed to transfer file to %s" % out_path)

        if returncode != 0:
            raise errors.AnsibleError("failed to transfer file to %s:\n%s\n%s" % (out_path, stdout, stderr))
Beispiel #15
0
 def fetch_file(self, in_path, out_path):
     if _winrm_hacks:
         in_path = _winrm_hacks.fix_slashes(in_path)
     out_path = out_path.replace('\\', '/')
     vvv("FETCH %s TO %s" % (in_path, out_path), host=self.host)
     buffer_size = 2**20 # 1MB chunks
     if not os.path.exists(os.path.dirname(out_path)):
         os.makedirs(os.path.dirname(out_path))
     with open(out_path, 'wb') as out_file:
         offset = 0
         while True:
             try:
                 script = '''
                     $bufferSize = %d;
                     $stream = [System.IO.File]::OpenRead("%s");
                     $stream.Seek(%d, [System.IO.SeekOrigin]::Begin) | Out-Null;
                     $buffer = New-Object Byte[] $bufferSize;
                     $bytesRead = $stream.Read($buffer, 0, $bufferSize);
                     $bytes = $buffer[0..($bytesRead-1)];
                     [System.Convert]::ToBase64String($bytes);
                     $stream.Close() | Out-Null;
                 ''' % (buffer_size, self._winrm_escape(in_path), offset)
                 cmd_parts = self._winrm_get_script_cmd(script)
                 result = self._winrm_exec(cmd_parts[0], cmd_parts[1:])
                 data = base64.b64decode(result.std_out.strip())
                 out_file.write(data)
                 if len(data) < buffer_size:
                     break
                 offset += len(data)
             except Exception: # IOError?
                 traceback.print_exc()
                 raise errors.AnsibleError("failed to transfer file to %s" % out_path)
Beispiel #16
0
    def exec_command(self, cmd, tmp_path, sudo_user, sudoable=False, executable='/bin/sh', in_data=None):
        ''' run a command on the remote host '''

        if in_data:
            raise errors.AnsibleError("Internal Error: this module does not support optimized module pipelining")

        vvv("EXEC COMMAND %s" % cmd)

        if self.runner.sudo and sudoable:
            raise errors.AnsibleError(
                "When using fireball, do not specify sudo to run your tasks. " +
                "Instead sudo the fireball action with sudo. " +
                "Task will communicate with the fireball already running in sudo mode."
            )

        data = dict(
            mode='command',
            cmd=cmd,
            tmp_path=tmp_path,
            executable=executable,
        )
        data = utils.jsonify(data)
        data = utils.encrypt(self.key, data)
        self.socket.send(data)
        
        response = self.socket.recv()
        response = utils.decrypt(self.key, response)
        response = utils.parse_json(response)

        return (response.get('rc',None), '', response.get('stdout',''), response.get('stderr',''))
Beispiel #17
0
    def connect(self):
        ''' connect to the remote host '''

        vvv("ESTABLISH CONNECTION FOR USER: %s" % self.runner.remote_user, host=self.host)

        self.common_args = []
        extra_args = C.ANSIBLE_SSH_ARGS
        if extra_args is not None:
            self.common_args += shlex.split(extra_args)
        else:
            self.common_args += ["-o", "ControlMaster=auto",
                                 "-o", "ControlPersist=60s",
                                 "-o", "ControlPath=/tmp/ansible-ssh-%h-%p-%r"]
        self.common_args += ["-o", "StrictHostKeyChecking=no"]
        if self.port is not None:
            self.common_args += ["-o", "Port=%d" % (self.port)]
        if self.runner.private_key_file is not None:
            self.common_args += ["-o", "IdentityFile="+os.path.expanduser(self.runner.private_key_file)]
        if self.runner.remote_pass:
            self.common_args += ["-o", "GSSAPIAuthentication=no",
                                 "-o", "PubkeyAuthentication=no"]
        else:
            self.common_args += ["-o", "KbdInteractiveAuthentication=no",
                                 "-o", "PasswordAuthentication=no"]
        self.common_args += ["-o", "User="+self.runner.remote_user]

        return self
Beispiel #18
0
    def put_file(self, in_path, out_path):
        vvv("PUT %s TO %s" % (in_path, out_path), host=self.host)
        with open(in_path, 'rb') as fp:
            r = self.session.put(self._build_url('/upload'), data={'dest': out_path}, files={'src': fp})

        if r.status_code != 200:
            raise errors.AnsibleError("failed to transfer file from %s" % in_path)
    def connect(self, allow_ssh=True):
        ''' activates the connection object '''

        try:
            if not self.is_connected:
                tries = 3
                self.conn = socket.socket()
                self.conn.settimeout(constants.ACCELERATE_CONNECT_TIMEOUT)
                vvvv("attempting connection to %s via the accelerated port %d" % (self.host,self.accport))
                while tries > 0:
                    try:
                        self.conn.connect((self.host,self.accport))
                        break
                    except:
                        vvvv("failed, retrying...")
                        time.sleep(0.1)
                        tries -= 1
                if tries == 0:
                    vvv("Could not connect via the accelerated connection, exceeded # of tries")
                    raise errors.AnsibleError("Failed to connect")
                self.conn.settimeout(constants.ACCELERATE_TIMEOUT)
        except:
            if allow_ssh:
                vvv("Falling back to ssh to startup accelerated mode")
                res = self._execute_accelerate_module()
                if not res.is_successful():
                    raise errors.AnsibleError("Failed to launch the accelerated daemon on %s (reason: %s)" % (self.host,res.result.get('msg')))
                return self.connect(allow_ssh=False)
            else:
                raise errors.AnsibleError("Failed to connect to %s:%s" % (self.host,self.accport))
        self.is_connected = True
        return self
    def exec_command(self, cmd, tmp_path, become_user, **kwargs):
        executable = kwargs.get('executable', '/bin/sh')
        sudoable = kwargs.get('sudoable', False)
        if 'su' in kwargs or 'su_user' in kwargs:
            raise errors.AnsibleError("Internal Error: this module does not support running commands via su")

        if kwargs.get('in_data'):
            raise errors.AnsibleError("Internal Error: this module does not support optimized module pipelining")

        if sudoable and getattr(self.runner, 'become', False) and self.runner.become_method not in self.become_methods_supported:
            raise errors.AnsibleError("Internal Error: this module does not support running commands via %s" % self.runner.become_method)

        become = getattr(self.runner, 'become', False) or getattr(self.runner, 'sudo', False)
        remote_cmd = []
        if not become or not sudoable:
            if executable:
                remote_cmd.append(executable + ' -c ' + pipes.quote(cmd))
            else:
                remote_cmd.append(cmd)
        else:
            if hasattr(self.runner, 'become_exe'):
                becomecmd, prompt, success_key = utils.make_become_cmd(cmd, become_user, executable, self.runner.become_method, '', self.runner.become_exe)
            elif hasattr(self.runner, 'sudo_exe'):
                becomecmd, prompt, success_key = utils.make_sudo_cmd(self.runner.sudo_exe, become_user, executable, cmd)
            else:
                becomecmd, prompt, success_key = utils.make_sudo_cmd(become_user, executable, cmd)
            remote_cmd.append(becomecmd)
        remote_cmd = ' '.join(remote_cmd)
        vvv("execnet exec_command %r" % remote_cmd)
        rc, stdout, stderr = self.rpc.exec_command(remote_cmd)
        return (rc, '', stdout, stderr)
Beispiel #21
0
 def put_file(self, in_path, out_path):
     if _winrm_hacks:
         out_path = _winrm_hacks.fix_slashes(out_path)
     vvv("PUT %s TO %s" % (in_path, out_path), host=self.host)
     if not os.path.exists(in_path):
         raise errors.AnsibleFileNotFound("file or module does not exist: %s" % in_path)
     buffer_size = 1024 # FIXME: Find max size or optimize.
     with open(in_path) as in_file:
         in_size = os.path.getsize(in_path)
         for offset in xrange(0, in_size, buffer_size):
             try:
                 out_data = in_file.read(buffer_size)
                 if offset == 0:
                     if out_data.lower().startswith('#!powershell') and not out_path.lower().endswith('.ps1'):
                         out_path = out_path + '.ps1'
                 b64_data = base64.b64encode(out_data)
                 script = '''
                     $bufferSize = %d;
                     $stream = [System.IO.File]::OpenWrite("%s");
                     $stream.Seek(%d, [System.IO.SeekOrigin]::Begin) | Out-Null;
                     $data = "%s";
                     $buffer = [System.Convert]::FromBase64String($data);
                     $stream.Write($buffer, 0, $buffer.length) | Out-Null;
                     $stream.SetLength(%d) | Out-Null;
                     $stream.Close() | Out-Null;
                 ''' % (buffer_size, self._winrm_escape(out_path), offset, b64_data, in_size)
                 cmd_parts = self._winrm_get_script_cmd(script)
                 result = self._winrm_exec(cmd_parts[0], cmd_parts[1:])
                 if result.status_code != 0:
                     raise RuntimeError(result.std_err.encode('utf-8'))
                 script = u''
             except Exception: # IOError?
                 traceback.print_exc()
                 raise errors.AnsibleError("failed to transfer file to %s" % out_path)
    def exec_command(self, cmd, tmp_path, become_user=None, sudoable=False, executable='/bin/sh', in_data=None):
        ''' run a command on the local host '''

        # su requires to be run from a terminal, and therefore isn't supported here (yet?)
        if sudoable and self.runner.become and self.runner.become_method not in self.become_methods_supported:
            raise errors.AnsibleError("Internal Error: this module does not support running commands via %s" % self.runner.become_method)

        if in_data:
            raise errors.AnsibleError("Internal Error: this module does not support optimized module pipelining")

        if self.runner.become and sudoable:
            local_cmd, prompt, success_key = utils.make_become_cmd(cmd, become_user, executable, self.runner.become_method, '-H', self.runner.become_exe)
        else:
            if executable:
                local_cmd = executable.split() + ['-c', cmd]
            else:
                local_cmd = cmd
        executable = executable.split()[0] if executable else None

        vvv("EXEC %s" % (local_cmd), host=self.host)
        p = subprocess.Popen(local_cmd, shell=isinstance(local_cmd, basestring),
                             cwd=self.runner.basedir, executable=executable,
                             stdin=subprocess.PIPE,
                             stdout=subprocess.PIPE, stderr=subprocess.PIPE,
                             env=self.envs)

        if self.runner.become and sudoable and self.runner.become_pass:
            fcntl.fcntl(p.stdout, fcntl.F_SETFL,
                        fcntl.fcntl(p.stdout, fcntl.F_GETFL) | os.O_NONBLOCK)
            fcntl.fcntl(p.stderr, fcntl.F_SETFL,
                        fcntl.fcntl(p.stderr, fcntl.F_GETFL) | os.O_NONBLOCK)
            become_output = ''
            while success_key not in become_output:

                if prompt and become_output.endswith(prompt):
                    break
                if utils.su_prompts.check_su_prompt(become_output):
                    break

                rfd, wfd, efd = select.select([p.stdout, p.stderr], [],
                                              [p.stdout, p.stderr], self.runner.timeout)
                if p.stdout in rfd:
                    chunk = p.stdout.read()
                elif p.stderr in rfd:
                    chunk = p.stderr.read()
                else:
                    stdout, stderr = p.communicate()
                    raise errors.AnsibleError('timeout waiting for %s password prompt:\n' % self.runner.become_method + become_output)
                if not chunk:
                    stdout, stderr = p.communicate()
                    raise errors.AnsibleError('%s output closed while waiting for password prompt:\n' % self.runner.become_method + become_output)
                become_output += chunk
            if success_key not in become_output:
                p.stdin.write(self.runner.become_pass + '\n')
            fcntl.fcntl(p.stdout, fcntl.F_SETFL, fcntl.fcntl(p.stdout, fcntl.F_GETFL) & ~os.O_NONBLOCK)
            fcntl.fcntl(p.stderr, fcntl.F_SETFL, fcntl.fcntl(p.stderr, fcntl.F_GETFL) & ~os.O_NONBLOCK)

        stdout, stderr = p.communicate()
        return (p.returncode, '', stdout, stderr)
Beispiel #23
0
 def connect(self):
     vvv("ESTABLISH CONNECTION FOR USER: %s" % self.user, host=self.host)
     self.session = requests.Session()
     self.session.auth = (self.user, self.password)
     if CERTIFICATE:
         self.session.cert = os.path.expanduser(CERTIFICATE)
     self.session.verify = False
     return self
Beispiel #24
0
 def fetch_file(self, in_path, out_path):
     ''' fetch a file from remote to local '''
     vvv("FETCH %s TO %s" % (in_path, out_path), host=self.host)
     sftp_cmd = ["sftp"] + self.common_args + [self.host]
     p = subprocess.Popen(sftp_cmd, stdin=subprocess.PIPE,
                          stdout=subprocess.PIPE, stderr=subprocess.PIPE)
     stdout, stderr = p.communicate("get %s %s\n" % (in_path, out_path))
     if p.returncode != 0:
         raise errors.AnsibleError("failed to transfer file from %s:\n%s\n%s" % (in_path, stdout, stderr))
 def put_file(self, in_path, out_path):
     ''' transfer a file from local to remote '''
     vvv("PUT %s TO %s" % (in_path, out_path), host=self.host)
     if not os.path.exists(in_path):
         raise errors.AnsibleFileNotFound("file or module does not exist: %s" % in_path)
     try:
         self.sftp = self.ssh.open_sftp()
     except Exception, e:
         raise errors.AnsibleError("failed to open a SFTP connection (%s)" % e)
Beispiel #26
0
 def put_file(self, in_path, out_path):
    local_cmd = ['/usr/sbin/vzctl','exec',self.ctid,'/bin/sh','-c','"','cat > %s' % format(out_path),'"']
    vvv("PUT CMD %s" % (local_cmd), host=self.host)
    vvv("PUT %s %s" % (in_path,out_path), host=self.host)
    p = subprocess.Popen(local_cmd, stdin=subprocess.PIPE,stdout=subprocess.PIPE,stderr=subprocess.PIPE)
    p.stdin.write(open(in_path).read())
    p.stdin.close()
    time.sleep(1)
    p.terminate()
Beispiel #27
0
    def connect(self):
        """ connect to the remote host """

        vvv("ESTABLISH CONNECTION FOR USER: %s" % self.user, host=self.host)

        self.common_args = []
        extra_args = C.ANSIBLE_SSH_ARGS
        if extra_args is not None:
            # make sure there is no empty string added as this can produce weird errors
            self.common_args += [x.strip() for x in shlex.split(extra_args) if x.strip()]
        else:
            self.common_args += [
                "-o",
                "ControlMaster=auto",
                "-o",
                "ControlPersist=60s",
                "-o",
                'ControlPath="%s"' % (C.ANSIBLE_SSH_CONTROL_PATH % dict(directory=self.cp_dir)),
            ]

        cp_in_use = False
        cp_path_set = False
        for arg in self.common_args:
            if "ControlPersist" in arg:
                cp_in_use = True
            if "ControlPath" in arg:
                cp_path_set = True

        if cp_in_use and not cp_path_set:
            self.common_args += ["-o", 'ControlPath="%s"' % (C.ANSIBLE_SSH_CONTROL_PATH % dict(directory=self.cp_dir))]

        if not C.HOST_KEY_CHECKING:
            self.common_args += ["-o", "StrictHostKeyChecking=no"]

        if self.port is not None:
            self.common_args += ["-o", "Port=%d" % (self.port)]
        if self.private_key_file is not None:
            self.common_args += ["-o", 'IdentityFile="%s"' % os.path.expanduser(self.private_key_file)]
        elif self.runner.private_key_file is not None:
            self.common_args += ["-o", 'IdentityFile="%s"' % os.path.expanduser(self.runner.private_key_file)]
        if self.password:
            self.common_args += ["-o", "GSSAPIAuthentication=no", "-o", "PubkeyAuthentication=no"]
        else:
            self.common_args += [
                "-o",
                "KbdInteractiveAuthentication=no",
                "-o",
                "PreferredAuthentications=gssapi-with-mic,gssapi-keyex,hostbased,publickey",
                "-o",
                "PasswordAuthentication=no",
            ]
        if self.user != pwd.getpwuid(os.geteuid())[0]:
            self.common_args += ["-o", "User="******"-o", "ConnectTimeout=%d" % self.runner.timeout]

        return self
Beispiel #28
0
    def exec_command(self, cmd, tmp_path, sudo_user, sudoable=False,
                     executable='/bin/sh', in_data=None):
        ''' run a command on the remote minion '''

        if in_data:
            raise errors.AnsibleError("Internal Error: this module does not support optimized module pipelining")

        vvv("EXEC %s" % (cmd), host=self.host)
        p = self.client.command.run(cmd)[self.host]
        return (p[0], '', p[1], p[2])
Beispiel #29
0
    def exec_command(self, cmd, tmp_path, sudo_user,sudoable=False):
        ''' run a command on the remote host '''

        ssh_cmd = ["ssh", "-tt", "-q"] + self.common_args + [self.host]
        if self.runner.sudo and sudoable:
            # Rather than detect if sudo wants a password this time, -k makes
            # sudo always ask for a password if one is required.
            # Passing a quoted compound command to sudo (or sudo -s)
            # directly doesn't work, so we shellquote it with pipes.quote()
            # and pass the quoted string to the user's shell.  We loop reading
            # output until we see the randomly-generated sudo prompt set with
            # the -p option.
            randbits = ''.join(chr(random.randint(ord('a'), ord('z'))) for x in xrange(32))
            prompt = '[sudo via ansible, key=%s] password: '******'sudo -k && sudo -p "%s" -u %s "$SHELL" -c %s' % (
                prompt, sudo_user, pipes.quote(cmd))
            sudo_output = ''
            ssh_cmd.append(sudocmd)
            vvv("EXEC %s" % ssh_cmd, host=self.host)
            p = subprocess.Popen(ssh_cmd, stdin=subprocess.PIPE,
                                 stdout=subprocess.PIPE, stderr=subprocess.STDOUT)
            if self.runner.sudo_pass:
                fcntl.fcntl(p.stdout, fcntl.F_SETFL,
                            fcntl.fcntl(p.stdout, fcntl.F_GETFL) | os.O_NONBLOCK)
                while not sudo_output.endswith(prompt):
                    rfd, wfd, efd = select.select([p.stdout], [],
                                                  [p.stdout], self.runner.timeout)
                    if p.stdout in rfd:
                        chunk = p.stdout.read()
                        if not chunk:
                            raise errors.AnsibleError('ssh connection closed waiting for sudo password prompt')
                        sudo_output += chunk
                    else:
                        stdout = p.communicate()
                        raise errors.AnsibleError('ssh connection error waiting for sudo password prompt')
                p.stdin.write(self.runner.sudo_pass + '\n')
                fcntl.fcntl(p.stdout, fcntl.F_SETFL, fcntl.fcntl(p.stdout, fcntl.F_GETFL) & ~os.O_NONBLOCK)
        else:
            ssh_cmd.append(cmd)
            vvv("EXEC %s" % ssh_cmd, host=self.host)
            p = subprocess.Popen(ssh_cmd, stdin=subprocess.PIPE,
                                 stdout=subprocess.PIPE, stderr=subprocess.STDOUT)

        # We can't use p.communicate here because the ControlMaster may have stdout open as well
        stdout = ''
        while p.poll() is None:
            rfd, wfd, efd = select.select([p.stdout], [], [p.stdout], 1)
            if p.stdout in rfd:
                stdout += os.read(p.stdout.fileno(), 1024)
        p.stdin.close()  # close stdin after we read from stdout (see also issue #848)

        if p.returncode != 0 and stdout.find('Bad configuration option: ControlPersist') != -1:
            raise errors.AnsibleError('using -c ssh on certain older ssh versions may not support ControlPersist, set ANSIBLE_SSH_ARGS="" (or ssh_args in the config file) before running again')

        return ('', stdout, '')
Beispiel #30
0
    def _connect_uncached(self):
        ''' activates the connection object '''

        if not HAVE_PARAMIKO:
            raise errors.AnsibleError("paramiko is not installed")

        vvv("ESTABLISH CONNECTION FOR USER: %s on PORT %s TO %s" %
            (self.user, self.port, self.host),
            host=self.host)

        ssh = paramiko.SSHClient()

        self.keyfile = os.path.expanduser("~/.ssh/known_hosts")

        if C.HOST_KEY_CHECKING:
            ssh.load_system_host_keys()

        ssh.set_missing_host_key_policy(MyAddPolicy(self.runner))

        allow_agent = True

        if self.password is not None:
            allow_agent = False

        try:

            if self.private_key_file:
                key_filename = os.path.expanduser(self.private_key_file)
            elif self.runner.private_key_file:
                key_filename = os.path.expanduser(self.runner.private_key_file)
            else:
                key_filename = None
            ssh.connect(self.host,
                        username=self.user,
                        allow_agent=allow_agent,
                        look_for_keys=True,
                        key_filename=key_filename,
                        password=self.password,
                        timeout=self.runner.timeout,
                        port=self.port)

        except Exception, e:

            msg = str(e)
            if "PID check failed" in msg:
                raise errors.AnsibleError(
                    "paramiko version issue, please upgrade paramiko on the machine running ansible"
                )
            elif "Private key file is encrypted" in msg:
                msg = 'ssh %s@%s:%s : %s\nTo connect as a different user, use -u <username>.' % (
                    self.user, self.host, self.port, msg)
                raise errors.AnsibleConnectionFailed(msg)
            else:
                raise errors.AnsibleConnectionFailed(msg)
Beispiel #31
0
 def put_file(self, in_path, out_path):
     ''' transfer a file from local to remote '''
     vvv("PUT %s TO %s" % (in_path, out_path), host=self.host)
     if not os.path.exists(in_path):
         raise errors.AnsibleFileNotFound(
             "file or module does not exist: %s" % in_path)
     try:
         self.sftp = self.ssh.open_sftp()
     except Exception, e:
         raise errors.AnsibleError("failed to open a SFTP connection (%s)" %
                                   e)
Beispiel #32
0
    def exec_command(self, cmd, tmp_path, become_user=None, sudoable=False, executable='/bin/sh', in_data=None):
        if in_data:
            raise errors.AnsibleError('Internal Error: this modules does not support optimized module pipelining')
       
        if executable:
            local_cmd = executable.split() + ['-c', cmd]
        else:
            local_cmd = cmd
        executable = executable.split()[0] if executable else None

        pipe_to_server = os.pipe()
        pipe_from_server = os.pipe()

        # os.environ is special, so we copy it into a dictionary and modify the dictionary instead
        env = dict()
        for key in os.environ.keys():
            env[key] = os.environ[key]
        env['SNMP_PIPE_IN'] = str(pipe_from_server[0])
        env['SNMP_PIPE_OUT'] = str(pipe_to_server[1])

        if 'PYTHONPATH' in env:
            env['PYTHONPATH'] = os.path.dirname(__file__) + ':' + env['PYTHONPATH']
        else:
            env['PYTHONPATH'] = os.path.dirname(__file__)

        vvv('EXEC %s' % (local_cmd), host=self.host)
        p = subprocess.Popen(local_cmd,
                             shell=isinstance(local_cmd, basestring),
                             cwd=self.runner.basedir,
                             executable=executable,
                             stdin=subprocess.PIPE,
                             stdout=subprocess.PIPE,
                             stderr=subprocess.PIPE,
                             env=env)

        # pysnmp insist on using its own socket map, so we use that instead
        conn = self._get_snmp_connection()
        sock_map = conn.dispatcher.getSocketMap()
        stdout = _BufferedDispatcher(asyncore.file_wrapper(p.stdout.fileno()), map=sock_map)
        stderr = _BufferedDispatcher(asyncore.file_wrapper(p.stderr.fileno()), map=sock_map)
        server = _Server(conn, pipe_to_server[0], pipe_from_server[1], map=sock_map)

        while stdout.readable() or stderr.readable():
            asyncore.poll(0.5, map=sock_map)
            conn.dispatcher.handleTimerTick(time.time())

        p.wait()

        os.close(pipe_to_server[0])
        os.close(pipe_to_server[1])
        os.close(pipe_from_server[0])
        os.close(pipe_from_server[1])
        
        return (p.returncode, '', stdout.data, stderr.data)
 def put_file(self, in_path, out_path):
     ''' transfer a file from local to local '''
     out_path = os.path.join(self.chroot, out_path.lstrip('/'))
     vvv("PUT %s TO %s" % (in_path, out_path), host=self.host)
     if not os.path.exists(in_path):
         raise errors.AnsibleFileNotFound(
             "file or module does not exist: %s" % in_path)
     try:
         self._exec_command('cp {} {}'.format(in_path, out_path))
     except Exception:
         traceback.print_exc()
         raise errors.AnsibleError("Some exceptions occurred.")
 def fetch_file(self, in_path, out_path):
     ''' fetch a file from local to local -- for copatibility '''
     in_path = os.path.join(self.chroot, in_path.lstrip('/'))
     vvv("FETCH %s TO %s" % (in_path, out_path), host=self.host)
     if not os.path.exists(out_path):
         raise errors.AnsibleFileNotFound(
             "file or module does not exist: %s" % out_path)
     try:
         self._exec_command('cp {} {}'.format(in_path, out_path))
     except Exception:
         traceback.print_exc()
         raise errors.AnsibleError("Some exceptions occurred.")
Beispiel #35
0
 def fetch_file(self, in_path, out_path):
     ''' save a remote file to the specified path '''
     vvv("FETCH %s TO %s" % (in_path, out_path), host=self.host)
     try:
         sftp = self.ssh.open_sftp()
     except:
         raise errors.AnsibleError("failed to open a SFTP connection")
     try:
         sftp.get(in_path, out_path)
     except IOError:
         raise errors.AnsibleError("failed to transfer file from %s" % in_path)
     sftp.close()
Beispiel #36
0
    def put_file(self, in_path, out_path):
        ''' transfer a file from local to remote '''
        vvv("PUT %s TO %s" % (in_path, out_path), host=self.host)

        if not os.path.exists(in_path):
            raise errors.AnsibleFileNotFound(
                "file or module does not exist: %s" % in_path)

        fd = file(in_path, 'rb')
        fstat = os.stat(in_path)
        try:
            vvv("PUT file is %d bytes" % fstat.st_size)
            while fd.tell() < fstat.st_size:
                data = fd.read(CHUNK_SIZE)
                last = False
                if fd.tell() >= fstat.st_size:
                    last = True
                data = dict(mode='put',
                            data=base64.b64encode(data),
                            out_path=out_path,
                            last=last)
                if self.runner.sudo:
                    data['user'] = self.runner.sudo_user
                data = utils.jsonify(data)
                data = utils.encrypt(self.key, data)

                if self.send_data(data):
                    raise errors.AnsibleError("failed to send the file to %s" %
                                              self.host)

                response = self.recv_data()
                if not response:
                    raise errors.AnsibleError(
                        "Failed to get a response from %s" % self.host)
                response = utils.decrypt(self.key, response)
                response = utils.parse_json(response)

                if response.get('failed', False):
                    raise errors.AnsibleError(
                        "failed to put the file in the requested location")
        finally:
            fd.close()
            response = self.recv_data()
            if not response:
                raise errors.AnsibleError("Failed to get a response from %s" %
                                          self.host)
            response = utils.decrypt(self.key, response)
            response = utils.parse_json(response)

            if response.get('failed', False):
                raise errors.AnsibleError(
                    "failed to put the file in the requested location")
Beispiel #37
0
    def fetch_file(self, in_path, out_path):
        ''' fetch a file from remote to local '''

        in_path = self._normalize_path(in_path, '/')
        vvv("FETCH %s TO %s" % (in_path, out_path), host=self.host)
        # need to use a tmp dir due to difference of semantic for getfile
        # ( who take a # directory as destination) and fetch_file, who
        # take a file directly
        tmpdir = tempfile.mkdtemp(prefix="func_ansible")
        self.client.local.getfile.get(in_path, tmpdir)
        shutil.move(os.path.join(tmpdir, self.host, os.path.basename(in_path)),
                    out_path)
        shutil.rmtree(tmpdir)
Beispiel #38
0
 def fetch_file(self, in_path, out_path):
     ''' fetch a file from remote to local '''
     vvv("FETCH %s TO %s" % (in_path, out_path), host=self.host)
     sftp_cmd = ["sftp"] + self.common_args + [self.host]
     p = subprocess.Popen(sftp_cmd,
                          stdin=subprocess.PIPE,
                          stdout=subprocess.PIPE,
                          stderr=subprocess.PIPE)
     stdout, stderr = p.communicate("get %s %s\n" % (in_path, out_path))
     if p.returncode != 0:
         raise errors.AnsibleError(
             "failed to transfer file from %s:\n%s\n%s" %
             (in_path, stdout, stderr))
Beispiel #39
0
    def put_file(self, in_path, out_path):
        ''' transfer a file from local to lxc '''

        out_path = self._normalize_path(out_path, '/')
        vvv("PUT %s TO %s" % (in_path, out_path), host=self.lxc)
        
        local_cmd = [self.cmd, '-q', '-c', 'lxc:///', 'lxc-enter-namespace', self.lxc, '--', '/bin/tee', out_path]
        vvv("EXEC %s" % (local_cmd), host=self.lxc)

        p = subprocess.Popen(local_cmd, cwd=self.runner.basedir,
                             stdin=subprocess.PIPE,
                             stdout=subprocess.PIPE, stderr=subprocess.PIPE) 
        stdout, stderr = p.communicate(open(in_path,'rb').read())
Beispiel #40
0
    def exec_command(self, cmd, tmp_path, sudo_user=None, sudoable=False, executable='/bin/sh', in_data=None, su=None, su_user=None):
        ''' run a command on the local host '''

        # su requires to be run from a terminal, and therefore isn't supported here (yet?)
        if su or su_user:
            raise errors.AnsibleError("Internal Error: this module does not support running commands via su")

        if in_data:
            raise errors.AnsibleError("Internal Error: this module does not support optimized module pipelining")

        if not self.runner.sudo or not sudoable:
            if executable:
                local_cmd = [executable, '-c', cmd]
            else:
                local_cmd = cmd
        else:
            local_cmd, prompt, success_key = utils.make_sudo_cmd(sudo_user, executable, cmd)

        vvv("EXEC %s" % (local_cmd), host=self.host)
        p = subprocess.Popen(local_cmd, shell=isinstance(local_cmd, basestring),
                             cwd=self.runner.basedir, executable=executable or None,
                             stdin=subprocess.PIPE,
                             stdout=subprocess.PIPE, stderr=subprocess.PIPE)

        if self.runner.sudo and sudoable and self.runner.sudo_pass:
            fcntl.fcntl(p.stdout, fcntl.F_SETFL,
                        fcntl.fcntl(p.stdout, fcntl.F_GETFL) | os.O_NONBLOCK)
            fcntl.fcntl(p.stderr, fcntl.F_SETFL,
                        fcntl.fcntl(p.stderr, fcntl.F_GETFL) | os.O_NONBLOCK)
            sudo_output = ''
            while not sudo_output.endswith(prompt) and success_key not in sudo_output:
                rfd, wfd, efd = select.select([p.stdout, p.stderr], [],
                                              [p.stdout, p.stderr], self.runner.timeout)
                if p.stdout in rfd:
                    chunk = p.stdout.read()
                elif p.stderr in rfd:
                    chunk = p.stderr.read()
                else:
                    stdout, stderr = p.communicate()
                    raise errors.AnsibleError('timeout waiting for sudo password prompt:\n' + sudo_output)
                if not chunk:
                    stdout, stderr = p.communicate()
                    raise errors.AnsibleError('sudo output closed while waiting for password prompt:\n' + sudo_output)
                sudo_output += chunk
            if success_key not in sudo_output:
                p.stdin.write(self.runner.sudo_pass + '\n')
            fcntl.fcntl(p.stdout, fcntl.F_SETFL, fcntl.fcntl(p.stdout, fcntl.F_GETFL) & ~os.O_NONBLOCK)
            fcntl.fcntl(p.stderr, fcntl.F_SETFL, fcntl.fcntl(p.stderr, fcntl.F_GETFL) & ~os.O_NONBLOCK)

        stdout, stderr = p.communicate()
        return (p.returncode, '', stdout, stderr)
Beispiel #41
0
    def exec_command(self, cmd, tmp_path, sudo_user, sudoable=False, executable='/bin/sh'):
        ''' run a command on the chroot '''

        # We enter lxc as root so sudo stuff can be ignored
        local_cmd = self._generate_cmd(executable, cmd)

        vvv("EXEC %s" % (local_cmd), host=self.lxc)
        p = subprocess.Popen(local_cmd, shell=isinstance(local_cmd, basestring),
                             cwd=self.runner.basedir,
                             stdin=subprocess.PIPE,
                             stdout=subprocess.PIPE, stderr=subprocess.PIPE)

        stdout, stderr = p.communicate()
        return (p.returncode, '', stdout, stderr)
Beispiel #42
0
    def fetch_file(self, in_path, out_path):
        ''' fetch a file from lxc to local '''

        in_path = self._normalize_path(in_path, '/')
        vvv("FETCH %s TO %s" % (in_path, out_path), host=self.lxc)

        local_cmd = [self.cmd, '-q', '-c', 'lxc:///', 'lxc-enter-namespace', self.lxc, '--', '/bin/cat', in_path]
        vvv("EXEC %s" % (local_cmd), host=self.lxc)

        p = subprocess.Popen(local_cmd, cwd=self.runner.basedir,
                             stdin=subprocess.PIPE,
                             stdout=subprocess.PIPE, stderr=subprocess.PIPE)
        stdout, stderr = p.communicate()
        open(out_path,'wb').write(stdout)
Beispiel #43
0
    def _connect_uncached(self):
        ''' activates the connection object '''

        if not HAVE_PARAMIKO:
            raise errors.AnsibleError("paramiko is not installed")

        user = self.runner.remote_user

        vvv("ESTABLISH CONNECTION FOR USER: %s on PORT %s TO %s" %
            (user, self.port, self.host),
            host=self.host)

        ssh = paramiko.SSHClient()
        ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())

        allow_agent = True
        if self.runner.remote_pass is not None:
            allow_agent = False
        try:
            private_key = None
            key_filename = None

            if self.runner.private_key:
                private_key = paramiko.RSAKey.from_private_key(
                    StringIO.StringIO(self.runner.private_key))

            if self.runner.private_key_file:
                key_filename = os.path.expanduser(self.runner.private_key_file)

            ssh.connect(self.host,
                        username=user,
                        allow_agent=allow_agent,
                        look_for_keys=True,
                        key_filename=key_filename,
                        pkey=private_key,
                        password=self.runner.remote_pass,
                        timeout=self.runner.timeout,
                        port=self.port)
        except Exception, e:
            msg = str(e)
            if "PID check failed" in msg:
                raise errors.AnsibleError(
                    "paramiko version issue, please upgrade paramiko on the machine running ansible"
                )
            elif "Private key file is encrypted" in msg:
                msg = 'ssh %s@%s:%s : %s\nTo connect as a different user, use -u <username>.' % (
                    user, self.host, self.port, msg)
                raise errors.AnsibleConnectionFailed(msg)
            else:
                raise errors.AnsibleConnectionFailed(msg)
Beispiel #44
0
    def __init__(self, runner, host, port, *args, **kwargs):
        self.host = host
        self.runner = runner
        self.has_pipelining = False
        if os.geteuid() != 0:
            raise errors.AnsibleError(
                "openvz connection requires running as root")

        if not self.host in self.list_containers():
            raise errors.AnsibleError("No such container: %s" % self.host)

        self.ctid = self.get_ctid()
        vvv("CTID: " + self.ctid, host=self.host)
        pass
Beispiel #45
0
    def put_file(self, in_path, out_path):
        ''' transfer a file from local to local '''

        vvv("PUT %s TO %s" % (in_path, out_path), host=self.host)
        if not os.path.exists(in_path):
            raise errors.AnsibleFileNotFound("file or module does not exist: %s" % in_path)
        try:
            shutil.copyfile(in_path, out_path)
        except shutil.Error:
            traceback.print_exc()
            raise errors.AnsibleError("failed to copy: %s and %s are the same" % (in_path, out_path))
        except IOError:
            traceback.print_exc()
            raise errors.AnsibleError("failed to transfer file to %s" % out_path)
Beispiel #46
0
    def exec_command(self,
                     cmd,
                     tmp_path,
                     sudo_user,
                     sudoable=False,
                     executable='/bin/sh'):
        ''' run a command on the remote host '''

        if executable == "":
            executable = constants.DEFAULT_EXECUTABLE

        if self.runner.sudo and sudoable and sudo_user:
            cmd, prompt, success_key = utils.make_sudo_cmd(
                sudo_user, executable, cmd)

        vvv("EXEC COMMAND %s" % cmd)

        data = dict(
            mode='command',
            cmd=cmd,
            tmp_path=tmp_path,
            executable=executable,
        )
        data = utils.jsonify(data)
        data = utils.encrypt(self.key, data)
        if self.send_data(data):
            raise errors.AnsibleError("Failed to send command to %s" %
                                      self.host)

        while True:
            # we loop here while waiting for the response, because a
            # long running command may cause us to receive keepalive packets
            # ({"pong":"true"}) rather than the response we want.
            response = self.recv_data()
            if not response:
                raise errors.AnsibleError("Failed to get a response from %s" %
                                          self.host)
            response = utils.decrypt(self.key, response)
            response = utils.parse_json(response)
            if "pong" in response:
                # it's a keepalive, go back to waiting
                vvvv("%s: received a keepalive packet" % self.host)
                continue
            else:
                vvvv("%s: received the response" % self.host)
                break

        return (response.get('rc', None), '', response.get('stdout', ''),
                response.get('stderr', ''))
Beispiel #47
0
 def _winrm_connect(self):
     '''
     Establish a WinRM connection over HTTP/HTTPS.
     '''
     port = self.port or 5986
     vvv("ESTABLISH WINRM CONNECTION FOR USER: %s on PORT %s TO %s" % \
         (self.user, port, self.host), host=self.host)
     netloc = '%s:%d' % (self.host, port)
     cache_key = '%s:%s@%s:%d' % (self.user, hashlib.md5(
         self.password).hexdigest(), self.host, port)
     if cache_key in _winrm_cache:
         vvvv('WINRM REUSE EXISTING CONNECTION: %s' % cache_key,
              host=self.host)
         return _winrm_cache[cache_key]
     transport_schemes = [('plaintext', 'https'),
                          ('plaintext', 'http')]  # FIXME: ssl/kerberos
     if port == 5985:
         transport_schemes = reversed(transport_schemes)
     exc = None
     for transport, scheme in transport_schemes:
         endpoint = urlparse.urlunsplit((scheme, netloc, '/wsman', '', ''))
         vvvv('WINRM CONNECT: transport=%s endpoint=%s' %
              (transport, endpoint),
              host=self.host)
         protocol = Protocol(endpoint,
                             transport=transport,
                             username=self.user,
                             password=self.password)
         try:
             protocol.send_message('')
             _winrm_cache[cache_key] = protocol
             return protocol
         except WinRMTransportError, exc:
             err_msg = str(exc.args[0])
             if re.search(r'Operation\s+?timed\s+?out', err_msg, re.I):
                 raise errors.AnsibleError(
                     "the connection attempt timed out")
             m = re.search(r'Code\s+?(\d{3})', err_msg)
             if m:
                 code = int(m.groups()[0])
                 if code == 401:
                     raise errors.AnsibleError(
                         "the username/password specified for this server was incorrect"
                     )
                 elif code == 411:
                     _winrm_cache[cache_key] = protocol
                     return protocol
             vvvv('WINRM CONNECTION ERROR: %s' % err_msg, host=self.host)
             continue
Beispiel #48
0
    def fetch_file(self, in_path, out_path):
        ''' fetch a file from docker to local '''

        in_path = self._normalize_path(in_path, '/')
        vvv("FETCH %s TO %s" % (in_path, out_path), host=self.docker_id)

        local_cmd = [self.cmd, 'cp', self.docker_id, ':', in_path, out_path]
        vvv("EXEC %s" % (local_cmd), host=self.docker_id)

        p = subprocess.Popen(local_cmd,
                             cwd=self.runner.basedir,
                             stdin=subprocess.PIPE,
                             stdout=subprocess.PIPE,
                             stderr=subprocess.PIPE)
        stdout, stderr = p.communicate()
Beispiel #49
0
 def put_file(self, in_path, out_path):
     local_cmd = [
         '/usr/sbin/vzctl', 'exec', self.ctid, '/bin/sh', '-c', '"',
         'cat > %s' % format(out_path), '"'
     ]
     vvv("PUT CMD %s" % (local_cmd), host=self.host)
     vvv("PUT %s %s" % (in_path, out_path), host=self.host)
     p = subprocess.Popen(local_cmd,
                          stdin=subprocess.PIPE,
                          stdout=subprocess.PIPE,
                          stderr=subprocess.PIPE)
     p.stdin.write(open(in_path).read())
     p.stdin.close()
     time.sleep(1)
     p.terminate()
Beispiel #50
0
    def handle_module_result(self, result, changed_if=None, failed_if=None):
        changed = result.get("changed", False)
        failed = result.get("failed", False)
        msg = result.get("msg", result.get("stderr", ""))

        vvv("result: failed={} changed={} msg={}".format(
            failed,
            changed,
            msg,
        ))

        if changed:
            self.changed = True
        if failed:
            raise ModuleError(msg)
        return result
Beispiel #51
0
 def put_file(self, in_path, out_path):
     ''' transfer a file from local to remote '''
     vvv("PUT %s TO %s" % (in_path, out_path), host=self.host)
     if not os.path.exists(in_path):
         raise errors.AnsibleFileNotFound(
             "file or module does not exist: %s" % in_path)
     sftp_cmd = ["sftp"] + self.common_args + [self.host]
     p = subprocess.Popen(sftp_cmd,
                          stdin=subprocess.PIPE,
                          stdout=subprocess.PIPE,
                          stderr=subprocess.PIPE)
     stdout, stderr = p.communicate("put %s %s\n" % (in_path, out_path))
     if p.returncode != 0:
         raise errors.AnsibleError(
             "failed to transfer file to %s:\n%s\n%s" %
             (out_path, stdout, stderr))
    def fetch_file(self, in_path, out_path):
        """ Fetch a file from container to local. """
        # out_path is the final file path, but docker takes a directory, not a
        # file path
        out_dir = os.path.dirname(out_path)
        args = [self.docker_cmd, "cp", "%s:%s" % (self.host, in_path), out_dir]

        vvv("FETCH %s TO %s" % (in_path, out_path), host=self.host)
        p = subprocess.Popen(args, stdin=subprocess.PIPE,
                             stdout=subprocess.PIPE, stderr=subprocess.PIPE)
        p.communicate()

        # Rename if needed
        actual_out_path = os.path.join(out_dir, os.path.basename(in_path))
        if actual_out_path != out_path:
            os.rename(actual_out_path, out_path)
Beispiel #53
0
    def put_file(self, in_path, out_path):
        ''' transfer a file from local to the namespace '''

        out_path = self._normalize_path(out_path, '/')
        vvv("PUT %s TO %s" % (in_path, out_path), host=self.docker_id)

        # cat localfile | docker exec -i  data sh -c 'cat > containerfile'
        local_cmd = [self.cmd, 'exec', '-i', self.docker_id, 'tee', out_path]
        vvv("EXEC %s" % (local_cmd), host=self.docker_id)

        p = subprocess.Popen(local_cmd,
                             cwd=self.runner.basedir,
                             stdin=subprocess.PIPE,
                             stdout=subprocess.PIPE,
                             stderr=subprocess.PIPE)
        stdout, stderr = p.communicate(open(in_path, 'rb').read())
Beispiel #54
0
    def connect(self):
        ''' activates the connection object '''

        if not HAVE_PARAMIKO:
            raise errors.AnsibleError("paramiko is not installed")

        user = self.runner.remote_user

        vvv("ESTABLISH CONNECTION FOR USER: %s" % user, host=self.host)



        #SSHConfig() checks
        config = SSHConfig()
        home_directory = os.getenv('HOME')
        config.parse(open(os.path.join(home_directory, '.ssh/config')))
        o = config.lookup(self.host)

        if o.has_key('port'):
            self.port = int(o['port'])
        if o.has_key('hostname'):
            self.host = o['hostname']
        if o.has_key('user'):
            user = o['user']


        #print user,self.host
        ssh = paramiko.SSHClient()
        ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())

        allow_agent = True
        if self.runner.remote_pass is not None:
            allow_agent = False
        try:
            ssh.connect(self.host, username=user, allow_agent=allow_agent, look_for_keys=True,
                key_filename=self.runner.private_key_file, password=self.runner.remote_pass,
                timeout=self.runner.timeout, port=self.port)
        except Exception, e:
            msg = str(e)
            if "PID check failed" in msg:
                raise errors.AnsibleError("paramiko version issue, please upgrade paramiko on the machine running ansible")
            elif "Private key file is encrypted" in msg:
                msg = 'ssh %s@%s:%s : %s\nTo connect as a different user, use -u <username>.' % (
                    user, self.host, self.port, msg)
                raise errors.AnsibleConnectionFailed(msg)
            else:
                raise errors.AnsibleConnectionFailed(msg)
    def connect(self):
        ''' connect to the remote host '''

        vvv("ESTABLISH CONNECTION FOR USER: %s" % self.user, host=self.host)

        self.common_args = []
        extra_args = C.ANSIBLE_SSH_ARGS
        if extra_args is not None:
            # make sure there is no empty string added as this can produce weird errors
            self.common_args += [x.strip() for x in shlex.split(extra_args) if x.strip()]
        else:
            self.common_args += ["-o", "ControlMaster=auto",
                                 "-o", "ControlPersist=60s",
                                 "-o", "ControlPath=\"%s\"" % (C.ANSIBLE_SSH_CONTROL_PATH % dict(directory=self.cp_dir))]

        cp_in_use = False
        cp_path_set = False
        for arg in self.common_args:
            if "ControlPersist" in arg:
                cp_in_use = True
            if "ControlPath" in arg:
                cp_path_set = True

        if cp_in_use and not cp_path_set:
            self.common_args += ["-o", "ControlPath=\"%s\"" % (C.ANSIBLE_SSH_CONTROL_PATH % dict(directory=self.cp_dir))]

        if not C.HOST_KEY_CHECKING:
            self.common_args += ["-o", "StrictHostKeyChecking=no"]

        if self.port is not None:
            self.common_args += ["-o", "Port=%d" % (self.port)]
        if self.private_key_file is not None:
            self.common_args += ["-o", "IdentityFile=\"%s\"" % os.path.expanduser(self.private_key_file)]
        elif self.runner.private_key_file is not None:
            self.common_args += ["-o", "IdentityFile=\"%s\"" % os.path.expanduser(self.runner.private_key_file)]
        if self.password:
            self.common_args += ["-o", "GSSAPIAuthentication=no",
                                 "-o", "PubkeyAuthentication=no"]
        else:
            self.common_args += ["-o", "KbdInteractiveAuthentication=no",
                                 "-o", "PreferredAuthentications=gssapi-with-mic,gssapi-keyex,hostbased,publickey",
                                 "-o", "PasswordAuthentication=no"]
        if self.user != pwd.getpwuid(os.geteuid())[0]:
            self.common_args += ["-o", "User="******"-o", "ConnectTimeout=%d" % self.runner.timeout]

        return self
Beispiel #56
0
    def not_in_host_file(self, host):
        if 'USER' in os.environ:
            user_host_file = os.path.expandvars("~${USER}/.ssh/known_hosts")
        else:
            user_host_file = "~/.ssh/known_hosts"
        user_host_file = os.path.expanduser(user_host_file)

        host_file_list = []
        host_file_list.append(user_host_file)
        host_file_list.append("/etc/ssh/ssh_known_hosts")
        host_file_list.append("/etc/ssh/ssh_known_hosts2")

        hfiles_not_found = 0
        for hf in host_file_list:
            if not os.path.exists(hf):
                hfiles_not_found += 1
                continue
            host_fh = open(hf)
            data = host_fh.read()
            host_fh.close()
            for line in data.split("\n"):
                if line is None or " " not in line:
                    continue
                tokens = line.split()
                if tokens[0].find(self.HASHED_KEY_MAGIC) == 0:
                    # this is a hashed known host entry
                    try:
                        (kn_salt, kn_host
                         ) = tokens[0][len(self.HASHED_KEY_MAGIC):].split(
                             "|", 2)
                        hash = hmac.new(kn_salt.decode('base64'),
                                        digestmod=sha1)
                        hash.update(host)
                        if hash.digest() == kn_host.decode('base64'):
                            return False
                    except:
                        # invalid hashed host key, skip it
                        continue
                else:
                    # standard host file entry
                    if host in tokens[0]:
                        return False

        if (hfiles_not_found == len(host_file_list)):
            vvv("EXEC previous known host file not found for %s" % host)
        return True
Beispiel #57
0
 def _winrm_connect(self):
     '''
     Establish a WinRM connection over HTTP/HTTPS.
     '''
     port = self.port or 5986
     vvv("ESTABLISH WINRM CONNECTION FOR USER: %s on PORT %s TO %s" % \
         (self.user, port, self.host), host=self.host)
     netloc = '%s:%d' % (self.host, port)
     exc = None
     for transport, scheme in self.transport_schemes['http' if port ==
                                                     5985 else 'https']:
         if transport == 'kerberos' and (not HAVE_KERBEROS
                                         or not '@' in self.user):
             continue
         if transport == 'kerberos':
             realm = self.user.split('@', 1)[1].strip() or None
         else:
             realm = None
         endpoint = urlparse.urlunsplit((scheme, netloc, '/wsman', '', ''))
         vvvv('WINRM CONNECT: transport=%s endpoint=%s' %
              (transport, endpoint),
              host=self.host)
         protocol = Protocol(endpoint,
                             transport=transport,
                             username=self.user,
                             password=self.password,
                             realm=realm)
         try:
             protocol.send_message('')
             return protocol
         except WinRMTransportError, exc:
             err_msg = str(exc)
             if re.search(r'Operation\s+?timed\s+?out', err_msg, re.I):
                 raise errors.AnsibleError(
                     "the connection attempt timed out")
             m = re.search(r'Code\s+?(\d{3})', err_msg)
             if m:
                 code = int(m.groups()[0])
                 if code == 401:
                     raise errors.AnsibleError(
                         "the username/password specified for this server was incorrect"
                     )
                 elif code == 411:
                     return protocol
             vvvv('WINRM CONNECTION ERROR: %s' % err_msg, host=self.host)
             continue
Beispiel #58
0
    def put_file(self, in_path, out_path):
        ''' transfer a file from local to remote '''
        vvv("PUT %s TO %s" % (in_path, out_path), host=self.host)

        if not os.path.exists(in_path):
            raise errors.AnsibleFileNotFound(
                "file or module does not exist: %s" % in_path)
        data = file(in_path).read()

        data = dict(mode='put', data=data, out_path=out_path)
        data = utils.jsonify(data)
        data = utils.encrypt(self.key, data)
        self.socket.send(data)

        response = self.socket.recv()
        response = utils.decrypt(self.key, response)
        response = utils.parse_json(response)
Beispiel #59
0
    def fetch_file(self, in_path, out_path):
        ''' save a remote file to the specified path '''
        vvv("FETCH %s TO %s" % (in_path, out_path), host=self.host)

        data = dict(mode='fetch', file=in_path)
        data = utils.jsonify(data)
        data = utils.encrypt(self.key, data)
        self.socket.send(data)

        response = self.socket.recv()
        response = utils.decrypt(self.key, response)
        response = utils.parse_json(response)
        response = response['data']

        fh = open(out_path, "w")
        fh.write(response)
        fh.close()
Beispiel #60
0
    def exec_command(self,
                     cmd,
                     become_user=None,
                     sudoable=False,
                     executable='/bin/sh',
                     in_data=None):
        ''' run a command on the remote minion '''

        if in_data:
            raise errors.AnsibleError(
                "Internal Error: this module does not support optimized module pipelining"
            )

        # totally ignores privlege escalation
        vvv("EXEC %s" % (cmd), host=self.host)
        p = self.client.command.run(cmd)[self.host]
        return (p[0], p[1], p[2])