使用Python下载并解压文件

15

我正在尝试下载并打开一个压缩文件,但使用zipfile时似乎遇到了问题。运行以下代码时出现错误信息“AttributeError: addinfourl instance has no attribute 'seek'”:

import zipfile
import urllib2

def download(url,directory,name):
 webfile = urllib2.urlopen('http://www.sec.gov'+url)
 webfile2 = zipfile.ZipFile(webfile)
 content = zipfile.ZipFile.open(webfile2).read()
 localfile = open(directory+name, 'w')
 localfile.write(content)
 localfile.close()
 return()

download(link.get("href"),'./fails_data', link.text)
5个回答

17

将所有东西放在一起,以下代码从网站上检索一个压缩文件中的第一个文件的内容:

import urllib.request
import zipfile
    
url = 'http://www.gutenberg.lib.md.us/4/8/8/2/48824/48824-8.zip'
filehandle, _ = urllib.request.urlretrieve(url)
zip_file_object = zipfile.ZipFile(filehandle, 'r')
first_file = zip_file_object.namelist()[0]
file = zip_file_object.open(first_file)
content = file.read()

3
对于更新版本的Python,请在第一行使用import urllib.request as urllib进行导入,而不是原来的方式。 - K.S.
这不会将其保留在内存中,它会在解压缩之前将压缩文件写入磁盘。 - Bastiaan

6
截至2020年,您可以使用 dload 下载并解压文件,例如:

import dload
dload.save_unzip("https://file-examples.com/wp-content/uploads/2017/02/zip_2MB.zip")

默认情况下,它会将文件提取到脚本路径上的一个目录中,该目录与zip文件名相同,但您可以指定提取位置:

dload.save_unzip("https://file-examples.com/wp-content/uploads/2017/02/zip_2MB.zip", "/extract/here")

使用 pip install dload 进行安装


2
有人在维护这个吗?自三月份以来我都没有看到任何提交记录。 - Ari
2
@Ari似乎不是这样的,这很不幸,因为它看起来是一个非常酷的包。当我使用save_unzip时,我也遇到了这个错误 - jrieke
我也遇到了这个错误。 ;( - etgriffiths

5

您无法在通过urllib2.urlopen打开的文件上进行搜索。它支持的方法在此处列出:http://docs.python.org/library/urllib.html#urllib.urlopen

您将不得不检索该文件(可能使用urllib.urlretrievehttp://docs.python.org/library/urllib.html#urllib.urlretrieve),然后对其使用zipfile

或者,您可以read() urlopen的文件,然后将其放入StringIO中,然后在其中使用zipfile,如果您想要在内存中获得压缩的数据。还要查看zipfileextractextract_all方法,如果您只想提取文件,而不是使用read


3

在@Marius的答案基础上进行迭代(直接从zip文件中读取单个文件),如果您想将所有文件提取到目录中,请执行以下操作:

import urllib
import zipfile

url = "http://www.gutenberg.lib.md.us/4/8/8/2/48824/48824-8.zip"
extract_dir = "example"

zip_path, _ = urllib.request.urlretrieve(url)
with zipfile.ZipFile(zip_path, "r") as f:
    f.extractall(extract_dir)

这将把zip文件存储在临时目录中。如果您想保留它,可以向urlretrieve传递一个文件名,例如:urllib.request.urlretrieve(url, "my_zip_file.zip")


3

我没有足够的声望来评论,但是关于Marius上面的答案,请注意对于Python3需要进行一些修改,涉及到import和urlretrieve的调用,因为urllib已经被分成几个模块。

import urllib

Becomes:

import urllib.request

并且
filehandle, _ = urllib.urlretrieve(url)

变成

filehandle, _ = urllib.request.urlretrieve(url)

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接