From c2b8fabf66545e3b4702c3fc152bdd3869ce0ac8 Mon Sep 17 00:00:00 2001 From: Michael DeHaan Date: Sat, 7 Jul 2012 09:10:18 -0400 Subject: [PATCH] Take a remote md5sum before a file transfer to decide whether to transfer the file or not. Allows for efficient transfer of large files. Templates do not sample first because they are small. --- lib/ansible/runner/__init__.py | 34 ++++++++++++++++++++++++---------- 1 file changed, 24 insertions(+), 10 deletions(-) diff --git a/lib/ansible/runner/__init__.py b/lib/ansible/runner/__init__.py index 1088f7c2f5..0964cf4c9c 100644 --- a/lib/ansible/runner/__init__.py +++ b/lib/ansible/runner/__init__.py @@ -430,24 +430,38 @@ class Runner(object): break if not found: results=dict(failed=True, msg="could not find src in first_available_file list") - return ReturnData(host=conn.host, is_error=True, results=results) + return ReturnData(host=conn.host, results=results) if self.module_vars is not None: inject.update(self.module_vars) source = utils.template(source, inject, self.setup_cache) + source = utils.path_dwim(self.basedir, source) - # transfer the file to a remote tmp location - tmp_src = tmp + source.split('/')[-1] - conn.put_file(utils.path_dwim(self.basedir, source), tmp_src) + local_md5 = utils.local_md5(source) + if local_md5 is None: + result=dict(failed=True, msg="could not find src=%s" % source) + return ReturnData(host=conn.host, result=result) + + remote_md5 = self._remote_md5(conn, tmp, dest) - # install the copy module - self.module_name = 'copy' - module = self._transfer_module(conn, tmp, 'copy') + exec_rc = None + if local_md5 != remote_md5: + # transfer the file to a remote tmp location + tmp_src = tmp + source.split('/')[-1] + conn.put_file(source, tmp_src) - # run the copy module - args = "src=%s dest=%s" % (tmp_src, dest) - exec_rc = self._execute_module(conn, tmp, module, args) + # install the copy module + self.module_name = 'copy' + module = self._transfer_module(conn, tmp, 'copy') + + # run the copy module + args = "src=%s dest=%s" % (tmp_src, dest) + exec_rc = self._execute_module(conn, tmp, module, args) + else: + # no need to transfer the file, already correct md5 + result = dict(changed=False, md5sum=remote_md5, transferred=False) + exec_rc = ReturnData(host=conn.host, result=result) if exec_rc.is_successful(): return self._chain_file_module(conn, tmp, exec_rc, options)