基于Apache Commons-net包,进行的FTP文件传输

FTP简介:

FTP(File Transfer Protocol):是应用层的一个文件传输协议 。主要作用是在服务器和客户端之间实现文件的传输和共享。FTP协议运行在TCP连接上,保证了文件传输的可靠性。在传输时,传输双方的操作系统、磁盘文件系统类型可以不同。

FTP协议:允许TCP/IP网络上的两台计算机之间进行文件传输。而FTP服务是基于FTP协议的文件传输服务。工作时,一台计算机上运行FTP客户端应用程序,另一台计算机上需要运行FTP服务器端程序。只有拥有了FTP服务,客户端才能进行文件传输。

Ⅰ.与HTTP的区别:

HTTP和FTP都是文件传输协议,都是运行在TCP上面,但是他们也有一些重要的区别。

FTP使用了两个并行的TCP来传输文件:一个是控制连接(port:21),一个是数据连接(port:20)。控制连接用于在两个主机之间传输控制信息,如口令,用户标识,存放、获取文件等命令。数据连接用于实际发送一个文件,发送完文件之后数据连接会关闭。因为FTP协议使用一个独立的控制连接,所以,也称FTP的控制信息是带外(out-of-band)传送的。

HTTP协议是在传输文件的同一个TCP连接中发送请求和相应首部行的。因此,HTTP也可以说是带内(in-band)发送控制信息。

Ⅱ.FTP协议的2种传输方式:

FTP支持两种方式的传输:文本(ASCII)方式和二进制(Binary)方式。

通常文本文件的传输采用ASCII方式;而图象、声音文件、加密和压缩文件等非文本文件采用二进制方式传输;

Ⅲ.FTP的2种传输模式:

FTP有两种传输模式——主动(FTP Port)模式和被动(FTP Passive)模式。由于主动模式存在着安全问题,最近几年,大部分的TFP客户端开始默认使用被动模式。

被动方式(Passive):

由于主动方式中,服务端需要主动连客户端,对于客户端的防火墙来说,属于外部连接内部,会出现被阻塞的情况。被动方式解决了这个问题。被动连接的核心是——控制连接请求和数据连接请求都是由客户端发起。

被动方式的步骤如下:

1.客户端任意打开约1024的两个本地端口(P1和P1+1)

2.P1端口发送请求连接服务器的21端口(控制连接端口)同时提交PASV命令。

3.服务器收到请求后,会开启任意一个大约1024的端口P2,然后返回如下格式内容:

227 entering passive mode(h1,h2,h3,h4,p1,p2)

4.客户端收到服务端返回的内容后,计算出服务端开放的数据连接端口

5.客户端通过P1+1端口向服务端的发送连接请求。进行数据传输

关于服务端返回的报文格式(h1,h2,h3,h4,p1,p2)具体含义如下:

h1,h2,h3,h4代表服务器的ip地址;

p1,p2代表服务器监听的数据连接端口地址。计算方法为P1*256+P2

FTP的限制:当客户端用户数量不断增多,FTP服务器所要维持的会话总数,也会迅速增长。这会大大限制FTP服务器的性能。

应答:

FTP客户端每个发出的命令都会对应一个FTP服务器发出的应答。应答是一个3位的数字,后跟一个可选信息。他与HTTP响应报文的状态码和状态信息的结构相同,比较常见的几个应答可以参考如下:

以上内容参考文章:https://zhuanlan.zhihu.com/p/337513218 (侵删)

FTP服务器应用:

环境配置:Win10、IDEA2020、easyftp-server-1.7.0.10

1.文件列表显示

public class ftp {
    public static void main(String[] args) {
        //创建基于FTP协议访问的文件服务器的客户端对象
        FTPClient ftpClient = new FTPClient();


        try {

            //连接服务器验证用户名密码
            ftpClient.connect("127.0.0.1",21);//IP地址,端口号
            ftpClient.login("admin","123456");//验证用户名密码

            SimpleDateFormat fmt = new SimpleDateFormat("yyyy年MM月dd日");//设置时间格式

            //获取当前目录中所有文件
            FTPFile[] ftpFilesList = ftpClient.listFiles();
            for (FTPFile file : ftpFilesList) {
                 //文件名称包含乱码
                 String fileName = file.getName();
                 fileName = new String(fileName.getBytes("iso-8859-1"), "gb2312");//汉字转码
                 System.out.println("name:" + fileName);//文件名称

                 Date createDate = file.getTimestamp().getTime();//获取时间
                 System.out.println("time" + fmt.format(createDate));//文件创建时间
                 System.out.println("size" + file.getSize());//文件大小
                }        
        } catch (SocketException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }finally {
            try {
                ftpClient.disconnect();//断开与FTP服务器连接
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }
}

2.文件上传

public class ftp {
    public static void main(String[] args) {
        //创建基于FTP协议访问的文件服务器的客户端对象
        FTPClient ftpClient = new FTPClient();

        //选择需要上传的文件,创建input输入流
        try(FileInputStream in = new FileInputStream("d:\\text\\1.jpg")){
            //连接服务器验证用户名密码
            ftpClient.connect("127.0.0.1",21);//IP地址,端口号
            ftpClient.login("admin","123456");//用户名,密码

            //选择上传至的目录,切换目录操作
            boolean isChange = ftpClient.changeWorkingDirectory("Admin");
            //若无则创建目录
            if (!isChange){
                ftpClient.makeDirectory("Admin");//创建目录
                //切换至目录
                ftpClient.changeWorkingDirectory("Admin");
            }

            //上传文件至FTP服务器
            ftpClient.setFileType(FTPClient.BINARY_FILE_TYPE);//二进制字节流上传
            //参数1:FTP文件保存名称,参数2:本地文件输入流
            boolean isStore =  ftpClient.storeFile(System.currentTimeMillis()+"jpg",in);
            System.out.println("上传成功?" + isStore);
            
        } catch (SocketException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }finally {
            //断开连接
            try {
                ftpClient.disconnect();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }
}

3.文件下载

public class ftp {
    public static void main(String[] args) {
        //创建基于FTP协议访问的文件服务器的客户端对象
        FTPClient ftpClient = new FTPClient();

        //选择下载路径,创建output输出流
        try (FileOutputStream out = new FileOutputStream("d:\\text\\"+System.currentTimeMillis()+"jpg")) {
            //连接FTP服务器并验证用户信息
            ftpClient.connect("127.0.0.1", 21);
            ftpClient.login("Admin", "123456");

            //切换至服务器的个人目录
            boolean isChange = ftpClient.changeWorkingDirectory("User");

            //下载文件
            ftpClient.setFileType(FTPClient.BINARY_FILE_TYPE);//文件类型
            boolean isStore = ftpClient.retrieveFile("2.jpg",out);//需要下载的文件名称
            System.out.println("下载成功?"+isStore);

        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }finally {
            //断开连接
            try {
                ftpClient.disconnect();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }
}

小结:

1.访问下载文件可通过浏览器访问FTP服务器的方式实现

2.文件上传下载以二进制流的方式进行,注意上传下载输入输出流的区分

                                                                                          向上攀爬的痛苦,终会在登顶时烟消云散

                                       ——ZQY

  • 32
    点赞
  • 30
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
要使用Apache Commons Net将服务器A中A目录下的所有文件传输服务器B中的B文件夹下,你可以使用FTPClient这个类来实现。 具体实现步骤如下: 1. 导入Apache Commons Net的jar:将Apache Commons Net的jar导入到你的Java项目中。 2. 建立FTP连接:使用FTPClient类建立与服务器A的FTP连接,设置A服务器的IP地址、端口号、用户名和密码等信息。 3. 切换到A目录:使用FTPClient对象的changeWorkingDirectory方法切换到A目录下。 4. 获取A目录下的所有文件:使用FTPClient对象的listFiles方法获取A目录下的所有文件。 5. 建立FTP连接:使用FTPClient类建立与服务器B的FTP连接,设置B服务器的IP地址、端口号、用户名和密码等信息。 6. 切换到B目录:使用FTPClient对象的changeWorkingDirectory方法切换到B目录下。 7. 上传文件:使用FTPClient对象的storeFile方法将A目录下的文件上传到B目录下。 8. 关闭FTP连接:使用FTPClient对象的disconnect方法关闭FTP连接。 示例代码如下: ```java import java.io.IOException; import org.apache.commons.net.ftp.*; public class FtpExample { public static void main(String[] args) { String userA = "usernameA"; String passwordA = "passwordA"; String hostA = "hostA"; int portA = 21; String directoryA = "/path/to/A"; String userB = "usernameB"; String passwordB = "passwordB"; String hostB = "hostB"; int portB = 21; String directoryB = "/path/to/B"; FTPClient ftp = new FTPClient(); try { // 建立与服务器A的FTP连接 ftp.connect(hostA, portA); ftp.login(userA, passwordA); // 切换到A目录 ftp.changeWorkingDirectory(directoryA); // 获取A目录下的所有文件 FTPFile[] files = ftp.listFiles(); // 建立与服务器B的FTP连接 ftp.disconnect(); ftp.connect(hostB, portB); ftp.login(userB, passwordB); // 切换到B目录 ftp.changeWorkingDirectory(directoryB); // 上传文件 for (FTPFile file : files) { if (file.isFile()) { ftp.storeFile(file.getName(), ftp.retrieveFileStream(file.getName())); ftp.completePendingCommand(); } } // 关闭FTP连接 ftp.logout(); ftp.disconnect(); } catch (IOException e) { e.printStackTrace(); } } } ``` 以上是使用Apache Commons Net实现将服务器A中A目录下的所有文件传输服务器B中的B文件夹下的基本步骤。通过这个示例代码,你可以在C服务中实现这个功能。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

菜鸟0917

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值