【问题标题】:Python Requests form-encodes parameters but not URLsPython请求表单编码参数而不是URL
【发布时间】:2019-10-07 07:42:49
【问题描述】:

我正在通过 Python 3 和 Requests 使用 Microsoft Graph API。以下代码有效:

r = graph_session.get(graph_endpoint + '''/groups?$filter=groupTypes/any(c:c+eq+'Unified')''')
print(r.url)

>>> https://graph.microsoft.com/v1.0/groups?$filter=groupTypes/any(c:c+eq+'Unified')

但是,这不起作用:

parameters = {'$filter': '''groupTypes/any(c:c+eq+'Unified')'''}
r = graph_session.get(graph_endpoint + '/groups', params=parameters)
print(r.url)

>>> https://graph.microsoft.com/v1.0/groups?%24filter=groupTypes%2Fany%28c%3Ac%2Beq%2B%27Unified%27%29

为什么后一种看起来更干净的方法会产生 400 错误(Bad request)?好像是编码问题。

【问题讨论】:

  • Unified的结束引用的位置吗? parameters = {'$filter': '''groupTypes/any(c:c+eq+'Unified')'''}
  • @Kamal 我不这么认为。它最终应该是$filter=groupTypes/any(c:c+eq+'Unified')
  • 是的,你在工作的情况下使用了它,但在不工作的情况下,你已经完成了...'Unified)'''',它的结尾是...%27Unified%29%27。但你希望它为...%27Unified%27%29
  • @Kamal 哎呀,这只是一个错字。 (我再次尝试确定;它不起作用。)我编辑了帖子;谢谢。

标签: python-3.x python-requests microsoft-graph-api


【解决方案1】:

这似乎是一个编码问题。

确实如此,在这种情况下,过滤器表达式正在被编码(即by design),Microsoft Graph 返回以下错误:

{
    "error": {
        "code": "BadRequest",
        "message": "Invalid filter clause",
        //...
    }
}

如果params 参数作为string 传递,则可以防止编码:

parameters = {'$filter': '''groupTypes/any(c:c+eq+'Unified')'''}
parameters_str = "&".join("%s=%s" % (k, v) for k, v in parameters.items())
r = graph_session.get(graph_endpoint + '/groups', params=parameters_str, headers=headers)

请参阅this answer 了解其他选项。

【讨论】:

  • 谢谢!虽然不太灵活,parameters = '''$filter:groupTypes/any(c:c+eq+'Unified')''' 也可以。此外,docs 提到传递字符串将避免表单编码。我不知道“form-encoded”和“url encoding”这两个神奇的词。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2011-08-21
  • 1970-01-01
  • 1970-01-01
  • 2011-04-21
  • 1970-01-01
  • 2017-02-13
  • 2014-03-14
相关资源
最近更新 更多