包含json.dumps时,python请求授权失败

时间:2014-12-19 03:40:20

标签: python json box-api

编辑:

如何在python中复制以下curl请求?

curl https://api.box.com/2.0/files/content
-H "Authorization: Bearer TOKEN" -d '{"name": "Wolves owners.ppt", "parent": {"id": "2841136315"}, "size": 15243}' 
-X OPTIONS`

当我将json.dump引入请求授权失败时

以下请求正文未正确格式化。它只是一个python字典,嵌套属性没有通过。

h.kwargs['body'] = {"size": 45810, "parent": {"id": "2841136315"}, "name": "83db7037-2037-4f38-8349-255299343e6d"}

first = requests.options(
        h.kwargs['url'], headers=h.headers, data=h.kwargs['body']
    )

查看正文设置为size=45810&parent=id&name=83db7037-2037-4f38-8349-255299343e6d

的回复

标题是

`{'Content-Length': '62', 'Content-Type': 'application/x-www-form-urlencoded', 'Accept-Encoding': 'gzip, deflate', 'Authorization': 'Bearer TOKEN', 'Accept': '*/*', 'User-Agent': 'python...'}`

在第二个请求上,一旦引入了json.dump,授权就会失败401

second = requests.options(
        h.kwargs['url'], headers=h.headers, data=json.dumps(h.kwargs['body'])
    )

标题是

`{'Content-Length': '95', 'Accept': '*/*', 'User-Agent': 'python...', 'Accept-Encoding': 'gzip, deflate', 'Authorization': 'Bearer TOKEN'}`

如何在不弄乱授权的情况下格式化正文以进行通话?

我已经尝试将第二个请求的内容类型设置为json,但它不起作用

1 个答案:

答案 0 :(得分:2)

修改2

我发现id字段是必需的。您的请求没有id的值(父文件夹的ID),这就是您接收HTTP状态400的原因。这里的API似乎有点奇怪;为什么父文件夹id需要指定两次?

无论如何,所需的最低字段为parentidnamesize不是必需的,但如果提供了它们的值,则会检查它们的值,即验证名称并将大小与配额和可用存储空间进行比较。

我还发现当省略id字段时,curl和Python会生成相同的400响应。也许你在卷曲测试中包含了id

最后,Content-type标题没有影响。

这是经过修改的Python代码。

import requests
import json

url = 'https://api.box.com/2.0/files/content'
h.headers = {'Authorization':'Bearer TOKEN'}
parent_folder_id = "2843500681"    # replace with your folder id

h.kwargs = {"name": "Wolves owners.ppt",
            "parent": {"id": parent_folder_id},
            "id": parent_folder_id,
            "size": 15243}

resp = requests.options(url, headers=h.headers, data=json.dumps(h.kwargs))

编辑1:问题更新后

发送与curl相同的请求:

import requests

url = 'https://api.box.com/2.0/files/content'
h.headers = {'Content-type': 'application/x-www-form-urlencoded',
             'Authorization':'Bearer TOKEN'}    

h.kwargs = {"name": "Wolves owners.ppt",
            "parent": {"id": "2841136315"},
            "size": 15243}

resp = requests.options(url, headers=h.headers, data=json.dumps(h.kwargs))

请注意,这会像curl一样将Content-type标头显式设置为application/x-www-form-urlencoded。否则请求中没有显着差异。

另请注意,此请求中的正文实际上不是application/x-www-form-urlencoded,它只是一个字符串。将Content-type设置为application/json似乎更合适。

这是卷曲请求:

OPTIONS /2.0/files/content HTTP/1.1
User-Agent: curl/7.32.0
Host: api.box.com
Accept: */*
Authorization: Bearer TOKEN
Content-Length: 76
Content-Type: application/x-www-form-urlencoded

{"name": "Wolves owners.ppt", "parent": {"id": "2841136315"}, "size": 15243}

这是上面代码生成的请求:

OPTIONS /2.0/files/content HTTP/1.1
Host: api.box.com
Content-Length: 76
Accept-Encoding: gzip, deflate
Accept: */*
User-Agent: python-requests/2.5.0 CPython/2.7.5 Linux/3.17.4-200.fc20.x86_64
Connection: keep-alive
Content-type: application/x-www-form-urlencoded
Authorization: Bearer TOKEN

{"name": "Wolves owners.ppt", "parent": {"id": "2841136315"}, "size": 15243}