[英]Mocking download of a file using Python requests and responses
我有一些 python 代碼,它使用requests從 URL 成功下載圖像,並將其保存到/tmp/
。 我想測試它應該做什么。 我正在使用響應來測試 JSON 文件的獲取,但我不確定如何模擬獲取文件的行為。
我認為它類似於模擬標准響應,如下所示,但我想我對如何將body
設置為文件感到茫然......
@responses.activate
def test_download():
responses.add(responses.GET, 'http://example.org/images/my_image.jpg',
body='', status=200,
content_type='image/jpeg')
#...
更新:按照 Ashafix 的評論,我正在嘗試這個(python 3):
from io import BytesIO
@responses.activate
def test_download():
with open('tests/images/tester.jpg', 'rb') as img1:
imgIO = BytesIO(img1.read())
responses.add(responses.GET, 'http://example.org/images/my_image.jpg',
body=imgIO, status=200,
content_type='image/jpeg')
imgIO.seek(0)
#...
但是,隨后,當我正在測試的代碼嘗試執行我收到的請求時:
a bytes-like object is required, not '_io.BytesIO'
感覺幾乎是對的,但我很難過。
更新 2:嘗試遵循 Steve Jessop 的建議:
@responses.activate
def test_download():
with open('tests/images/tester.jpg', 'rb') as img1:
responses.add(responses.GET, 'http://example.org/images/my_image.jpg',
body=img1.read(), status=200,
content_type='image/jpeg')
#...
但這一次被測試的代碼提出了這個:
I/O operation on closed file.
當然圖像應該仍然在with
塊內打開嗎?
更新 3:我正在測試的代碼是這樣的:
r = requests.get(url, stream=True)
if r.status_code == 200:
with open('/tmp/temp.jpg', 'wb') as f:
r.raw.decode_content = True
shutil.copyfileobj(r.raw, f)
似乎最后的shutil
行正在生成“對已關閉文件的 I/O 操作”。 錯誤。 我不太了解這一點 - 文件的流媒體 - 不知道如何最好地模擬這種行為,以測試下載的文件是否保存到/tmp/
。
您可能需要將stream=True
傳遞給responses.add
調用。 類似的東西:
@responses.activate
def test_download():
with open("tests/images/tester.jpg", "rb") as img1:
responses.add(
responses.GET,
"http://example.org/images/my_image.jpg",
body=img1.read(),
status=200,
content_type="image/jpeg",
stream=True,
)
首先,總結一下我現在過長的問題......我正在測試一些類似的代碼:
def download_file(url):
r = requests.get(url, stream=True)
if r.status_code == 200:
filename = os.path.basename(url)
with open('/tmp/%s' % filename, 'wb') as f:
r.raw.decode_content = True
shutil.copyfileobj(r.raw, f)
return filename
它下載一個圖像,並流式傳輸它,將其保存到/tmp/
。 我想模擬這個請求,這樣我就可以測試其他東西。
@responses.activate
def test_downloads_file(self):
url = 'http://example.org/test.jpg'
with open('tests/images/tester.jpg', 'rb') as img:
responses.add(responses.GET, url,
body=img.read(), status=200,
content_type='image/jpg',
adding_headers={'Transfer-Encoding': 'chunked'})
filename = download_file(url)
# assert things here.
一旦我找到了為此使用open()
的方法,我仍然收到“關閉文件上的 I/O 操作”。 從shutil.copyfileobj()
。 停止此操作的是添加Transfer-Encoding
標頭,當我發出真正的請求時,該標頭出現在標頭中。
非常歡迎對其他更好的解決方案的任何建議!
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.