提问人:Anon 提问时间:3/12/2014 最后编辑:Anon 更新时间:10/23/2015 访问量:41692
Python - 使用请求将文件直接下载到内存
Python - Download File Using Requests, Directly to Memory
问:
目标是从 Internet 下载文件,并从中创建文件对象或类似文件的对象,而无需接触硬盘驱动器。这只是我的知识,想知道它是否可行或实用,特别是因为我想看看我是否可以规避必须编写文件删除行。
这就是我通常从网络上下载内容并将其映射到内存的方式:
import requests
import mmap
u = requests.get("http://www.pythonchallenge.com/pc/def/channel.zip")
with open("channel.zip", "wb") as f: # I want to eliminate this, as this writes to disk
f.write(u.content)
with open("channel.zip", "r+b") as f: # and his as well, because it reads from disk
mm = mmap.mmap(f.fileno(), 0)
mm.seek(0)
print mm.readline()
mm.close() # question: if I do not include this, does this become a memory leak?
答:
11赞
poke
3/12/2014
#1
你的答案是。内容在内存中。除非将其写入文件,否则它不会存储在磁盘上。u.content
评论
1赞
Anon
3/12/2014
你如何获取u.content,并创建一个像对象一样的文件(mmap 所做的),而不把它写到磁盘上?
50赞
jfs
3/14/2014
#2
r.raw
(HTTPResponse
) 已经是一个类似文件的对象(只需传递):stream=True
#!/usr/bin/env python
import sys
import requests # $ pip install requests
from PIL import Image # $ pip install pillow
url = sys.argv[1]
r = requests.get(url, stream=True)
r.raw.decode_content = True # Content-Encoding
im = Image.open(r.raw) #NOTE: it requires pillow 2.8+
print(im.format, im.mode, im.size)
一般来说,如果你有字节字符串;你可以把它包装成 ,在不接触磁盘的情况下得到一个类似文件的对象:f = io.BytesIO(r.content)
#!/usr/bin/env python
import io
import zipfile
from contextlib import closing
import requests # $ pip install requests
r = requests.get("http://www.pythonchallenge.com/pc/def/channel.zip")
with closing(r), zipfile.ZipFile(io.BytesIO(r.content)) as archive:
print({member.filename: archive.read(member) for member in archive.infolist()})
您不能直接传递到,因为前者是不可查找的文件。r.raw
ZipFile()
我想看看我是否可以规避必须编写文件删除行
tempfile
可以自动删除文件 f = tempfile。后台处理TemporaryFile();f.write(u.content)。
直到调用方法(如果某些 api 需要真实文件)或到达;数据保存在内存中。即使数据写入磁盘;文件关闭后立即删除。.fileno()
maxsize
13赞
Anon
3/14/2014
#3
这就是我最终所做的。
import zipfile
import requests
import StringIO
u = requests.get("http://www.pythonchallenge.com/pc/def/channel.zip")
f = StringIO.StringIO()
f.write(u.content)
def extract_zip(input_zip):
input_zip = zipfile.ZipFile(input_zip)
return {i: input_zip.read(i) for i in input_zip.namelist()}
extracted = extract_zip(f)
评论