Transferring Files by SFTP

Introduction

One of the common requirements of a Java SSH API is to transfer files to a remote server using the SFTP protocol. SFTP runs over the SSH protocol and is in our opinion the most secure way to transfer files between computers.

SFTP can also be used to create folders, change file permissions, create symbolic links etc. In this example we examine the size of the transferred files using the stat command to get the files attributes and its getSize method which returns the size of the remote file.

Source Code

package examples;

import java.io.BufferedReader;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.io.RandomAccessFile;

import com.sshtools.client.SshClient;
import com.sshtools.client.sftp.SftpClient;
import com.sshtools.client.sftp.TransferCancelledException;
import com.sshtools.common.permissions.PermissionDeniedException;
import com.sshtools.common.sftp.SftpFileAttributes;
import com.sshtools.common.sftp.SftpStatusException;
import com.sshtools.common.ssh.SshException;
import com.sshtools.common.util.IOUtils;
import com.sshtools.common.util.Utils;

public class SFTP {

public static void main(String[] args) throws IOException {

   try (BufferedReader reader = new BufferedReader(new InputStreamReader(System.in))) {
			
      String hostname = Utils.prompt(reader, "Hostname", "localhost");
      int port = 22;
      if (Utils.hasPort(hostname)) {
        port = Utils.getPort(hostname);
      }

      String username = Utils.prompt(reader, "Username", System.getProperty("user.name"));
      String password = Utils.prompt(reader, "Password");

      try (SshClient ssh = new SshClient(hostname, port, username, password.toCharArray())) {

         SftpClient sftp = new SftpClient(ssh);
				
         File file = new File("local.dat");
         file.createNewFile();
				
         RandomAccessFile localFile = new RandomAccessFile(file, "rw");
         localFile.setLength(IOUtils.fromByteSize("5mb"));
         localFile.close();
				
         System.out.println("Local file size is " + IOUtils.toByteSize(file.length()));
				
         sftp.lcd(System.getProperty("user.dir"));
         sftp.put("local.dat", "remote.dat");
				
         SftpFileAttributes attrs = sftp.stat("remote.dat");
         System.out.println("Remote file size is " + IOUtils.toByteSize(attrs.getSize().longValue()));
         sftp.get("remote.dat", "local2.dat");
			
         System.out.println("Local2 file size is " + IOUtils.toByteSize(new File("local2.dat").length()));
				
         try(OutputStream out = sftp.getOutputStream("stream.dat")) {
            try(FileInputStream in = new FileInputStream("local.dat")) {
               IOUtils.copy(in, out);
            }
         }
				
         attrs = sftp.stat("stream.dat");
         System.out.println("Streamed file size is " + IOUtils.toByteSize(attrs.getSize().longValue()));
				
         try(InputStream in  = sftp.getInputStream("stream.dat")) {
            try(FileOutputStream out = new FileOutputStream("stream2.dat")) {
               IOUtils.copy(in, out);
            }
         }
				
         System.out.println("Local streamed file size is " + IOUtils.toByteSize(new File("stream2.dat").length()));
         ssh.disconnect();
      } catch (SftpStatusException | TransferCancelledException | PermissionDeniedException e) {
         System.out.println(e);
      }

   } catch (IOException | SshException e) {
      System.out.println(e);
   }
}
}