Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How can I access an FTP server with JSch?

Tags:

java

sftp

ftp

jsch

I installed FileZilla FTP Server on my local Windows 7 machine. I also installed FileZilla FTP client on the same machine. Connection is successfull between both of them confirming the server and client partnership exists.

I wrote a small quick and dirtry Jsch program for connecting to the FileZilla FTP server and below is the program:

public class TestJSch {

/** Creates a new instance of TestCommonsNet */
public TestJSch() {
}

/**
 * main - Unit test program
 * 
 * @param args
 *            Command line arguments
 * 
 */
public static void main(String[] args) {
    try {
        String ftpHost = "127.0.0.1";
        int ftpPort = 21;// 14147;
        // int ftpPort = 990;// 14147;
        String ftpUserName = "kedar";
        String ftpPassword = "XXXXXXXXXXX";
        String ftpRemoteDirectory = "C:\\KEDAR\\Java\\FTP_Folder";
        String fileToTransmit = "C:\\KEDAR\\Java\\File_Folder\\Customer.txt";
        String identityfile = "C:\\KEDAR\\Java\\Ftp\\certificate.crt";

        //
        // First Create a JSch session
        //
        JSch.setLogger(new MyLogger());
        System.out.println("Creating session.");

        JSch jsch = new JSch();

        String knownHostsFilename = "C:\\Windows\\System32\\drivers\\etc\\hosts";
        jsch.setKnownHosts(knownHostsFilename);
        jsch.addIdentity(identityfile);
        Session session = null;
        Channel channel = null;
        ChannelSftp c = null;

        //
        // Now connect and SFTP to the SFTP Server
        //
        try {
            // Create a session sending through our username and password
            session = jsch.getSession(ftpUserName, ftpHost, ftpPort);
            System.out.println("Session created.");
            session.setPassword(ftpPassword);
            // Security.addProvider(new com.sun.crypto.provider.SunJCE());

            // b
            // Setup Strict HostKeyChecking to no so we dont get the
            // unknown host key exception
            //
            java.util.Properties config = new java.util.Properties();
            config.put("StrictHostKeyChecking", "no");
            session.setConfig(config);
            session.connect();
            System.out.println("Session connected.");

            //
            // Open the SFTP channel
            //
            System.out.println("Opening Channel.");
            channel = session.openChannel("sftp");
            channel.connect();
            c = (ChannelSftp) channel;
        } catch (Exception e) {
            System.err.println("Unable to connect to FTP server."
                    + e.toString());
            throw e;
        }

        //
        // Change to the remote directory
        //
        System.out.println("Changing to FTP remote dir: "
                + ftpRemoteDirectory);
        c.cd(ftpRemoteDirectory);

        //
        // Send the file we generated
        //
        try {
            File f = new File(fileToTransmit);
            System.out.println("Storing file as remote filename: "
                    + f.getName());
            c.put(new FileInputStream(f), f.getName());
        } catch (Exception e) {
            System.err
                    .println("Storing remote file failed." + e.toString());
            throw e;
        }   

        //
        // Disconnect from the FTP server
        //
        try {
            c.quit();
        } catch (Exception exc) {
            System.err.println("Unable to disconnect from FTPserver. "
                    + exc.toString());
        }

    } catch (Exception e) {
        System.err.println("Error: " + e.toString());
    }

    System.out.println("Process Complete.");
    System.exit(0);
}

public static class MyLogger implements com.jcraft.jsch.Logger {
    static java.util.Hashtable name = new java.util.Hashtable();
    static {
        name.put(new Integer(DEBUG), "DEBUG: ");
        name.put(new Integer(INFO), "INFO: ");
        name.put(new Integer(WARN), "WARN: ");
        name.put(new Integer(ERROR), "ERROR: ");
        name.put(new Integer(FATAL), "FATAL: ");
    }

    public boolean isEnabled(int level) {
        return true;
    }

    public void log(int level, String message) {
        System.err.print(name.get(new Integer(level)));
        System.err.println(message);
    }
}
}

I tried running this program and below is the FTP log:

