python - python如何通过http下载文件?

  显示原文与译文双语对照的内容

我有一个小工具,我用来从一个网站下载 MP3,然后构建/更新一个播客文件,我显然已经在iTunes上添加了它。

创建/更新XML文件的文本处理是用 python 编写的。 我在 Windows .bat 文件中使用wget来下载实际的MP3 。 我宁愿用 python 编写整个工具。

我努力想办法在 python 加载文件,因此我采取 wget的原因。

那么,如何使用 python 下载该文件?

时间:

在 python 2中,使用标准库附带的urllib2.


import urllib2
response = urllib2.urlopen('http://www.example.com/')
html = response.read()

这是使用库的最基本方法,减去任何错误处理。 你还可以做更复杂的事情,比如更改标题。 可以在这里找到文档

再一次,使用 urlretrieve:


import urllib
urllib.urlretrieve ("http://www.example.com/songs/mp3.mp3","mp3.mp3")

另一个,带有"progressbar,"


import urllib2

url ="http://download.thinkbroadband.com/10MB.zip"

file_name = url.split('/')[-1]
u = urllib2.urlopen(url)
f = open(file_name, 'wb')
meta = u.info()
file_size = int(meta.getheaders("Content-Length")[0])
print"Downloading: %s Bytes: %s" % (file_name, file_size)

file_size_dl = 0
block_sz = 8192
while True:
 buffer = u.read(block_sz)
 if not buffer:
 break

 file_size_dl += len(buffer)
 f.write(buffer)
 status = r"%10d [%3.2f%%]" % (file_size_dl, file_size_dl * 100./file_size)
 status = status + chr(8)*(len(status)+1)
 print status,

f.close()

在 2012中,使用 python 请求库


>>> import requests
>>> 
>>> url ="http://download.thinkbroadband.com/10MB.zip"
>>> r = requests.get(url)
>>> print len(r.content)
10485760

你可以运行 pip install requests 来获取它。

请求有许多优点,因为API比其他方法更简单。 如果你必须进行身份验证,则尤其如此。 urllib和urllib2在这种情况下是非常unintuitive和痛苦的。


import urllib2
mp3file = urllib2.urlopen("http://www.example.com/songs/mp3.mp3")
output = open('test.mp3','wb')
output.write(mp3file.read())
output.close()

'wb'open('test.mp3','wb') 打开( 并清除任何现有的) 文件,binaraly,所以你可以用它来保存数据,而不是文本。

我同意科里,urllib2完成比 urllib,可能应该使用的模块,如果你想做更复杂的事情,而是使答案更加完整,urllib是一个简单的模块如果你想基础:


import urllib
response = urllib.urlopen('http://www.example.com/sound.mp3')
mp3 = response.read()

将正常工作。或者,如果你不想处理"响应"对象可以调用 read() 直接:


import urllib
mp3 = urllib.urlopen('http://www.example.com/sound.mp3').read()

wget图书馆在纯 python 只是为了这个目的。 这是泵与 urlretrieve 这些特性 2.0的版本。

一个改进版本的PabloG代码 python 2/3:


from __future__ import ( division, absolute_import, print_function, unicode_literals )

import sys, os, tempfile, logging

if sys.version_info> = (3,):
 import urllib.request as urllib2
 import urllib.parse as urlparse
else:
 import urllib2
 import urlparse

def download_file(url, desc=None):
 u = urllib2.urlopen(url)

 scheme, netloc, path, query, fragment = urlparse.urlsplit(url)
 filename = os.path.basename(path)
 if not filename:
 filename = 'downloaded.file'
 if desc:
 filename = os.path.join(desc, filename)

 with open(filename, 'wb') as f:
 meta = u.info()
 meta_func = meta.getheaders if hasattr(meta, 'getheaders') else meta.get_all
 meta_length = meta_func("Content-Length")
 file_size = None
 if meta_length:
 file_size = int(meta_length[0])
 print("Downloading: {0} Bytes: {1}".format(url, file_size))

 file_size_dl = 0
 block_sz = 8192
 while True:
 buffer = u.read(block_sz)
 if not buffer:
 break

 file_size_dl += len(buffer)
 f.write(buffer)

 status ="{0:16}".format(file_size_dl)
 if file_size:
 status +=" [{0:6.2f}%]".format(file_size_dl * 100/file_size)
 status += chr(13)
 print(status, end="")
 print()

 return filename

url ="http://download.thinkbroadband.com/10MB.zip"
filename = download_file(url)
print(filename)

这可能有点晚了,但是我看到了pablog代码,并且无法添加 os.system('cls') 来让它看起来很棒 ! 检查一下:


 import urllib2,os

 url ="http://download.thinkbroadband.com/10MB.zip"

 file_name = url.split('/')[-1]
 u = urllib2.urlopen(url)
 f = open(file_name, 'wb')
 meta = u.info()
 file_size = int(meta.getheaders("Content-Length")[0])
 print"Downloading: %s Bytes: %s" % (file_name, file_size)
 os.system('cls')
 file_size_dl = 0
 block_sz = 8192
 while True:
 buffer = u.read(block_sz)
 if not buffer:
 break

 file_size_dl += len(buffer)
 f.write(buffer)
 status = r"%10d [%3.2f%%]" % (file_size_dl, file_size_dl * 100./file_size)
 status = status + chr(8)*(len(status)+1)
 print status,

 f.close()

你也可以通过urlretrieve获得进度反馈:


def report(blocknr, blocksize, size):
 current = blocknr*blocksize
 sys.stdout.write("r{0:.2f}%".format(100.0*current/size))

def downloadFile(url):
 print"n",url
 fname = url.split('/')[-1]
 print fname
 urllib.urlretrieve(url, fname, report)

源代码可以是:


import urllib
sock = urllib.urlopen("http://diveintopython.org/")
htmlSource = sock.read() 
sock.close() 
print htmlSource 

...