How to monitor transfers and commands

It can be very useful to be able to monitor FTP transfers, that is, to receive programmatic feedback on how the transfer is progressing. Similarly, it can be useful to obtain the commands that are being sent back and forth.

Progress monitoring

The FTPProgressMonitor interface is used to monitor the number of bytes being transferred. Typically, the developer implements this interface in their own class (perhaps as an anonymous class). An instance is set via setProgressMonitor, and once the transfer begins, the instance is notified periodically during the transfer of how many bytes have been transferred up to that point. setProgressMonitor optionally permits an interval to be passed in, so that the notification period (i.e. the number of bytes transferred) can be altered. getMonitorInterval returns the interval currently being used.

An example of progress monitor usage is shown below. Firstly the implementation is defined, and then an instance set in the client:

// progress monitor that logs progress
class LogProgressMonitor implements FTPProgressMonitor {
  public void bytesTransferred(long bytes) {
    log.debug(bytes + " transferred");
  }
}
ftp.setProgressMonitor(new LogProgressMonitor(), 100000);

More sophisticated usages might be to display a progress bar in a GUI. For this to be achieved, first obtain the size of file via the size method. Then progress can be accurated estimately and displayed.

Command monitoring

The FTPMessageListener interface provides a means of obtaining the commands that are sent between client and FTP server. This includes but is not limited to transfer commands - all commands can be collected. This is mainly useful for debugging purposes. The developer implements this interface in their own class, and an instance is set via setMessageListener. From that point on, all commands (from client to server and from server to client) are provided to this instance. An example is shown below that logs all commands:

// progress monitor that logs progress
class LogMessageListener implements FTPMessageListener {
  public void logCommand(String cmd) {
    log.debug("Command: " + cmd);
  }
  public void logReply(String reply) {
    log.debug("Reply: " + reply);
  }
}
ftp.setMessageListener(new LogMessageListener()); 

For convenience, the FTPMessageCollector class is provided. This is an implementation of FTPMessageListener that maintains a log of messages (as a single string) which can be obtained at any time.