2
\$\begingroup\$

I've created a Java class for Android that connects to a FTP server (using the FTPClient library from commons-net-3.6) and uploads a file that is stored on an Android device. The code of the class is the following:


public class FTPHandler{ 
    private String HOST = "ipftpserver";
    private String USERNAME = "mylogin";
    private String PASSWORD = "mypassword";
    private int PORT = portnumber;
    FTPClient mFTPClient = new FTPClient();

    private boolean ftpConnect() {
        boolean ftpConnected;
        for (int i = 0; i <= 10; i++) {
            try {
                mFTPClient.connect(HOST, PORT);
                if (FTPReply.isPositiveCompletion(mFTPClient.getReplyCode())) {
                    boolean status = mFTPClient.login(USERNAME, PASSWORD);
                    mFTPClient.setFileType(FTP.BINARY_FILE_TYPE);
                    mFTPClient.enterLocalPassiveMode();
                    return status;
                }
                Thread.sleep(400);
            } catch (Exception e) {
                Log.d("TAG", "Error: could not connect to host " + HOST);
            }
        }
        return false;
    }

    private boolean ftpDisconnect() {
        try {
            mFTPClient.logout();
            mFTPClient.disconnect();
            return true;
        } catch (Exception e) {
            Log.d("TAG", "Error occurred while disconnecting from ftp server.");
        }
        return false;
    }

    public void uploadToFTP(String localPath, String remotePath) {
        Thread t = new Thread(new Runnable() {
            public void run() {
                try {
                    if (ftpConnect()) {
                        File remoteFile = new File(remotePath);
                        String remoteFileName = remoteFile.getName();

                        // check if remote file exists
                        boolean fileExists = false;
                        InputStream inputStream = mFTPClient.retrieveFileStream("/tmp/." + remoteFileName);
                        int returnCode = mFTPClient.getReplyCode();
                        if (inputStream == null || returnCode == 550) {
                            fileExists = false;
                        } else {
                            fileExists = true;
                        }
                        if (inputStream != null) {
                            inputStream.close();
                        }

                        // delete remote file if it exists
                        if (fileExists) {
                            mFTPClient.deleteFile("/tmp/." + remoteFileName);
                        }

                        ftpDisconnect(); // I don't know why I need to close and open the connection again here, if I don't the new file won't be uploaded after deleting the repeated old file on the server
                        ftpConnect();

                        // upload file to server
                        boolean status = false;
                        FileInputStream localStreamObject = new FileInputStream(localPath);
                        File remoteFileObject = new File("/tmp/." + remoteFileName);
                        String remoteDirectory = remoteFileObject.getParent();
                        if (mFTPClient.changeWorkingDirectory(remoteDirectory)) {
                            status = mFTPClient.storeFile("/tmp/." + remoteFileName, localStreamObject);
                            mFTPClient.rename("/tmp/." + remoteFileName, remotePath);
                        }
                        localStreamObject.close();
                        System.err.println(status);
                    }
                } catch (Exception e) {
                    System.err.println("uploadToFTP: error uploading fle");
                }
                ftpDisconnect();
            }
        });
        t.start();
    }

}

Basically, I have three methods:

  • ftpConnect(), connects to the FTP server

  • ftpDisconnect(), closes the connection to the FTP server

  • uploadToFTP(String localPath, String remotePath), uploads a file to the FTP server, I made it in a way that it mimics the command line mv command. So I just need to give the local path and the server path in order to transfer a file to it. Also, I first upload it to the /temp folder and after finishing the upload I move the file location on the server (just so I know that in the moment that the file was moved to the remotePath I'm 100% sure that the upload has finished its streaming of data).

This code works fine for its purpose... But I'd like some advice on how to make it better. I'm managing the permissions outside the FTPHandler class and I'm not so sure if the way that I've created the thread (on Android I'm obligated to run internet interactions as threads) is the best way of doing it (In a good practice perspective would it be better creating the thread outside my FTPClass?). Any ideas about how to improve this code or alternative ways of doing the same thing more efficiently?

\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Browse other questions tagged or ask your own question.