使用Python & Flask 实现RESTful Web API的实例


Posted in Python onSeptember 19, 2017

环境安装:

sudo pip install flask

Flask 是一个Python的微服务的框架,基于Werkzeug, 一个 WSGI 类库。

Flask 优点:

Written in Python (that can be an advantage);
Simple to use;
Flexible;
Multiple good deployment options;
RESTful request dispatching

RESOURCES

一个响应 /articles 和 /articles/:id的 API 服务:

from flask import Flask, url_for
app = Flask(__name__)

@app.route('/')
def api_root():
 return 'Welcome'

@app.route('/articles')
def api_articles():
 return 'List of ' + url_for('api_articles')

@app.route('/articles/<articleid>')
def api_article(articleid):
 return 'You are reading ' + articleid

if __name__ == '__main__':
 app.run()

请求:

curl http://127.0.0.1:5000/

响应:

GET /
Welcome

GET /articles
List of /articles

GET /articles/123
You are reading 123

REQUESTS

GET Parameters

from flask import request

@app.route('/hello')
def api_hello():
 if 'name' in request.args:
  return 'Hello ' + request.args['name']
 else:
  return 'Hello John Doe'

请求:

GET /hello
Hello John Doe

GET /hello?name=Luis
Hello Luis

Request Methods (HTTP Verbs)

@app.route('/echo', methods = ['GET', 'POST', 'PATCH', 'PUT', 'DELETE'])
def api_echo():
 if request.method == 'GET':
  return "ECHO: GET\n"

 elif request.method == 'POST':
  return "ECHO: POST\n"

 elif request.method == 'PATCH':
  return "ECHO: PACTH\n"

 elif request.method == 'PUT':
  return "ECHO: PUT\n"

 elif request.method == 'DELETE':
  return "ECHO: DELETE"

请求指定request type:

curl -X PATCH http://127.0.0.1:5000/echo
GET /echo
ECHO: GET

POST /ECHO
ECHO: POST

Request Data & Headers

from flask import json

@app.route('/messages', methods = ['POST'])
def api_message():

 if request.headers['Content-Type'] == 'text/plain':
  return "Text Message: " + request.data

 elif request.headers['Content-Type'] == 'application/json':
  return "JSON Message: " + json.dumps(request.json)

 elif request.headers['Content-Type'] == 'application/octet-stream':
  f = open('./binary', 'wb')
  f.write(request.data)
    f.close()
  return "Binary message written!"

 else:
  return "415 Unsupported Media Type ;)"

请求指定content type:

curl -H "Content-type: application/json" \
-X POST http://127.0.0.1:5000/messages -d '{"message":"Hello Data"}'

curl -H "Content-type: application/octet-stream" \
-X POST http://127.0.0.1:5000/messages --data-binary @message.bin

RESPONSES

from flask import Response

@app.route('/hello', methods = ['GET'])
def api_hello():
 data = {
  'hello' : 'world',
  'number' : 3
 }
 js = json.dumps(data)

 resp = Response(js, status=200, mimetype='application/json')
 resp.headers['Link'] = 'http://luisrei.com'

 return resp

查看response HTTP headers:

curl -i http://127.0.0.1:5000/hello

优化代码:

from flask import jsonify

使用

resp = jsonify(data)
resp.status_code = 200

替换

resp = Response(js, status=200, mimetype='application/json')

Status Codes & Errors

@app.errorhandler(404)
def not_found(error=None):
 message = {
   'status': 404,
   'message': 'Not Found: ' + request.url,
 }
 resp = jsonify(message)
 resp.status_code = 404

 return resp

@app.route('/users/<userid>', methods = ['GET'])
def api_users(userid):
 users = {'1':'john', '2':'steve', '3':'bill'}
 
 if userid in users:
  return jsonify({userid:users[userid]})
 else:
  return not_found()

请求:

GET /users/2
HTTP/1.0 200 OK
{
"2": "steve"
}

GET /users/4
HTTP/1.0 404 NOT FOUND
{
"status": 404,
"message": "Not Found: http://127.0.0.1:5000/users/4"
}

AUTHORIZATION

from functools import wraps

def check_auth(username, password):
 return username == 'admin' and password == 'secret'

def authenticate():
 message = {'message': "Authenticate."}
 resp = jsonify(message)

 resp.status_code = 401
 resp.headers['WWW-Authenticate'] = 'Basic realm="Example"'

 return resp

def requires_auth(f):
 @wraps(f)
 def decorated(*args, **kwargs):
  auth = request.authorization
  if not auth: 
   return authenticate()

  elif not check_auth(auth.username, auth.password):
   return authenticate()
  return f(*args, **kwargs)

 return decorated

