【问题标题】:Data truncation from FTP download using Apache使用 Apache 截断 FTP 下载的数据
【发布时间】:2023-03-09 04:11:02
【问题描述】:

使用来自commons-net:commons-net:3.6 的 Apache FTP 客户端,我正在从我们的 FTPS 服务器读取文件

FTPClient#retrieveFile("/OUT/somefile.xml", someBAOS)

通常,一切正常,但有时文件会被截断。

这是一切正常时的协议:

< 220 ProFTPD 1.3.5a Server (someserver) [::ffff:...]
> AUTH TLS
< 234 AUTH TLS successful
> PBSZ 0
< 200 PBSZ 0 successful
> PROT P
< 200 Protection set to Private
> USER someuser
< 331 Password required for someuser
> PASS ***
< 230 User someuser logged in
> TYPE I
< 200 Type set to I
> PASV
< 227 Entering Passive Mode (...).
> RETR /OUT/somefile.xml
< 150 Opening BINARY mode data connection for /OUT/somefile.xml (4769503 bytes)
< 226 Transfer complete

当文件被截断时,记录较小的大小:

< 150 Opening BINARY mode data connection for /OUT/somefile.xml (2569402 bytes)

截断偶尔发生。在下一次下载时,一小时后,一切都恢复正常了。我们很确定该文件在此期间没有更改。

日志文件是使用SocketClient#addProtocolCommandListener 生成的,我很确定更改的大小不是来自我的听众。我猜,文本是由 FTP 服务器生成并按原样转储的。 有人可以确认文件大小确实来自服务器(而不是由 Apache 客户端添加)吗?

有趣的是,下载的截断文件有2602133字节(我很确定,没有通过文本转换等添加\rs;首先,我们进行转换;其次,差异是31371字节,有那里有 56577 行)。

最可能的解释是有人在此期间更改了文件,但服务器日志清楚地表明当时没有其他人。

知道如何找出发生了什么吗?

结果

我还有一些日志清楚地显示在问题发生时前后有上传。同时,日志声称没有时间重叠。无论如何,确认150 ... 行直接来自服务器,毫无疑问,并发访问是罪魁祸首。

【问题讨论】:

  • 缺少字节或被截断?我假设被截断但值得确认。知道一些类似的错误,但认为 3.3 解决了大部分问题
  • 您似乎有两个不同的问题。注意&lt;表示它是从服务器接收到的消息,所以服务器认为文件更小...至于服务器的大小想法和实际接收到的大小之间的差异,我们必须查看代码,看看someBAOS 会发生什么。
  • 编码?也许ftpClient.setControlEncoding("UTF-8");(我知道它的二进制模式,应该没关系)。
  • @ficuscr 被截断,之前没有任何遗漏,只是检查了一下。关于编码:没有文件名包含任何特殊字符。没有文件可以混淆。但是,是的,我会setControlEncoding
  • @JimGarrison &lt; 来自我,但是是的,它是从protocolReplyReceived 调用的(我这边没有处理,除了过滤 PWD)。我可以想象 Apache 扩展消息(这该死的愚蠢,但愚蠢的事情总是发生)。关于代码,没有任何人可以在someBAOS.toByteArray() 中搞砸并在下一行记录长度。无论如何,我已经检查了几十次......并且下载工作几乎总是有一些罕见的例外 - 恕我直言,这样的错误必须与网络相关。

标签: java apache file ftp ftp-client


【解决方案1】:

消息

< 150 Opening BINARY mode data connection for /OUT/somefile.xml (2569402 bytes)

来自服务器,即提供文件的服务器只看到长度为 2569402 字节的文件。最可能的原因 - 在不知道此处涉及的实际系统的情况下 - 是您尝试下载的文件当前已创建。这就是为什么它会在几分钟后工作,因为此时文件创建完成。

这是不同解决方案的常见问题:

  • 创建具有已定义前缀或后缀的同名锁定文件,您可以检查该文件是否存在,如果不存在则仅执行下载。
  • 检查大小一段时间,只有在一段时间内大小没有变化时才尝试下载。
  • 使用临时名称或其他目录创建文件并将其重命名/移动到目标名称和目标

正如我所说,我不认为这是您的客户端的问题,服务器清楚地报告了错误的长度,所以问题的原因必须在那里。

【讨论】:

    【解决方案2】:

    150 Opening... 消息由服务器在数据连接建立后立即发送,即数据传输开始时。这意味着当数据传输开始时,从服务器的角度来看,消息包含文件的大小。这意味着文件在传输过程中不会被截断,而是比您在服务器端所期望的要小。

    由于使用二进制模式,服务器端不会更改行尾。鉴于您获得的实际下载大小比服务器报告的要大,但比您预期的要小,可能是在下载运行时服务器端的文件发生了变化。

    【讨论】:

    • 我接受了另一个答案,因为它有点快。我猜,你不在乎。
    猜你喜欢
    • 1970-01-01
    • 2023-03-11
    • 1970-01-01
    • 1970-01-01
    • 2012-05-04
    • 2018-10-04
    • 2014-11-21
    • 2013-10-18
    • 2020-06-23
    相关资源
    最近更新 更多