下载zip文件并用Python将其写入磁盘有特殊技巧吗?

时间:2009-02-23 01:00:38

标签: python ftp ftplib

我使用Python的ftplib从远程FTP站点FTP文件。然后我尝试将其写入磁盘。文件写入工作,但大多数尝试使用WinZip或WinRar打开zip失败;这两个应用声称该文件已损坏。然而奇怪的是,当右键单击并尝试使用WinRar提取文件时,文件提取。

所以要明确的是,文件写入将起作用,但不会在流行的zip应用程序中打开,但使用相同的应用程序进行解压缩。请注意,Python zipfile模块从不无法提取拉链。

以下是我用来从FTP站点获取zip文件的代码(请忽略错误的标签,这不是问题)。

filedata = None
def appender(chunk):
    global filedata
    filedata += chunk


def getfile(filename):
  try:
      ftp = None

      try:
          ftp = FTP(address)
          ftp.login('user', 'password')

      except Exception, e:
          print e

      command = 'RETR ' + filename

      idx = filename.rfind('/')
      path = filename[0:idx]
      ftp.cwd(path)
      fileonly = filename[idx+1:len(filename)]

      ftp.retrbinary('RETR ' + filename, appender)

      global filedata
      data = filedata

      ftp.close()

      filedata = ''
      return data

  except Exception, e:
      print e

data = getfile('/archives/myfile.zip')    
file = open(pathtoNTFileShare, 'wb')
file.write(data)
file.close()

2 个答案:

答案 0 :(得分:2)

直接在retrbinary函数内传递file.write而不是传递appender。这将起作用,当您下载大文件时它也不会使用那么多RAM。

如果您希望存储在变量中的数据,您还可以使用名为:

的变量
blocks = []

然后传递给retrbinary而不是appender:

blocks.append

您当前的appender功能是错误的。当存在二进制数据时,+ =将无法正常工作,因为它将尝试执行字符串追加并在它看到的第一个NULL处停止。

如@Lee B所述,您也可以使用urllib2或Curl。但是,如果您进行上面提到的小修改,那么您当前的代码几乎是正确的。

答案 1 :(得分:1)

我从未使用过那个库,但urllib2工作正常,而且更直接。卷曲更好。

看看你的代码,我可以看到一些错误。您的异常捕获仅打印异常,然后继续。对于没有获得FTP连接的致命错误,他们需要打印消息然后退出。此外,你的filedata以None开头,然后你的appender使用+ =来添加,所以你试图追加一个字符串+ None,当我在这里尝试它时会产生一个TypeError。我很惊讶它正在工作;我猜想appender会抛出一个异常,所以FTP副本会中止。

在重读时,我刚刚注意到关于在二进制数据上使用+ =的另一个答案。那可能就是这样; python有时候会变得聪明,并且当你加入带有空格或NUL的字符串时,可能会“帮助”,或类似的东西。你最好的办法是让文件打开(让我们把它称为outfile),并使用你的appender只是outfile.write(chunk)。