Python调用RESTful API时踩到的各种坑

本文介绍了如何解决使用Python的urllib2模块访问特定API接口时返回400错误的问题。通过对比cURL的成功请求与Python失败请求,发现问题在于参数传递方式的不同。最终通过使用json.dumps方法正确格式化参数解决了问题。

开篇首先推荐一款REST接口调试的利器,Chrome的扩展程序Advanced REST client,功能十分齐全!使用它来模拟访问接口可以获取到详尽的信息,借助它排查接口是否可用。

问题1:curl访问API成功,但是使用python的urllib2模块访问却返回400。
接口规则如下:
POST /v2.0/tokens HTTP/1.0
Host: 192.168.85.183:35357
Content-Type: application/json
Accept: application/json
{
    "auth":{
        "passwordCredentials":{
            "username":"alan",
            "password":"admin"
        },
        "tenantName":"swifttenant1"
    }
}

cURL模拟访问实现如下:

curl -s -d '{"auth":{"passwordCredentials":{"username":"alan","password":"admin"},"tenantName":"swifttenant1"}}' -H "Content-type: application/json" http://192.168.85.183:35357/v2.0/tokens | python -mjson.tool
后台日志:
2013-09-03 05:34:20.133 23199 INFO access [-] 192.168.85.183 - - [03/Sep/2013:12:34:20 +0000] "POST http://192.168.85.183:35357/v2.0/tokens HTTP/1.0" 200 2711

python使用urllib2模块:
#!/usr/bin/python
import urllib
import urllib2

def curl_keystone_failed():
    url = 'http://192.168.85.183:35357/v2.0/tokens'
    values = {"auth":{"passwordCredentials":{"username":"alan","password":"admin"},"tenantName":"swifttenant1"}}
    # 这里千万不要仿照网上的方法进行加密,因为它本身就没有加密的一个过程!不然还是会返回400的!
    # params = urllib.urlencode(values)
    params = str(values)
    headers = {"Content-type":"application/json","Accept": "application/json"}
    req = urllib2.Request(url, params, headers)
    response = urllib2.urlopen(req)
    print response.read()

if __name__ == "__main__":
    curl_keystone_failed()
后台日志:
2013-09-03 05:43:11.928 23199 INFO access [-] 192.168.85.185 - - [03/Sep/2013:12:43:11 +0000] "POST http://192.168.85.183:35357/v2.0/tokens HTTP/1.0" 400 244


随后使用httplib重写方法,查看返回的报错信息可发现,它没有获取到一个有效json格式的内容,原来python传输的时候是严格判定内容的type的。使用json来dumps一下可以解决问题!

def curl_keystone():
    url = 'http://192.168.85.183:35357/v2.0/tokens'
    values = {"auth":{"passwordCredentials":{"username":"alan","password":"admin"},"tenantName":"swifttenant1"}}
    params = json.dumps(values)
    headers = {"Content-type":"application/json","Accept": "application/json"}
    req = urllib2.Request(url, params, headers)
    response = urllib2.urlopen(req)
    print response.read()

后台日志: 
2013-09-03 05:50:52.884 23199 INFO access [-] 192.168.85.185 - - [03/Sep/2013:12:50:52 +0000] "POST http://192.168.85.183:35357/v2.0/tokens HTTP/1.0" 200 2711 


转载于:https://my.oschina.net/alanlqc/blog/158954

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值