(000033)9/12/2011 13:08:53 PM - (not logged in) (127.0.0.1)> Connected, sending welcome message...
(000033)9/12/2011 13:08:53 PM - (not logged in) (127.0.0.1)> 220-FileZilla Server version 0.9.39 beta
(000033)9/12/2011 13:08:53 PM - (not logged in) (127.0.0.1)> 220-written by Tim Kosse ([email protected])
(000033)9/12/2011 13:08:53 PM - (not logged in) (127.0.0.1)> 220 Please visit http://sourceforge.net/projects/filezilla/
(000033)9/12/2011 13:08:53 PM - (not logged in) (127.0.0.1)> SSH-2.0-JSCH-0.1.44
(000033)9/12/2011 13:08:53 PM - (not logged in) (127.0.0.1)> 500 Syntax error, command unrecognized.
(000033)9/12/2011 13:09:54 PM - (not logged in) (127.0.0.1)> 421 Login time exceeded. Closing control connection.
(000033)9/12/2011 13:09:54 PM - (not logged in) (127.0.0.1)> disconnected.

I don't understand why the JSch program is issuing SSH-2.0-JSCH-0.1.44 command and the communication is then turned down. How do we avoid this?

like image 804
Kedar Pulaparthi Avatar asked Sep 12 '11 20:09

Kedar Pulaparthi


People also ask

How do I transfer files using JSch?

JSch library provides the get() and put() method to transfer file between server and client. The put() method is used to transfer files from a local system to a remote server. Add the jsch dependency to the pom. xml file.


2 Answers

JSch is not an FTP client. JSch is an SSH client (with an included SFTP implementation).

The SSH protocol is a protocol to allow secure connections to a server, for shell access, file transfer or port forwarding. For this, the server must have an SSH server (usually on port 22, but that can vary). SFTP is a binary file transfer protocol which is usually tunneled over SSH, and not related to FTP (other than by name).

If you want to use JSch to download/upload files, you need to install and activate an SSH/SFTP server on your computer (respective the computer you want to access).

For FTP, you have to use other Java libraries (Apache Commons FTPClient seems to be famous, from the questions here).

By the way, the known hosts file for JSch is a file listing the public keys of the SSH hosts, not the file listing their IP addresses (which is the Windows config file you are trying to supply here).

like image 63
Paŭlo Ebermann Avatar answered Sep 18 '22 13:09

Paŭlo Ebermann


Use Apache commons-net FTP library.

import java.io.IOException;

import org.apache.commons.net.ftp.FTPClient;

import org.apache.commons.net.ftp.FTPReply;

public class FTPConnectionCode {

    public static void main(String[] args) {
        String server = "www.website.com";
       // generally ftp port is 21
        int port = 21;
        String user = "ftpusername";
        String pass = "ftppassword";

        FTPClient ftpClient = new FTPClient();

        try {

            ftpClient.connect(server, port);
            showServerReply(ftpClient);

            int replyCode = ftpClient.getReplyCode();
            if (!FTPReply.isPositiveCompletion(replyCode)) {
                System.out.println("Connect failed");
                return;
            }

            boolean success = ftpClient.login(user, pass);
            showServerReply(ftpClient);

            if (!success) {
                System.out.println("Could not login to the server");
                return;
            }

            // Changes working directory
            success = ftpClient.changeWorkingDirectory("/dir");
            showServerReply(ftpClient);

            if (success) {
                System.out.println("Successfully changed working directory.");
            } else {
                System.out.println("Failed to change working directory. See server's reply.");
            }

            // logs out
            ftpClient.logout();
            ftpClient.disconnect();

        } catch (IOException ex) {
            System.out.println("Oops! Something wrong happened");
            ex.printStackTrace();
        }
    }

    private static void showServerReply(FTPClient ftpClient) {
        String[] replies = ftpClient.getReplyStrings();
        if (replies != null && replies.length > 0) {
            for (String aReply : replies) {
                System.out.println("SERVER: " + aReply);
            }
        }
    }
}
like image 20
DemoUser Avatar answered Sep 20 '22 13:09

DemoUser