2

因此,我知道服务器代码有效,因为该站点目前正在生产中并且运行良好。另一方面,我已经开发了一个测试脚本来对 API 进行单元测试。我正在尝试使用 HTTP POST 方法将 PDF 文件发送到服务器的 nginx -> gunicorn -> flask 应用程序环境。

服务器通过以下方式获取附件:

@app.route('<ObjectId:_id>/attachments', methods=['POST'])
@csrf.exempt
@opportunity_owner_required
@auth.login_required
@nocache
def upload_attachment(_id):
    upload = request.files.get('file')
    if not upload:
        abort(400, "Missing attached file.")

我尝试将pdf文件传递给服务器:

def test_add_opportunity_attachment(self):
    files = {'file': ("mozilla.pdf", open('%s/mozilla.pdf' % PATHTOFILE, 'rb'))}
    headers = {'Content-Type': 'application/pdf', "enctype": "multipart/form-data", "Content-Disposition":"attachment;filename=mozilla.pdf"}
    r=self.session.post(self.formatURL('/attachments'), headers=headers, files=files)
    assert r.status_code == 200

但我总是得到状态 400。

当使用 ngrep 跟踪输出时,我确实看到了似乎是通过网络传递的 PDF 的编码形式,但服务器看不到它。

请注意:由于其专有性质,某些信息丢失。但是测试功能中使用的所有功能都可以正常工作。formatURL 按预期对其进行格式化,并且 url 匹配。

4

1 回答 1

1

所以这个问题比我想象的要模糊一些。服务器上的一些后端逻辑,将文件保存到目录中,然后继续使用@app.route() 获取 URL 位置。我的本地副本缺少一些权限,因此当它尝试保存 PDF 文件时,上传会失败。

另一个问题,如 sigmavirus24 所述,自定义标头设置不正确,因此有效的最终版本如下所示:

def test_add_opportunity_attachment(self):
    payload = {"title": "Testing upload title", "description": "Testing upload description"}
    file_contents = open('%s/mozilla.pdf' % PATHTOFILE, 'rb')
    files = {'file': ('mozilla.pdf', file_contents)}
    r=self.session.post(self.formatURL('/attachments'), files=files, data=payload)
    if r.status_code != 200:
        assert r.status_code == 409 #Successful, but no duplicates allowed.
于 2013-04-16T13:16:09.243 回答