我已经尝试构建一个API超过4个小时了,我搜索并询问了所有可以找到的地方,但找不到帮助。问题在于处理POST请求的级别。我尝试使用NodeJS(验证和表达(以及中间件))和Python(烧瓶,瓶子),但仍然无法理解为什么我在python中得到一个带有express或None的空对象。我的瓶子有以下代码
1 from bottle import run, Bottle, post, request, redirect
2 import json
3
4 pika = Bottle()
5
6 @post("/shorturl")
7 def shorten():
8 data = request.json
9 #data = json.dumps(rdata)
10 print(data)
11 return f"You posted {data}"
12
13 run(host="localhost", port=3000, debug=True)
我一开始就有以下代码(我已删除并从头开始重新启动)-您可以找到tweet here。
分别使用request.get_json()
和request.json()
时,我无法从烧瓶和瓶子中获得None,这是我从文档中找到的方法。
任何帮助表示赞赏。
谢谢
答案 0 :(得分:1)
您的python代码似乎是正确的,因为我尝试了并且有效。 要进行故障排除,您可以插入:
print(request.headers['Content-Type']) #output should be: application/json'
print(request.body.read()) #output should be like: b'{"key":"value"}'
我使用Postman,当我第一次尝试时,我犯了一个错误,即选择正文 form 而不是 raw 。在Postman中,您必须在标头中手动编写 Content-Type:appliction / json 并将json插入为 raw 。 我认为在Restler中,它是相似的(我从未使用过Restler)。
因此,如果您必须手动配置它,请确保标头包含'Content-Type':'application / json' 并且您的身体设置为原始,看起来像这样。 例如,如果选择了 form-data ,邮递员将不会使用手动设置的标头,而 print(request.header ['Content-Type'])会输出一些内容像这样: multipart / form-data; boundary = -------------------------- 742283902180513961059188
可以想象Restler有同样的网罗。
答案 1 :(得分:1)
这是处理api动态路由的一种方法。现在,您只需将方法添加到API类中,瓶子应用程序会自动选择这些方法。我将POST和GET合并为一个方法字符串,以将查询参数和表单合并为一个有效载荷,您可以通过self.payload
import ujson as json
from login import User
def check(data):
try:
if isinstance(data, (str,bytes)):
return json.loads(data)
except:
return data
return data
def merge_dicts(*args):
result = {}
for dictionary in args:
result.update(dictionary or {})
return result
class API:
def __init__(self, payload, user):
self.payload = payload
self.option = ''
self.request = None
@classmethod
def bot(cls, request, option, user):
payload = merge_dicts(dict(request.forms), dict(request.query.decode())) # merge query and form inputs
slf = cls(payload, user)
slf.request = request
slf.option = str(option)
return slf
def test(self): # localhost/api/test
return self.payload
@get('/api/<command>')
@post('/api/<command>')
@get('/api/<command>/<option>')
@post('/api/<command>/<option>')
def routeapi(command='', option=''):
user = User()
wapi = API.bot(request, option, user)
func = getattr(wapi, f"{command}", None)
if callable(func):
result = func()
if result:
if request.method == 'GET':
response.headers['Content-Type'] = 'application/json'
response.headers['Cache-Control'] = 'no-cache'
return {command:json.check(result)}
else:
return {command:None}