对JAVA的两个FTP包进行比较分析

Python015

对JAVA的两个FTP包进行比较分析,第1张

ftp *

这是一个不被官方支持的 但是放在JDK下面的FTP包 正因为不被支

持 所以没有官方提供API 这是其最大的缺陷之一 最重要由于不是官方支持的

所以文档也是没有的

[url]l[/url]

这里有该包的API

先给一个简单的例子 (例子来源互联网)

)显示FTP服务器上的文件

void ftpList_actionPerformed(ActionEvent e) {

String server=serverEdit getText()//输入的FTP服务器的IP地址

String user=userEdit getText()file://登/录FTP服务器的用户名

String password=passwordEdit getText()//登录FTP服务器的用户名的口令

String path=pathEdit getText()//FTP服务器上的路径

try {

FtpClient ftpClient=new FtpClient()//创建FtpClient对象

ftpClient openServer(server)//连接FTP服务器

ftpClient login(user password)//登录FTP服务器

if (path length()!= ) ftpClient cd(path)

TelnetInputStream is=ftpClient list()

int c

while ((c=is read())!= ) {

System out print((char) c)}

is close()

ftpClient closeServer()//退出FTP服务器

} catch (IOException ex) {}

}

)从FTP服务器上下传一个文件

void getButton_actionPerformed(ActionEvent e) {

String server=serverEdit getText()

String user=userEdit getText()

String password=passwordEdit getText()

String path=pathEdit getText()

String filename=filenameEdit getText()

try {

FtpClient ftpClient=new FtpClient()

ftpClient openServer(server)

ftpClient login(user password)

if (path length()!= ) ftpClient cd(path)

ftpClient binary()

TelnetInputStream is=ftpClient get(filename)

File file_out=new File(filename)

FileOutputStream os=new

FileOutputStream(file_out)

byte[] bytes=new byte[ ]

int c

while ((c=is read(bytes))!= ) {

os write(bytes c)

}

is close()

os close()

ftpClient closeServer()

} catch (IOException ex) {}

}

)向FTP服务器上上传一个文件

void putButton_actionPerformed(ActionEvent e) {

String server=serverEdit getText()

String user=userEdit getText()

String password=passwordEdit getText()

String path=pathEdit getText()

String filename=filenameEdit getText()

try {

FtpClient ftpClient=new FtpClient()

ftpClient openServer(server)

ftpClient login(user password)

if (path length()!= ) ftpClient cd(path)

ftpClient binary()

TelnetOutputStream os=ftpClient put(filename)

File file_in=new File(filename)

FileInputStream is=new FileInputStream(file_in)

byte[] bytes=new byte[ ]

int c

while ((c=is read(bytes))!= ){

os write(bytes c)}

is close()

os close()

ftpClient closeServer()

} catch (IOException ex) {}

}

}

看了这个例子 应该就能用他写东西了

这个包缺点很多 首先就是不被支持也不被官方推荐使用

其次是这个包功能过于简单 简单到无法区分FTP服务器上的File是文件还是目录 有人说

通过返回的字符串来判断 但是据说FTP在不同系统下返回的东西不大一样 所以如果通过

判断字符串会有不好移植的问题

自己想出了一个办法 通过FtpClient中的cd方法来判断

代码如下

try{

ftp cd(file)//file为当前判断的文件

//如果过了说明file是目录

}

catch(IOException e){

//说明file是文件

}

finally{

ftp cd( )//返回上级目录继续判断下一文件

}

我用这种方法做过尝试 结果是只能判断正确一部分 有些目录仍会被认做文件 不知道

是我的方法有错还是别的什么原因

如果对FTP服务没有过高的要求 使用这个包还是不错的 因为他本身就包含在JDK中 不

存在CLASSPATH的问题 不需要导入外部包 较为方便

ftp *

这个包在Jakarta Commons Net library里 现在的最高版本是 可以从以下地址

下载

[url] net [/url]

zip

里面包含了打包好的jar API 及全部的class文件

[url] net [/url]

src zip

这里包含一些例子以及全部的代码

给出一个该包的例子

import ftp *

public static void getDataFiles( String server

String username

String password

String folder

String destinationFolder

Calendar start

Calendar end )

