繁体   English   中英

读取文件数据而不将其保存在 Flask 中

[英]Read file data without saving it in Flask

我正在编写我的第一个烧瓶应用程序。 我正在处理文件上传,基本上我想要的是在不保存的情况下读取上传文件的数据/内容,然后将其打印在结果页面上。 是的,我假设用户总是上传一个文本文件。

这是我正在使用的简单上传功能:

@app.route('/upload/', methods=['GET', 'POST'])
def upload():
    if request.method == 'POST':
        file = request.files['file']
        if file:
            filename = secure_filename(file.filename)
            file.save(os.path.join(app.config['UPLOAD_FOLDER'], filename))
            a = 'file uploaded'

    return render_template('upload.html', data = a)

现在,我正在保存文件,但我需要的是“a”变量来包含文件的内容/数据......有什么想法吗?

FileStorage包含stream字段。 这个对象必须扩展 IO 或文件对象,所以它必须包含read和其他类似的方法。 FileStorage还扩展了stream字段对象属性,因此您可以使用file.read()代替file.stream.read() 您也可以使用带有dst参数的save参数作为StringIO或其他 IO 或文件对象将FileStorage.stream复制到另一个 IO 或文件对象。

请参阅文档: http : //flask.pocoo.org/docs/api/#flask.Request.fileshttp://werkzeug.pocoo.org/docs/datastructures/#werkzeug.datastructures.FileStorage

如果您想使用标准的 Flask 内容 - 如果上传的文件大小 > 500kb,则无法避免保存临时文件。 如果它小于 500kb - 它将使用“BytesIO”,它将文件内容存储在内存中,如果它超过 500kb - 它会将内容存储在 TemporaryFile() 中(如werkzeug 文档中所述)。 在这两种情况下,您的脚本都会阻塞,直到收到整个上传的文件。

我发现解决此问题的最简单方法是:

1) 创建您自己的类似文件的 IO 类,您可以在其中对传入数据进行所有处理

2)在你的脚本中,用你自己的覆盖请求类:

class MyRequest( Request ):
  def _get_file_stream( self, total_content_length, content_type, filename=None, content_length=None ):
    return MyAwesomeIO( filename, 'w' )

3) 用你自己的替换 Flask 的 request_class:

app.request_class = MyRequest

4) 去喝点啤酒 :)

我分享我的解决方案(假设一切都已配置为连接到烧瓶中的谷歌存储桶)

from google.cloud import storage

@app.route('/upload/', methods=['POST'])
def upload():
    if request.method == 'POST':
        # FileStorage object wrapper
        file = request.files["file"]                    
        if file:
            os.environ["GOOGLE_APPLICATION_CREDENTIALS"] = app.config['GOOGLE_APPLICATION_CREDENTIALS']
            bucket_name = "bucket_name" 
            storage_client = storage.Client()
            bucket = storage_client.bucket(bucket_name)
            # Upload file to Google Bucket
            blob = bucket.blob(file.filename) 
            blob.upload_from_string(file.read())

我的帖子

直接到 Flask 中的 Google Bucket

我试图做完全相同的事情,打开一个文本文件(实际上是 Pandas 的 CSV)。 不想复制它,只想打开它。 form-WTF 有一个不错的文件浏览器,但它会打开文件并创建一个临时文件,将其显示为内存流。 在引擎盖下做一些工作,

form = UploadForm() 
 if form.validate_on_submit(): 
      filename = secure_filename(form.fileContents.data.filename)  
      filestream =  form.fileContents.data 
      filestream.seek(0)
      ef = pd.read_csv( filestream  )
      sr = pd.DataFrame(ef)  
      return render_template('dataframe.html',tables=[sr.to_html(justify='center, classes='table table-bordered table-hover')],titles = [filename], form=form) 

我分享我的解决方案,使用熊猫


@app.route('/upload/', methods=['POST'])
def upload():
    if request.method == 'POST':
        # FileStorage object wrapper
        file = request.files["file"]                    
        if file:
            df = pd.read_excel(files_excel["file"])

基于@tbicr 的一个很好的答案,最简单的形式归结为:

for line in request.files.get('file'):
   print("Next line: " + line)

我正在编写我的第一个烧瓶应用程序。 我正在处理文件上传,基本上我想要的是在不保存的情况下读取上传文件的数据/内容,然后将其打印在结果页面上。 是的,我假设用户始终上传一个文本文件。

这是我正在使用的简单上传功能:

@app.route('/upload/', methods=['GET', 'POST'])
def upload():
    if request.method == 'POST':
        file = request.files['file']
        if file:
            filename = secure_filename(file.filename)
            file.save(os.path.join(app.config['UPLOAD_FOLDER'], filename))
            a = 'file uploaded'

    return render_template('upload.html', data = a)

现在,我正在保存文件,但是我需要的是一个'a'变量来包含文件的内容/数据..有什么想法吗?

在功能上

def handleUpload():
    if 'photo' in request.files:
        photo = request.files['photo']
        if photo.filename != '':      
            image = request.files['photo']  
            image_string = base64.b64encode(image.read())
            image_string = image_string.decode('utf-8')
            #use this to remove b'...' to get raw string
            return render_template('handleUpload.html',filestring = image_string)
    return render_template('upload.html')

在 html 文件中

<html>
<head>
    <title>Simple file upload using Python Flask</title>
</head>
<body>
    {% if filestring %}
      <h1>Raw image:</h1>
      <h1>{{filestring}}</h1>
      <img src="data:image/png;base64, {{filestring}}" alt="alternate" />.
    {% else %}
      <h1></h1>
    {% endif %}
</body>

如果我们想将内存文件转储到磁盘。 可以使用此代码

  if isinstanceof(obj,SpooledTemporaryFile):
    obj.rollover()

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM