urllib.urlretrieve
也会静默返回,它只是将html页面保存到指定文件中。例如:
urllib.urlretrieve('http://google.com/abc.jpg', 'abc.jpg')
只是默默地返回,即使google.com服务器上不存在abc.jpg,生成的abc.jpg
也不是有效的jpg文件,它实际上是一个html页面。我想返回的头文件(httplib.HTTPMessage实例)可用于实际判断检索是否成功,但我找不到httplib.HTTPMessage
的任何文档。
有人可以提供有关此问题的一些信息吗?
答案 0 :(得分:26)
如果可能,请考虑使用urllib2
。它比urllib
更先进,更易于使用。
您可以轻松检测到任何HTTP错误:
>>> import urllib2
>>> resp = urllib2.urlopen("http://google.com/abc.jpg")
Traceback (most recent call last):
<<MANY LINES SKIPPED>>
urllib2.HTTPError: HTTP Error 404: Not Found
resp
实际上是HTTPResponse
对象,您可以通过以下方式执行许多有用的操作:
>>> resp = urllib2.urlopen("http://google.com/")
>>> resp.code
200
>>> resp.headers["content-type"]
'text/html; charset=windows-1251'
>>> resp.read()
"<<ACTUAL HTML>>"
答案 1 :(得分:6)
我保持简单:
# Simple downloading with progress indicator, by Cees Timmerman, 16mar12.
import urllib2
remote = r"http://some.big.file"
local = r"c:\downloads\bigfile.dat"
u = urllib2.urlopen(remote)
h = u.info()
totalSize = int(h["Content-Length"])
print "Downloading %s bytes..." % totalSize,
fp = open(local, 'wb')
blockSize = 8192 #100000 # urllib.urlretrieve uses 8192
count = 0
while True:
chunk = u.read(blockSize)
if not chunk: break
fp.write(chunk)
count += 1
if totalSize > 0:
percent = int(count * blockSize * 100 / totalSize)
if percent > 100: percent = 100
print "%2d%%" % percent,
if percent < 100:
print "\b\b\b\b\b", # Erase "NN% "
else:
print "Done."
fp.flush()
fp.close()
if not totalSize:
print
答案 2 :(得分:3)
根据文件是undocumented
要访问该消息,您可能会执行以下操作:
a, b=urllib.urlretrieve('http://google.com/abc.jpg', r'c:\abc.jpg')
b是消息实例
因为我已经学会了Python,所以当我输入时使用Python的内省能力总是有用的
dir(b)
我看到很多方法或功能可以使用
然后我开始用b
做事例如
b.items()
列出了很多有趣的东西,我怀疑玩这些东西会让你获得你想要操纵的属性。
对不起,这是一个初学者的答案,但我正在努力掌握如何使用内省能力来改善我的学习,并突然出现你的问题。
我尝试了一些有趣的事情 - 我想知道我是否可以自动从目录中出现的每个不需要参数的内容中获取输出,所以我写道:
needparam=[]
for each in dir(b):
x='b.'+each+'()'
try:
eval(x)
print x
except:
needparam.append(x)
答案 3 :(得分:2)
您可以创建新的URLopener(继承自FancyURLopener)并以任何方式抛出异常或处理错误。不幸的是,FancyURLopener忽略了404和其他错误。看到这个问题:
答案 4 :(得分:1)
我最终得到了自己的retrieve
实现,在pycurl
的帮助下,它支持比urllib / urllib2更多的协议,希望它可以帮助其他人。
import tempfile
import pycurl
import os
def get_filename_parts_from_url(url):
fullname = url.split('/')[-1].split('#')[0].split('?')[0]
t = list(os.path.splitext(fullname))
if t[1]:
t[1] = t[1][1:]
return t
def retrieve(url, filename=None):
if not filename:
garbage, suffix = get_filename_parts_from_url(url)
f = tempfile.NamedTemporaryFile(suffix = '.' + suffix, delete=False)
filename = f.name
else:
f = open(filename, 'wb')
c = pycurl.Curl()
c.setopt(pycurl.URL, str(url))
c.setopt(pycurl.WRITEFUNCTION, f.write)
try:
c.perform()
except:
filename = None
finally:
c.close()
f.close()
return filename
答案 5 :(得分:0)
class MyURLopener(urllib.FancyURLopener):
http_error_default = urllib.URLopener.http_error_default
url = "http://page404.com"
filename = "download.txt"
def reporthook(blockcount, blocksize, totalsize):
pass
...
try:
(f,headers)=MyURLopener().retrieve(url, filename, reporthook)
except Exception, e:
print e
答案 6 :(得分:0)
:)我在StackOverflow上的第一篇文章多年来一直是潜伏者。 :)
可悲的是,dir(urllib.urlretrieve)缺乏有用的信息。 所以从这个线程到目前为止我试着写这个:
a,b = urllib.urlretrieve(imgURL, saveTo)
print "A:", a
print "B:", b
产生了这个:
A: /home/myuser/targetfile.gif
B: Accept-Ranges: bytes
Access-Control-Allow-Origin: *
Cache-Control: max-age=604800
Content-Type: image/gif
Date: Mon, 07 Mar 2016 23:37:34 GMT
Etag: "4e1a5d9cc0857184df682518b9b0da33"
Last-Modified: Sun, 06 Mar 2016 21:16:48 GMT
Server: ECS (hnd/057A)
Timing-Allow-Origin: *
X-Cache: HIT
Content-Length: 27027
Connection: close
我想可以查一下:
if b.Content-Length > 0:
我的下一步是测试检索失败的场景......
答案 7 :(得分:0)
针对其他服务器/网站的结果 - 返回的内容&#34; B&#34;有点随机,但可以测试某些值:
A: get_good.jpg
B: Date: Tue, 08 Mar 2016 00:44:19 GMT
Server: Apache
Last-Modified: Sat, 02 Jan 2016 09:17:21 GMT
ETag: "524cf9-18afe-528565aef9ef0"
Accept-Ranges: bytes
Content-Length: 101118
Connection: close
Content-Type: image/jpeg
A: get_bad.jpg
B: Date: Tue, 08 Mar 2016 00:44:20 GMT
Server: Apache
Content-Length: 1363
X-Frame-Options: deny
Connection: close
Content-Type: text/html
在&#39;坏&#39; case(不存在的图像文件)&#34; B&#34;检索了一小部分(Googlebot?)HTML代码并将其保存为目标,因此Content-Length为1363字节。