{

try

{

// Connect and logon to FTP Server

FTPClient ftp = new FTPClient()

nnect( server )

ftp login( username password )

System out println( Connected to +

server + )

System out print(ftp getReplyString())

// List the files in the directory

ftp changeWorkingDirectory( folder )

FTPFile[] files = ftp listFiles()

System out println( Number of files in dir: + files length )

DateFormat df = DateFormat getDateInstance( DateFormat SHORT )

for( int i= i

{

Date fileDate = files[ i ] getTimestamp() getTime()

if( pareTo( start getTime() ) >= &&

pareTo( end getTime() ) <= )

{

// Download a file from the FTP Server

System out print( df format( files[ i ] getTimestamp() getTime() ) )

System out println( \t + files[ i ] getName() )

File file = new File( destinationFolder +

File separator + files[ i ] getName() )

FileOutputStream fos = new FileOutputStream( file )

ftp retrieveFile( files[ i ] getName() fos )

fos close()

file setLastModified( fileDate getTime() )

}

}

// Logout from the FTP Server and disconnect

ftp logout()

ftp disconnect()

}

catch( Exception e )

{

e printStackTrace()

}

}

同 ftp相同 都是先建立FtpClient(注意两包的大小写不同)的实例 然后通过

connect()方法连接 login()方法登陆 但是 ftp *明显比sun

net ftp功能强大很多

ftp *包将FTP中的file单独出来成为了一个新类FTPFile 还有

类FTPFileEntryParser parse 没有仔细研究 但是从字面来看应该是转化为某种形势的

类 有待研究

同时这个mons net jar包中也提供了FTP服务器 telnet mail等一系列类库

ftp *包的缺点在于需要设置classpath 并且需要下载jakarta

oro jar这个包才能运行(如果没有这个包 会在ftp listFiles()方法后抛出找不

到class异常) 此包无须在代码中import 只需设置在classpath中即可 下载地址

[url] oro zip[/url]

如果想要强大的FTP服务 那么 ftp *包应该是你的最好选择 而

且也是开源 免费的

这个包的问题是:

使用Jakarta Commons Net library需要在环境变量里面编辑classpath

这是不方便的地方

lishixinzhi/Article/program/Java/hx/201311/27057

学习了计算机网络之后,利用java写了一个ftp服务器。

一、实现的ftp命令

实现了基本的user,pass,list,port,quit,retr,cwd,stor等命令

二、以上命令所对应的功能

对应的功能是:下载,上传,获取服务器目录,切换目录等

三、用于测试的ftp客户端:windows自带的ftp客户端

四、实现的思想

1、使用ServerSocket进行监听,每个控制连接的请求到来之后,开启一个线程进行处理(这里使用的java bio,效率较差,对于控制连接最好使用NIO处理,之后会再写个

nio的实现)

2、 对于命令使用工厂方法模式进行设计,当需要添加新的命令的时候,只需要添加一个新的命令类,实现相应接口,修改工厂产生逻辑,而不用修改其他的程序代码。可

扩展性较好,同时符合开闭原则。

五、实现过程中碰到的问题

1、对于tcp与socket的关系理解错误,以为所有的数据的输入都是要经过serverSocket().accept()方法。其实,ServerSocket.accept()所对应的是tcp里面的三次握手建

立连接的阶段,之后的tcp的连接由客户端和服务器端的一对socket来维护,是属于establish阶段,在这个阶段,通信是全双工的,任何一方都能够发送数据。

socket.close()对应的阶段是断开连接(四次挥手)的阶段。

2、刚开始对于ftp协议不是很理解,不知道他的工作方式是怎样的,后来在看了tcp协议卷里面的ftp的内容之后,才知道ftp命令和应答码是关键。eg:刚开始测试时,在

输入用户名之后,不会提示输入密码的。原因:没有返回对应的应答码:331. 另外要注意的是:返回的数据要以换行回车作为结束--\r\n.

六、代码列表

简单说明:

ftpServer:是服务器的主程序,入口,同时负责监听本地的21号端口。

ControllerThread.java:用于处理控制连接的线程(每一个控制连接请求对应一个线程)ps:实在很浪费(流量小,连接多)。

Share:一些全局性数据的维护。

Command:是命令接口,定义了一个所有命令都要实现的方法。

CommandFactory:命令工厂,通过传人的参数,决定生成的命令对象。

UserCommand,PortCommand等:是具体ftp命令的实现

多次需要把文件上传到单独的服务器,而程序是在单独的服务器上部署的,在进行文件操作的时候就需要跨服务器进行操作包括:文件上传、文件下载、文件删除等。跨服务器文件操作一般是需要FTP协议和SFTP协议两种,现在就通过Java实现FTP协议的文件上传。要实现FTP操作文件需要引入jar包: commons-net-1.4.1.jar

参考资料来源:百度贴吧