Python (3.5) - urllib.request.urlopen - 进度条可用吗?
Python (3.5) - urllib.request.urlopen - Progress Bar Available?
我正试图在万维网上搜索这个答案,但我觉得答案可能是否定的。我正在使用 Python 3.5 和一个名为 urllib.request
的库以及一个名为 urllib.request.urlopen(url)
的方法来打开 link 并下载文件。
由于文件超过 200MB,最好对此进行某种进度衡量。我正在查看 API here,但没有看到任何带钩子的参数。
这是我的代码:
downloadURL = results[3] #got this from code earlier up
rel_path = account + '/' + eventID + '_' + title + '.mp4'
filename_abs_path = os.path.join(script_dir, rel_path)
print('>>> Downloading >>> ' + title)
# Download .mp4 from a url and save it locally under `file_name`:
with urllib.request.urlopen(downloadURL) as response, open(filename_abs_path, 'wb') as out_file:
shutil.copyfileobj(response, out_file)
如果有人认为我可能有一个进度条或者唯一的方法是使用不同的库,他们可以提供见解吗?我希望让代码非常简短,我只需要一些正在下载的文件的指示。感谢您提供的任何帮助!
如果响应包含 content-length
,您可以按块读取传入数据并计算完成百分比。不幸的是,"chunk" 响应的 Web 服务器并不总是提供内容长度,因此它并不总是有效。这是一个测试的例子。
import urllib.request
import sys
import io
try:
url = sys.argv[1]
except IndexError:
print("usage: test.py url")
exit(2)
resp = urllib.request.urlopen(url)
length = resp.getheader('content-length')
if length:
length = int(length)
blocksize = max(4096, length//100)
else:
blocksize = 1000000 # just made something up
print(length, blocksize)
buf = io.BytesIO()
size = 0
while True:
buf1 = resp.read(blocksize)
if not buf1:
break
buf.write(buf1)
size += len(buf1)
if length:
print('{:.2f}\r done'.format(size/length), end='')
print()
@tdelaney 的回答很好,但是在 Python 3.8 中你必须使用 getvalue() 方法而不是 read():
import io, urllib.request
with urllib.request.urlopen(Url) as Response:
Length = Response.getheader('content-length')
BlockSize = 1000000 # default value
if Length:
Length = int(Length)
BlockSize = max(4096, Length // 20)
print("UrlLib len, blocksize: ", Length, BlockSize)
BufferAll = io.BytesIO()
Size = 0
while True:
BufferNow = Response.read(BlockSize)
if not BufferNow:
break
BufferAll.write(BufferNow)
Size += len(BufferNow)
if Length:
Percent = int((Size / Length)*100)
print(f"download: {Percent}% {Url}")
print("Buffer All len:", len(BufferAll.getvalue()))
我正试图在万维网上搜索这个答案,但我觉得答案可能是否定的。我正在使用 Python 3.5 和一个名为 urllib.request
的库以及一个名为 urllib.request.urlopen(url)
的方法来打开 link 并下载文件。
由于文件超过 200MB,最好对此进行某种进度衡量。我正在查看 API here,但没有看到任何带钩子的参数。
这是我的代码:
downloadURL = results[3] #got this from code earlier up
rel_path = account + '/' + eventID + '_' + title + '.mp4'
filename_abs_path = os.path.join(script_dir, rel_path)
print('>>> Downloading >>> ' + title)
# Download .mp4 from a url and save it locally under `file_name`:
with urllib.request.urlopen(downloadURL) as response, open(filename_abs_path, 'wb') as out_file:
shutil.copyfileobj(response, out_file)
如果有人认为我可能有一个进度条或者唯一的方法是使用不同的库,他们可以提供见解吗?我希望让代码非常简短,我只需要一些正在下载的文件的指示。感谢您提供的任何帮助!
如果响应包含 content-length
,您可以按块读取传入数据并计算完成百分比。不幸的是,"chunk" 响应的 Web 服务器并不总是提供内容长度,因此它并不总是有效。这是一个测试的例子。
import urllib.request
import sys
import io
try:
url = sys.argv[1]
except IndexError:
print("usage: test.py url")
exit(2)
resp = urllib.request.urlopen(url)
length = resp.getheader('content-length')
if length:
length = int(length)
blocksize = max(4096, length//100)
else:
blocksize = 1000000 # just made something up
print(length, blocksize)
buf = io.BytesIO()
size = 0
while True:
buf1 = resp.read(blocksize)
if not buf1:
break
buf.write(buf1)
size += len(buf1)
if length:
print('{:.2f}\r done'.format(size/length), end='')
print()
@tdelaney 的回答很好,但是在 Python 3.8 中你必须使用 getvalue() 方法而不是 read():
import io, urllib.request
with urllib.request.urlopen(Url) as Response:
Length = Response.getheader('content-length')
BlockSize = 1000000 # default value
if Length:
Length = int(Length)
BlockSize = max(4096, Length // 20)
print("UrlLib len, blocksize: ", Length, BlockSize)
BufferAll = io.BytesIO()
Size = 0
while True:
BufferNow = Response.read(BlockSize)
if not BufferNow:
break
BufferAll.write(BufferNow)
Size += len(BufferNow)
if Length:
Percent = int((Size / Length)*100)
print(f"download: {Percent}% {Url}")
print("Buffer All len:", len(BufferAll.getvalue()))