【问题标题】:Twisted upload muliple files key error扭曲上传多个文件关键错误
【发布时间】:2017-11-22 16:54:50
【问题描述】:

我正在尝试在 Python 3.6 中编写一个 Twisted Webserver,它可以上传多个文件,但对于 Python 和 Web 来说都是相当新的我遇到了一个我不明白的问题,我也没有找到任何好的例子与多文件上传有关。

我得到以下代码

from twisted.web import server, resource
from twisted.internet import reactor, endpoints
import cgi


class Counter(resource.Resource):
    isLeaf = True
    numberRequests = 0

    def render_GET(self, request):
        print("GET " + str(self.numberRequests))
        self.numberRequests += 1
        # request.setHeader(b"content-type", b"text/plain")
        # content = u"I am request #{}\n".format(self.numberRequests)
        content = """<html>
        <body>
        <form enctype="multipart/form-data" method="POST">
            Text: <input name="text1" type="text" /><br />
            File: <input name="file1" type="file" multiple /><br />
            <input type="submit" />
        </form>
        </body>
        </html>"""
        print(request.uri)


        return content.encode("ascii")

    def render_POST(selfself, request):
        postheaders = request.getAllHeaders()
        try:
            postfile = cgi.FieldStorage(
                fp=request.content,
                headers=postheaders,
                environ={'REQUEST_METHOD': 'POST',
                        # 'CONTENT_TYPE': postheaders['content-type'], Gives builtins.KeyError: 'content-type'
                         }
            )
        except Exception as e:
            print('something went wrong: ' + str(e))

        filename = postfile["file"].filename #file1 tag also does not work
        print(filename)

        file = request.args["file"][0] #file1 tag also does not work



endpoints.serverFromString(reactor, "tcp:1234").listen(server.Site(Counter()))

reactor.run()

错误日志

C:\Users\theuser\AppData\Local\conda\conda\envs\py36\python.exe C:/Users/theuser/PycharmProjects/myproject/twweb.py
GET 0
b'/'
# My comment POST starts here
Unhandled Error
Traceback (most recent call last):
  File "C:\Users\theuser\AppData\Local\conda\conda\envs\py36\lib\site-packages\twisted\web\http.py", line 1614, in dataReceived
    finishCallback(data[contentLength:])
  File "C:\Users\theuser\AppData\Local\conda\conda\envs\py36\lib\site-packages\twisted\web\http.py", line 2029, in _finishRequestBody
    self.allContentReceived()
  File "C:\Users\theuser\AppData\Local\conda\conda\envs\py36\lib\site-packages\twisted\web\http.py", line 2104, in allContentReceived
    req.requestReceived(command, path, version)
  File "C:\Users\theuser\AppData\Local\conda\conda\envs\py36\lib\site-packages\twisted\web\http.py", line 866, in requestReceived
    self.process()
--- <exception caught here> ---
  File "C:\Users\theuser\AppData\Local\conda\conda\envs\py36\lib\site-packages\twisted\web\server.py", line 195, in process
    self.render(resrc)
  File "C:\Users\theuser\AppData\Local\conda\conda\envs\py36\lib\site-packages\twisted\web\server.py", line 255, in render
    body = resrc.render(self)
  File "C:\Users\theuser\AppData\Local\conda\conda\envs\py36\lib\site-packages\twisted\web\resource.py", line 250, in render
    return m(request)
  File "C:/Users/theuser/PycharmProjects/myproject/twweb.py", line 42, in render_POST
    filename = postfile["file"].filename #file1 tag also does not work
  File "C:\Users\theuser\AppData\Local\conda\conda\envs\py36\lib\cgi.py", line 604, in __getitem__
    raise KeyError(key)
builtins.KeyError: 'file'

我不明白如何获取一个或多个文件,因此我可以在 render_POST 中提交表单后保存上传的文件。这个帖子SO似乎没有这个问题。最终的应用程序应该能够为多个用户异步执行此操作,但在此之前我很乐意让一个简单的应用程序正常工作。

在带有 Python 3.6 的 Windows 10 上使用 conda

【问题讨论】:

    标签: python-3.x twisted


    【解决方案1】:

    FieldStorage 在 Python 3+ 中返回一个 dict,其键为字节,而不是字符串。所以你必须像这样访问密钥:

    postfile[ b"file" ]
    

    请注意,密钥附加了b""。如果您是 Python 新手并且不知道 Python 3 和 2 字符串之间的变化,这会有点令人困惑。

    另外,我不久前回答了similar question,但无法让它在 Python 3.4 上正常工作,但我不记得究竟是什么不工作。希望您在使用 3.6 时不会遇到任何问题。

    【讨论】:

    • 使用 b'content-type' 我通过了 cgi.FieldStorage 中的问题。但是我以后无法获取文件的字段,它解析出 2 个键名和文件名,其中包含字段,但我无法将它们从中取出。我切换到 Python 2.7,然后我可以让它工作,所以我仍然认为 3.4 的问题存在于 3.6
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2011-07-08
    • 1970-01-01
    • 2016-08-09
    • 1970-01-01
    • 1970-01-01
    • 2017-04-25
    • 1970-01-01
    相关资源
    最近更新 更多