【问题标题】:Issue with org.apache.commons.net.ftp.FTPClient listFiles()org.apache.commons.net.ftp.FTPClient listFiles() 的问题
【发布时间】:2011-02-04 07:41:48
【问题描述】:

org.apache.commons.net.ftp.FTPClientlistFiles() 方法适用于 127.0.0.1 上的 Filezilla 服务器,但在公共 FTP 服务器(如 belnet.be)的根目录上返回 null

下面的链接上有一个相同的问题,但enterRemotePassiveMode() 似乎没有帮助。 Apache Commons FTPClient.listFiles

这可能是列表解析的问题吗?如果是这样,如何解决这个问题?

编辑:这是一个目录缓存转储:

FileZilla 目录缓存转储

转储 1 个缓存目录

Entry 1:
Path: /
Server: anonymous@ftp.belnet.be:21, type: 4096
Directory contains 7 items:
  lrw-r--r-- ftp ftp      D          28      2009-06-17   debian
  lrw-r--r-- ftp ftp      D          31      2009-06-17   debian-cd
  -rw-r--r-- ftp ftp                  0 2010-03-04 13:30  keepalive.txt
  drwxr-xr-x ftp ftp      D        4096 2010-02-18 14:22  mirror
  lrw-r--r-- ftp ftp      D           6      2009-06-17   mirrors
  drwxr-xr-x ftp ftp      D        4096      2009-06-23   packages
  lrw-r--r-- ftp ftp      D           1      2009-06-17   pub

这是我使用我制作的包装器的代码(在包装器内进行测试会产生相同的结果):

public static void main(String[] args) {        
    FTPUtils ftpUtils = new FTPUtils();
    String ftpURL = "ftp.belnet.be";
    Connection connection = ftpUtils.getFTPClientManager().getConnection( ftpURL );

    if( connection == null ){
        System.out.println( "Could not connect" );
        return; 
    }

    FTPClientManager manager = connection.getFptClientManager();
    FTPClient client = manager.getClient();

    try {
        client.enterRemotePassiveMode();
    } catch (IOException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }

    if( connection != null ){
        System.out.println( "Connected to FTP" );
        connection.login("Anonymous", "Anonymous");
        if( connection.isLoggedIn() ){
            System.out.println( "Login successful" );
            LoggedInManager loggedin = connection.getLoggedInManager(); 
            System.out.println( loggedin );
            String[] fileList = loggedin.getFileList();

            System.out.println( loggedin.getWorkingDirectory() );

            if( fileList == null || fileList.length == 0 )
                System.out.println( "No files found" );
            else{
                for (String name : fileList ) {
                    System.out.println( name );
                }
            }

            connection.disconnect();

            if( connection.isDisconnected() )
                System.out.println( "Disconnection successful" );
            else
                System.out.println( "Error disconnecting" );
        }else{
            System.out.println( "Unable to login" );
        }
    } else {
        System.out.println( "Could not connect" );
    }
}

产生这个输出:

Connected to FTP
Login succesful
utils.ftp.FTPClientManager$Connection$LoggedInManager@156ee8e
null
No files found
Disconnection successful

在包装器内部(尝试同时使用 listNames()listFiles() ):

        public String[] getFileList() {
            String[] fileList = null;
            FTPFile[] ftpFiles = null;

            try {
                ftpFiles = client.listFiles();
                //fileList = client.listNames();
                //System.out.println( client.listNames() );
            } catch (IOException e) {
                return null;
            }

            fileList = new String[ ftpFiles.length ];

            for( int i = 0; i < ftpFiles.length; i++ ){
                fileList[ i ] = ftpFiles[ i ].getName();
            }

            return fileList;
        }

对于FTPClient,处理如下:

public class FTPUtils {

private FTPClientManager clientManager;

public FTPClientManager getFTPClientManager(){
    clientManager = new FTPClientManager();
    clientManager.setClient( new FTPClient() );

    return clientManager;
}

【问题讨论】:

    标签: java apache-commons ftp-client


    【解决方案1】:

    每个 FTP 服务器都有不同的文件列表布局(是的,它不是 FTP 标准的一部分,它很愚蠢),因此您必须使用正确的 FTPFileEntryParser,要么手动指定它,要么允许 CommonsFTP 自动- 检测它。

    自动检测通常可以正常工作,但有时不能,您必须明确指定它,例如

    FTPClientConfig conf = new FTPClientConfig(FTPClientConfig.SYST_UNIX);
    
    FTPClient client = FTPClient();
    client.configure(conf);
    

    这将预期的 FTP 服务器类型显式设置为 UNIX。尝试各种类型,看看效果如何。我试着找出自己,但ftp.belnet.be 拒绝我的联系:(

    【讨论】:

    • 谢谢。您知道是否有可能在解析之前获得原始列表输出?此外,Belnet(比利时研究网络)可能仅限于比利时 ips。你可以试试c64.rulez.org
    • @James:我想你可以提供你自己的FTPFileEntryParser实现
    • 顺便说一下,如果你看到构造函数,默认是 Unix,它就像这样 public FTPClientConfig() { this("UNIX"); }
    【解决方案2】:

    您是否尝试过检查是否可以使用普通 FTP 客户端列出文件? (由于某些原因,我什至无法连接到“belnet.be”的 FTP 端口。)

    编辑

    根据listFiles() 的javadoc,解析是使用解析器工厂提供的FTPFileEntryParser 实例完成的。您可能需要确定哪些解析器与 FTP 服务器的 LIST 输出匹配并相应地配置工厂。

    【讨论】:

    • 是的。 belnet.be 上的文件在 FileZilla 中显示良好。根目录中的一些文件夹似乎是快捷方式或链接。我不知道这是否有问题。我添加了目录列表的转储。
    • 谢谢。另外,ftp地址是ftp.belnet.be。
    【解决方案3】:

    在早期版本的 apache-Commons-net 中存在解析问题,SYST 命令在 returns null(突然)时返回服务器类型未处理解析异常。尝试使用 apache-commons-net 的 latest jar 可能会解决您的问题。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2020-11-11
      • 1970-01-01
      • 2012-01-07
      • 2012-09-30
      • 1970-01-01
      • 1970-01-01
      • 2021-07-07
      • 2016-03-13
      相关资源
      最近更新 更多