python vue token_Flask与Vue的token认证
后端使用flask设计基于token认证方式的restful接口,前端使用vue.js全家桶,利用axios通讯。
感谢两篇文章的作者:
后端Flask
Flask采用token认证方式,主要思路是通过/api/login登录获取token,然后使用token调用各个接口。
所用到框架的库:
flask
flask-cors:flask跨域
flask-sqlachemy: flask数据库orm
flask-httpauth:flask的auth认证
passlib: python密码解析库
itsdangerous
后端结构图
flask/
├── app # 主目录
│ ├── __init__.py
│ ├── __init__.pyc
│ ├── models.py # 数据库
│ ├── models.pyc
│ ├── views.py # 视图
│ └── views.pyc
├── config.py # 配置信息
├── config.pyc
├── db_create.py # 创建数据库
├── db_migrate.py # 更新数据库
├── db_repository
│ ├── __init__.py
│ ├── __init__.pyc
│ ├── manage.py
│ ├── migrate.cfg
│ ├── README
│ └── versions
│ ├── 008_migration.py
│ ├── 008_migration.pyc
│ ├── 009_migration.py
│ ├── 009_migration.pyc
│ ├── __init__.py
│ └── __init__.pyc
├── index.html
└── run.py # app的运行文件
具体实现
系统初始化app/__init__.py
# -*- coding:utf-8 -*-
from flask import Flask
from flask_sqlalchemy import SQLAlchemy
from flask_httpauth import HTTPBasicAuth
from flask_cors import CORS
app = Flask(__name__)
# flask的跨域解决
CORS(app)
app.config.from_object('config')
db = SQLAlchemy(app)
auth = HTTPBasicAuth()
from . import models, views
配置文件config.py
import os
basedir = os.path.abspath(os.path.dirname(__file__))
SQLALCHEMY_DATABASE_URI = "mysql://root:123456@127.0.0.1/rest"
SQLALCHEMY_MIGRATE_REPO = os.path.join(basedir, 'db_repository')
SQLALCHEMY_TRACK_MODIFICATIONS = True
BASEDIR = basedir
# 安全配置
CSRF_ENABLED = True
SECRET_KEY = 'jklklsadhfjkhwbii9/sdf\sdf'
环境中使用mysql数据库,版本为mariadb 10.1.22。创建rest表
$ mysql -uroot -p xxxxxx
$ create database rest default charset utf8;
创建数据库表app/models.py
# -*- coding:utf-8 -*-
from app import db, app
from passlib.apps import custom_app_context
from itsdangerous import TimedJSONWebSignatureSerializer as Serializer, SignatureExpired, BadSignature
class User(db.Model):
__tablename__ = 'users'
id = db.Column(db.Integer, primary_key=True)
username = db.Column(db.String(32), index=True)
password = db.Column(db.String(128))
# 密码加密
def hash_password(self, password):
self.password = custom_app_context.encrypt(password)
# 密码解析
def verify_password(self, password):
return custom_app_context.verify(password, self.password)
# 获取token,有效时间10min
def generate_auth_token(self, expiration = 600):
s = Serializer(app.config['SECRET_KEY'], expires_in = expiration)
return s.dumps({ 'id': self.id })
# 解析token,确认登录的用户身份
@staticmethod
def verify_auth_token(token):
s = Serializer(app.config['SECRET_KEY'])
try:
data = s.loads(token)
except SignatureExpired:
return None # valid token, but expired
except BadSignature:
return None # invalid token
user = User.query.get(data['id'])
return user
创建数据库users表:
$ python db_create.py
$ python db_migrate.py
视图app/views.py
from app import app, db, auth
from flask import render_template, json, jsonify, request, abort, g
from app.models import *
@app.route("/")
@auth.login_required
def index():
return jsonify('Hello, %s' % g.user.username)
@app.route('/api/users', methods = ['POST'])
def new_user():
username = request.json.get('username')
password = request.json.get('password')
if username is None or password is None:
abort(400) # missing arguments
if User.query.filter_by(username = username).first() is not None:
abort(400) # existing user
user = User(username = username)
user.hash_password(password)
db.session.add(user)
db.session.commit()
return jsonify({ 'username': user.username })
@auth.verify_password
def verify_password(username_or_token, password):
if request.path == "/api/login":
user = User.query.filter_by(username=username_or_token).first()
if not user or not user.verify_password(password):
return False
else:
user = User.verify_auth_token(username_or_token)
if not user:
return False
g.user = user
return True
@app.route('/api/login')
@auth.login_required
def get_auth_token():
token = g.user.generate_auth_token()
return jsonify(token)
用户注册后密码加密存储,确认用户身份时密码解密。需要认证的api上添加@auth.login_required,它会在调用接口之前调用@auth.verify_password下的方法(此方法唯一)如verify_password。根据请求的路径选择不同的认证方式。
测试
使用curl命令测试接口
注册用户:
$ curl -i -X POST -H "Content-Type: application/json" -d '{"username":"admin","password":"123456"}' http://127.0.0.1:5000/api/register
HTTP/1.0 200 OK
Content-Type: application/json
Access-Control-Allow-Origin: *
Content-Length: 26
Server: Werkzeug/0.12.2 Python/2.7.13
Date: Wed, 20 Sep 2017 06:33:46 GMT
{
"username": "admin"
}
查看数据库:
MariaDB [rest]> select * from users\G;
*************************** 1. row ***************************
id: 1
username: admin
password: $6$rounds=656000$etV4F3xLL0dwflX8$mLFX9l5dumBnQFtajGmey346viGuQ4bxR7YhQdKtB/nQH9ij2e3HHMEBPj.ef/o//4o9P2Wd3Y7dxQfjwR2hY/
1 row in set (0.00 sec)
获取token:
curl -i -u admin:123456 -X GET -H "Content-Type: application/json" http://127.0.0.1:5000/api/login
HTTP/1.0 200 OK
Content-Type: application/json
Access-Control-Allow-Origin: *
Content-Length: 125
Server: Werkzeug/0.12.2 Python/2.7.13
Date: Wed, 20 Sep 2017 06:37:01 GMT
"eyJhbGciOiJIUzI1NiIsImV4cCI6MTUwNTg5MDAyMSwiaWF0IjoxNTA1ODg5NDIxfQ.eyJpZCI6MX0.nUIKq-ZhFOiLPwZyUmfgWPfHYNy8o6eoR6lmzdsY0oQ"
使用token调用api:
$ curl -i -u eyJhbGciOiJIUzI1NiIsImV4cCI6MTUwNTg5MDAyMSwiaWF0IjoxNTA1ODg5NDIxfQ.eyJpZCI6MX0.nUIKq-ZhFOiLPwZyUmfgWPfHYNy8o6eoR6lmzdsY0oQ:unused -X GET -H "Content-Type: application/json" http://127.0.0.1:5000/
HTTP/1.0 200 OK
Content-Type: application/json
Access-Control-Allow-Origin: *
Content-Length: 15
Server: Werkzeug/0.12.2 Python/2.7.13
Date: Wed, 20 Sep 2017 06:38:22 GMT
"Hello, admin"
基于token的Flask api成功!!!!
前端Vue.js
前端使用vue的全家桶,axios前后端通讯,axios拦截器,localStorage保存token
所使用的框架和库:
vue2.0
iview2.X
axios
vuex
vue-router
具体实现
main.js
// 初始化axios
axios.defaults.baseURL = 'http://127.0.0.1:5000'
axios.defaults.auth = {
username: '',
password: '',
}
// axios.interceptors.request.use((config) => {
// console.log(config)
// return config;
// }, (error) => {
// return Promise.reject(error)
// })
// axios拦截器,401状态时跳转登录页并清除token
axios.interceptors.response.use((response) => {
return response;
}, (error) => {
if (error.response) {
switch (error.response.status) {
case 401:
store.commit('del_token')
router.push('/login')
}
}
return Promise.reject(error.response.data)
})
// 路由跳转
router.beforeEach((to, from, next) => {
if (to.meta.required) {
// 检查localStorage
if (localStorage.token) {
store.commit('set_token', localStorage.token)
// 添加axios头部Authorized
axios.defaults.auth = {
username: store.state.token,
password: store.state.token,
}
// iview的页面加载条
iView.LoadingBar.start();
next()
} else {
next({
path: '/login',
})
}
} else {
iView.LoadingBar.start();
next()
}
})
router.afterEach((to, from, next) => {
iView.LoadingBar.finish();
})
路由
export default new Router({
routes: [{
path: '/',
name: 'index',
component: Index,
meta: {
required: true,
}
}, {
path: '/login',
name: 'login',
component: Login,
}]
})
路由添加meta字段,作为需要认证路由的标志
vuex
export default new Vuex.Store({
state: {
token: ''
},
mutations: {
set_token(state, token) {
state.token = token
localStorage.token = token
},
del_token(state) {
state.token = ''
localStorage.removeItem('token')
}
}
})
vuex中保存token,同时修改删除token和localStorage.token
登录和登出
登录:
handleSubmit(name, form) {
this.$refs[name].validate((valid) => {
if (valid) {
// 用户名密码简单验证后添加到axios的auth中
this.$axios.defaults.auth = {
username: form.username,
password: form.password,
}
this.$axios.get('/api/login').then(response => {
this.$Message.success("提交成功")
let data = response.data
// 保存token
this.$store.commit('set_token', data)
this.$router.push('/')
}).catch(error => {
this.$Message.error(error.status)
})
} else {
this.$Message.error('表单验证失败!');
}
})
}
登出:
logout() {
this.$store.commit('del_token')
this.$router.push('/login')
}
删除token并跳转到登录页
flask和vue的token认证就完成了!!!!
python vue token_Flask与Vue的token认证相关推荐
- Vue 用户登入及token 认证
VUE 项目 新建vue 项目(eight) #创建一个基于webpack模板的新项目 vue init webpack D:\node_workspace\eight # 切换至项目路径 cd d: ...
- 路由守卫 AJAX,vue路由导航守卫 和 请求拦截以及基于node的token认证
#####什么时候需要登录验证与权限控制 1.业务系统通常需要登录才能访问受限资源,在用户未登录情况下访问受限资源需要重定向到登录页面: 2.多个业务系统之间要实现单点登录,即在一个系统或应用已登录的 ...
- 前端学习(1879)vue之电商管理系统电商系统之通过axios拦截器添加token认证
目录结构 router.js import Vue from 'vue' import Router from 'vue-router' import Login from './components ...
- vue中axios如何实现token验证
title: vue中axios如何实现token验证 date: 2018-02-08 17:50:07 tags: [axios,vue] 继上篇实现Auth认证之后,然后每个跳转页面都会在后端验 ...
- php vue jwt 实战,Vue路由之JWT身份认证的实现方法
一.JWT身份认证简介 JSON Web Token(JWT)是目前最流行的跨域身份验证解决方案,相较于session机制,服务器就不需要保存任何 session 数据了,也就是说,服务器变成无状态了 ...
- vue axios封装以及登录token过期跳转问题
Axios配置JWT/封装插件/发送表单数据 首先请务必已仔细阅读 Axios 文档并熟悉 JWT: 中文文档 JWT 中文文档 安装 npm install axios npm install es ...
- eslint 验证vue文件 报错 unexpected token =解决方法
eslint 验证vue文件 报错 unexpected token =解决方法 参考文章: (1)eslint 验证vue文件 报错 unexpected token =解决方法 (2)https: ...
- python怎么新建工程_Python vue坏境搭建及项目创建
vue项目坏境搭建 node ~~ python:node是用c++编写用来运行js代码的 npm(cnpm)~~pip:npm是一个终端应用商城,可以换国内源cnpm vue~~ django:vu ...
- Vue实现用户登录及token验证
写博客不是为了博眼球 而是为了记笔记 请勿复制全部代码防止错乱,这里放源码是为了个人做笔记 //登录 login: params => { return API.POS ...
最新文章
- 关于C++模版的连接错误问题
- AB1601LED之pwm
- 《Java 核心技术卷1 第10版》学习笔记------Object类的 equals 方法
- 从0开始搭建ELK及采集日志的简单应用
- Java 对抽象类的理解
- python兼职程序员工资-没想到,学会Python即使不做程序员都能月入过万!
- 国务院印发《政务信息资源共享管理暂行办法》
- 基于Java坦克大战小游戏设计(3)
- ArcGIS中相对高程的提取
- 音视频多媒体开发基础概述之颜色空间(2)YUV YIQ YCrCb CMY颜色空间
- 拼多多推广位备案方法(2021.5.5)
- #国产工业软件#外行人看工业软件,接轨还是出轨?
- OpenCV调试利器——Image Watch插件的安装和使用
- web版拳皇,使用html,css,js来制作一款拳皇游戏
- 方向向量转欧拉角_【姿态表示】旋转向量、旋转矩阵、欧拉角、四元数
- CentOS清理tmp下临时文件
- 文件服务器杀毒软件推荐,服务器杀毒软件哪个好 服务器装什么杀毒软件【详解】...
- 第九章 面向对象方法学(3)
- 响应式网页设计_响应式网页设计:我们从这里去哪里?
- 逻辑回归算法 - 乳腺癌预测
热门文章
- Mac terminal 清屏快捷键
- Andorid Studio NDK 开发 - Hello World
- 实战开发经验:是什么阻碍了我们跨平台
- c语言c99标准_C语言的三套标准:C89、C99和C11
- 阿里云服务器如何扩容云盘?
- vuex mapstate_Vuex从使用到原理解析
- windows系统bat批处理 arp扫描一个网段的IP地址
- 阿里云服务器上单机部署大数据开发环境(hadoop2.6-cdh5.8.0系列)
- java家谱树_青锋家谱系统-基于springboot+orgtree的青锋家谱树管理系统
- 的有效性最好_股票职业玩家教韭菜实战,验证技术指标的有效性,资产增值是王道...