replacing the check_auth function and using the requires_auth decorator:

@app.route('/secrets')
@requires_auth
def api_hello():
return "Shhh this is top secret spy stuff!"
HTTP basic authentication:

curl -v -u "admin:secret" http://127.0.0.1:5000/secrets

SIMPLE DEBUG & LOGGING

Debug:

app.run(debug=True)
Logging:

import logging
file_handler = logging.FileHandler('app.log')
app.logger.addHandler(file_handler)
app.logger.setLevel(logging.INFO)

@app.route('/hello', methods = ['GET'])
def api_hello():
 app.logger.info('informing')
 app.logger.warning('warning')
 app.logger.error('screaming bloody murder!')
 
 return "check your logs\n"

以上这篇使用Python & Flask 实现RESTful Web API的实例就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持三水点靠木。

Python 相关文章推荐
浅析Python中的序列化存储的方法
Apr 28 Python
Python实现读取json文件到excel表
Nov 18 Python
分享一个简单的python读写文件脚本
Nov 25 Python
Python Tkinter实现简易计算器功能
Jan 30 Python
Python中property属性实例解析
Feb 10 Python
pandas DataFrame实现几列数据合并成为新的一列方法
Jun 08 Python
3个用于数据科学的顶级Python库
Sep 29 Python
Django框架模板介绍
Jan 15 Python
django中SMTP发送邮件配置详解
Jul 19 Python
python写一个随机点名软件的实例
Nov 28 Python
Python操作Elasticsearch处理timeout超时
Jul 17 Python
python爬虫 requests-html的使用
Nov 30 Python
python基本语法练习实例
Sep 19 #Python
基于python3 类的属性、方法、封装、继承实例讲解
Sep 19 #Python
浅谈python中列表、字符串、字典的常用操作
Sep 19 #Python
Python 文件操作的详解及实例
Sep 18 #Python
python Socket之客户端和服务端握手详解
Sep 18 #Python
Python基于time模块求程序运行时间的方法
Sep 18 #Python
Python使用当前时间、随机数产生一个唯一数字的方法
Sep 18 #Python
You might like
php下正则来匹配dede模板标签的代码
2010/08/21 PHP
在windows平台上构建自己的PHP实现方法(仅适用于php5.2)
2013/07/05 PHP
php 中的closure用法详解
2017/06/12 PHP
PHP高效获取远程图片尺寸和大小的实现方法
2017/10/20 PHP
php单元测试phpunit入门实例教程
2017/11/17 PHP
javascript取消文本选定的实现代码
2010/11/14 Javascript
读jQuery之九 一些瑕疵说明
2011/06/21 Javascript
AngularJS入门教程之MVC架构实例分析
2016/11/01 Javascript
浅谈jQuery hover(over, out)事件函数
2016/12/03 Javascript
前端JS面试中常见的算法问题总结
2016/12/23 Javascript
巧用canvas
2017/01/21 Javascript
Angular弹出模态框的两种方式
2017/10/19 Javascript
jQuery实现手机号正则验证输入及自动填充空格功能
2018/01/02 jQuery
vue中使用gojs/jointjs的示例代码
2018/08/24 Javascript
解决vue 引入子组件报错的问题
2018/09/06 Javascript
js中怎么判断两个字符串相等的实例
2019/01/17 Javascript
小程序卡片切换效果组件wxCardSwiper的实现
2020/02/13 Javascript
在JavaScript中查找字符串中最长单词的三种方法(推荐)
2021/01/18 Javascript
[03:40]DOTA2抗疫特别篇《英雄年代》
2020/02/28 DOTA
Python在Windows和在Linux下调用动态链接库的教程
2015/08/18 Python
python匿名函数的使用方法解析
2019/10/10 Python
Python Tornado实现WEB服务器Socket服务器共存并实现交互的方法
2020/05/26 Python
什么是Python中的匿名函数
2020/06/02 Python
HTML5样式控制示例代码
2013/11/27 HTML / CSS
德国旅行、体验和活动的预订平台:Watado
2019/12/04 全球购物
法律专业实习鉴定
2013/12/22 职场文书
马云的职业生涯规划之路
2014/01/01 职场文书
图书馆志愿者活动总结
2014/06/27 职场文书
兽医医药专业求职信
2014/07/27 职场文书
调研汇报材料范文
2014/08/17 职场文书
家庭财产分割协议范文
2014/11/24 职场文书
清洁工岗位职责
2015/02/13 职场文书
新学期家长寄语2016
2015/12/03 职场文书
《社戏》教学反思
2016/02/22 职场文书
2019幼儿园感恩节活动策划书
2019/11/28 职场文书
分享一些Java的常用工具
2021/06/11 Java/Android