diff --git a/app/src/main/java/be/gyu/android/server/ftp/FTPSession.java b/app/src/main/java/be/gyu/android/server/ftp/FTPSession.java index 5729f64..b725115 100644 --- a/app/src/main/java/be/gyu/android/server/ftp/FTPSession.java +++ b/app/src/main/java/be/gyu/android/server/ftp/FTPSession.java @@ -107,6 +107,12 @@ public class FTPSession implements Runnable { case "PASV": handlePasv(); break; + case "RETR": + handleRetr(argument); + break; + case "STOR": + handleStor(argument); + break; case "NOOP": handleNoop(); break; @@ -369,6 +375,104 @@ public class FTPSession implements Runnable { } } + private void handleRetr(String fileName) throws IOException { + if (!isAuthenticated) { + sendResponse(FTPResponse.NOT_LOGGED_IN, "Please login first"); + return; + } + + if (fileName.isEmpty()) { + sendResponse(FTPResponse.SYNTAX_ERROR_PARAMETERS, "No file name specified"); + return; + } + + if (dataConnection == null) { + sendResponse(FTPResponse.CANNOT_OPEN_DATA_CONNECTION, "Use PASV first"); + return; + } + + java.io.File file = fileSystem.getFile(fileName); + if (file == null || !file.exists() || !file.isFile()) { + sendResponse(FTPResponse.FILE_UNAVAILABLE, "File not found"); + dataConnection.close(); + dataConnection = null; + return; + } + + sendResponse(FTPResponse.FILE_STATUS_OK, "Opening data connection for " + fileName + " (" + file.length() + " bytes)"); + + if (dataConnection.acceptConnection()) { + try { + java.io.FileInputStream fis = new java.io.FileInputStream(file); + if (dataConnection.transferStream(fis)) { + fis.close(); + dataConnection.close(); + sendResponse(FTPResponse.CLOSING_DATA_CONNECTION, "Transfer complete"); + Log.i(TAG, "File sent: " + fileName + " (" + file.length() + " bytes)"); + } else { + fis.close(); + dataConnection.close(); + sendResponse(FTPResponse.CONNECTION_CLOSED, "Transfer failed"); + } + } catch (Exception e) { + Log.e(TAG, "Error sending file: " + e.getMessage()); + dataConnection.close(); + sendResponse(FTPResponse.CONNECTION_CLOSED, "Transfer error: " + e.getMessage()); + } + } else { + dataConnection.close(); + sendResponse(FTPResponse.CANNOT_OPEN_DATA_CONNECTION, "Cannot open data connection"); + } + + dataConnection = null; + } + + private void handleStor(String fileName) throws IOException { + if (!isAuthenticated) { + sendResponse(FTPResponse.NOT_LOGGED_IN, "Please login first"); + return; + } + + if (fileName.isEmpty()) { + sendResponse(FTPResponse.SYNTAX_ERROR_PARAMETERS, "No file name specified"); + return; + } + + if (dataConnection == null) { + sendResponse(FTPResponse.CANNOT_OPEN_DATA_CONNECTION, "Use PASV first"); + return; + } + + java.io.File file = new java.io.File(fileSystem.getCurrentDirectory(), fileName); + + sendResponse(FTPResponse.FILE_STATUS_OK, "Opening data connection for " + fileName); + + if (dataConnection.acceptConnection()) { + try { + java.io.FileOutputStream fos = new java.io.FileOutputStream(file); + if (dataConnection.receiveStream(fos)) { + fos.close(); + dataConnection.close(); + sendResponse(FTPResponse.CLOSING_DATA_CONNECTION, "Transfer complete"); + Log.i(TAG, "File received: " + fileName + " (" + file.length() + " bytes)"); + } else { + fos.close(); + dataConnection.close(); + sendResponse(FTPResponse.CONNECTION_CLOSED, "Transfer failed"); + } + } catch (Exception e) { + Log.e(TAG, "Error receiving file: " + e.getMessage()); + dataConnection.close(); + sendResponse(FTPResponse.CONNECTION_CLOSED, "Transfer error: " + e.getMessage()); + } + } else { + dataConnection.close(); + sendResponse(FTPResponse.CANNOT_OPEN_DATA_CONNECTION, "Cannot open data connection"); + } + + dataConnection = null; + } + private void handleNoop() throws IOException { sendResponse(FTPResponse.COMMAND_OK, "OK"); }