首页 > 代码库 > 使用Apache Commons Net API实现FTP上传下载过程中的坑点

使用Apache Commons Net API实现FTP上传下载过程中的坑点

       最近项目需要实现FTP上传、下载功能,采用了Apache Commons Net API。代码很快就完成了,但由于对相关API使用场景不是很熟悉,走了一些弯路,抽一点时间做一下总结。

        A)主动被动模式选择:FTP主动模式和被动模式的详细介绍可以参考(http://blog.csdn.net/huanggang028/article/details/41248663)。大概意思就是主动模式是客户端向服务端发送PORT命令,然后服务端通过20数据端口连接客户端开启的端口,然后发送数据;被动模式是客户端向服务端发送PASV命令,服务端随机开启一个端口并通知客户端,客户端根据该端口与服务端建立连接,然后发送数据。服务端是两种模式的,使用哪种模式取决于客户端,同时关键点在于网络环境适合用哪种模式,比如客户端在防火墙内,则最好选择被动模式。ftpClient.enterLocalActiveMode()便是配置成主动模式,而ftpClient.enterLocalPassiveMode()则配置成被动模式。

        B)文件格式选择:默认是类型是ASCII(普通文本文件),但是为了使得支持任何类型,建议设置成BINARY_FILE_TYPE,并且是在上传和下载操作开始前调用setFileType(int fileType)

       C)上传、下载重载方法的使用选择:比如上传,boolean storeFile(String remote, InputStream local)OutputStream storeFileStream(String remote),差别是第一个方法如果我们不用关心到底已经从InputStream中传递了多少字节,完全依靠接口内部实现完成输入输出操作,而第二个方法使得我们可以在上传过程中控制传送字节速度等额外操作,比如传送进度的实现便可以依赖此方法。但是,需要注意的是,如果采用了第二个方法来做, 必须靠我们去实现是否上传完毕、下载完毕的事后控制,否则会出现问题。比如我们采用第二个方法,需要手动关闭流,同时,紧接着调用completePendingCommand()方法。如果使用第一个方法不能调用completePendingCommand()方法,因为它一旦被调用, 会一直等待FTP服务器返回226Transfer complete,但是FTP服务器只有在接受流执行close方法时,才会返回。不该调用的时候调用了便会出现僵死现象,同时报错:

<span style="font-size:18px;">    14/11/19 13:43:29 ERROR expand.FTPSupport: FTP response 421 received.  Server closed connection.
org.apache.commons.net.ftp.FTPConnectionClosedException: FTP response 421 received.  Server closed connection.
at org.apache.commons.net.ftp.FTP.__getReply(FTP.java:363)
at org.apache.commons.net.ftp.FTP.__getReply(FTP.java:290)
at org.apache.commons.net.ftp.FTP.getReply(FTP.java:637)
at org.apache.commons.net.ftp.FTPClient.completePendingCommand(FTPClient.java:1637)</span>


使用Apache Commons Net API实现FTP上传下载过程中的坑点