在python查询参数中使用%20而不是+作为空格

时间:2014-02-17 08:21:27

标签: python python-requests

我使用python请求(http://requests.readthedocs.org/en/latest/)编写了以下python脚本:

import requests

payload = {'key1': 'value  1', 'key2': 'value 2'}
headers = {'Content-Type': 'application/json;charset=UTF-8'}
r = requests.get("http://example.com/service", params=payload, headers=headers, 
             auth=("admin", "password"))

如果我查看服务器的访问日志,传入的请求是: ?/服务键1 =值++ 1安培;键2 =值+ 2

但是,服务器需要...... value%20%201& ...

我已经读过使用+作为空格的占位符是内容类型application / x-www-form-urlencoded的一部分,但显然我已经请求了application / json。

有人知道如何使用%20作为pythons请求的查询参数中的空格吗?

7 个答案:

答案 0 :(得分:7)

为了跟进@ WeaselFox的回答,他们引入了一个补丁,接受quote_via关键字参数urllib.parse.urlencode。现在你可以这样做:

import requests
import urllib

payload = {'key1': 'value  1', 'key2': 'value 2'}
headers = {'Content-Type': 'application/json;charset=UTF-8'}
params = urllib.parse.urlencode(payload, quote_via=urllib.parse.quote)
r = requests.get("http://example.com/service", params=params, headers=headers,
    auth=("admin", "password"))

答案 1 :(得分:1)

我们可以使用urllib2.Request来调用url

import urllib2

send_params = {'key1': 'value  1', 'key2': 'value 2'}
new_send_params = []
for (k, v) in send_params.items():
    new_send_params.append(k + "=" + urllib2.quote(v))

url = 'http://example.com/service?'+ '&'.join(new_send_params)
req = urllib2.Request(url)
response = urllib2.urlopen(req)
print "Request URL: " + url
#Request URL: http://example.com/service?key1=value%20&key2=value%202
print response.read()
#Python Master Request handler 2016-07-04 16:05:19.928132 . Your request path is  /service?key1=value%20&key2=value%202

答案 2 :(得分:1)

PYTHON 2.7

  • 使用 urllib.quote

  • 覆盖 urllib.quote_pluse
  • urlencoder使用urllib.quote_pluse对数据进行编码。

import requests
import urllib
urllib.quote_plus=urllib.quote # A fix for urlencoder to give %20 
payload = {'key1': 'value  1', 'key2': 'value 2'}
headers = {'Content-Type': 'application/json;charset=UTF-8'}
param = urllib.urlencode(payload) #encodes the data
r = requests.get("http://example.com/service", params=param, headers=headers, 
             auth=("admin", "password"))

输出

the output for param = urllib.urlencode(payload)
'key2=value%202&key1=value%20%201' 

答案 3 :(得分:0)

试一试。

import urllib
urllib.urlencode(params)

http://docs.python.org/2/library/urllib.html#urllib.urlencode

答案 4 :(得分:0)

我只找到urllib.parse.quote,它可以将空格替换为%20

但是quote无法转换字典。

所以,我们必须提前使用quote转换字典。


#for python3
from urllib.parse import quote

payload = {'key1': 'value  1', 'key2': 'value 2'}

newpayload = {}
for (k, v) in payload.items():
    newpayload[quote(k)] = quote(v)
print(newpayload)
#print result: {'key1': 'value%20%201', 'key2': 'value%202'}
# Now, you can use it in requests

答案 5 :(得分:0)

这似乎是python中已知的错误/问题:

http://bugs.python.org/issue13866

我认为您必须使用urlliburllib2解决此问题并避免请求。请查看错误报告,了解有关如何执行此操作的一些提示。

答案 6 :(得分:0)

from urllib.parse import urlencode

def to_query_string(params):
    return urlencode(params, doseq=True).replace('+', '%20')

<罢工>

您可以将字符串而不是字典传递给params,然后手动处理空格。

也许有点像

def to_query_string(p, s=''):
    for k in p:
        v = p[k]
        if isinstance(v, str):
            s += f'{k}={v}&'.replace(' ', '%20')
        elif isinstance(v, int):
            s += f'{k}={v}&'
        elif isinstance(v, list):
            for i in v:
                s += f'{k}={i}&'
    return s[:-1]  # remove last '&'
可以用作
min = 10
max = 30
params = {'query': f'score between {min} and {max}', 'limit': 1, 'information': ['name', 'location']}
response = get('/api/dogs', params=to_query_string(params))