diff --git a/lib/kitchen/transport/sftp.rb b/lib/kitchen/transport/sftp.rb index b4cdf30..a6535f9 100644 --- a/lib/kitchen/transport/sftp.rb +++ b/lib/kitchen/transport/sftp.rb @@ -16,6 +16,7 @@ require 'benchmark' require 'digest/sha1' +require 'fileutils' require 'json' require 'kitchen/transport/ssh' @@ -94,6 +95,50 @@ def upload(locals, remote) end end + # (see Base::Connection#download) + def download(remotes, local) + # ensure the parent dir of the local target exists + FileUtils.mkdir_p(File.dirname(local)) + + Array(remotes).each do |remote| + entries = if remote.include? '*' + logger.debug("Interpreting remote '#{remote}' as glob, finding matching files...") + found_pattern = false + path = [] + pattern = [] + '/path/dir/*.json'.split('/').each do |comp| + found_pattern = true if comp.include? '*' + if found_pattern + pattern << comp + else + path << comp + end + end + sftp_session.dir.glob(path.join('/'), pattern.join('/')) + else + Array(remote) + end + + entries.each do |entry| + begin + logger.debug("Attempting to download '#{remote}' as file") + sftp_session.download!(entry, local) + rescue Net::SFTP::Error + begin + logger.debug("Attempting to download '#{remote}' as directory") + sftp_session.download!(entry, local, recursive: true) + rescue Net::SFTP::Error + logger.warn( + "SFTP download failed for file or directory '#{remote}', perhaps it does not exist?" + ) + end + end + end + end + rescue Net::SSH::Exception => ex + raise SshFailed, "SCP download failed (#{ex.message})" + end + private def sftp_upload!(local, remote, recursive: true, purge: true)