0. 概念講解:
應(yīng)用授權(quán)大致可分為有狀態(tài)的和無狀態(tài)的箩艺,前者是基于Session的驗證方式窜醉,用戶授權(quán)后無需再授權(quán)。而REST應(yīng)用多采用后者艺谆,每次請求都要發(fā)送憑據(jù)榨惰。注意:adonis使用Hash驗證密碼,記得使用Hash模塊處理密碼再存入數(shù)據(jù)庫
1. 建一個apiOnly的項目:
adonis new my-adonis-jwt-test --api-only --yarn
静汤,個人喜歡用yarn琅催,apionly不用視圖
cd my-adonis-jwt-test
//使用sqlite3
yarn add sqlite3 -S
執(zhí)行完畢后,項目database文件夾下會生成一個adonis.sqlite
文件虫给,這個名字是根據(jù)你的.env文件里面的設(shè)置生成的藤抡。
推薦用SQLiteStudio查看數(shù)據(jù)庫文件,下載:https://sqlitestudio.pl/index.rvt
其實單純講jwt的話狰右,不需要數(shù)據(jù)庫的杰捂,但實際中一般是數(shù)據(jù)庫查到記錄后再下發(fā)jwt token,所以還是安裝一下吧棋蚌。
--api-only
參數(shù)建立的項目嫁佳,默認(rèn)使用jwt驗證,所以不用設(shè)置谷暮,如果是自己手動建項目蒿往,則需要按照官網(wǎng)配置一下:http://adonisjs.com/docs/4.0/authentication#_setup
準(zhǔn)備工作完畢。
2. jwt基本使用:
- start/router.js
const Route = use('Route')
Route.post('users', 'UserController.save')
Route.get('users', 'UserController.show').middleware('auth')
Route.get('noauth','UserController.noauth')
分別是添加用戶和顯示用戶湿弦,我們給其中的顯示用戶加上auth中間件瓤漏,添加用戶肯定不能加,否則根本就沒法注冊了-_-||。最后的noauth路由在本文稍后解釋
終端輸入:adonis make:controller user
打開生成的UserController文件蔬充,編寫方法:
'use strict'
const User = use('App/Models/User')
class UserController {
async save({ request, response,auth }) {
const data = request.only(['username', 'password'])
try {
return await auth.withRefreshToken().attempt(data.username, data.password)
}
catch (ex) {
return ex.message
}
}
async show({ request, auth,response }) {
try {
return await auth.check()
response.ok("check token passed")
} catch (error) {
response.send(error.message)
}
}
noauth({ request,response }) {
response.ok('success')
}
}
module.exports = UserController
- 如果使用了
AuthProvider
蝶俱,則Controller自動獲得auth方法參數(shù) - save方法中,首先獲得用戶post進來的數(shù)據(jù)饥漫,然后使用auth的
attemp
方法生成jwt token榨呆,結(jié)果:
{
"type": "bearer",
"token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJ1aWQiOjEsImlhdCI6MTUxNTA4NzE1OH0.kRTOKu4PkSKz7NRVvsAtJAw0hU5X-cpR9Foc7GPzqMs",
"refreshToken": "b536e951396da7f80259983cfe17e005f70d3b7d7f9fe2f3efd083c765b282754e47805267f8eb1847d9ac1e16965901AFD49NcfhGJ980/qkvhohWNaebSBbBO2gVK62+QWUv46/BrQSDzF1pIzX6yCbzJP"
}
當(dāng)然,實際中不能這么干庸队,應(yīng)該是 驗證數(shù)據(jù)(validator組件)→ 保存用戶到數(shù)據(jù)庫 → 產(chǎn)生token并下發(fā)积蜻,一定注意,這個token不保存到數(shù)據(jù)庫彻消。
refreshToken
是用來產(chǎn)生新的token竿拆,就不用用戶名密碼了。
show方法啟用了驗證(路由中)宾尚,所以必須要在方法中進行token驗證丙笋,
auth.check
就是干這個用的,現(xiàn)在客戶端在請求show方法的時候煌贴,就必須帶上Authorization=Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJ1aWQiOjEsImlhdCI6MTUxNTA4NTM3OX0.yIYNgogUGfsFy5t08OQoAud9fhwi_SHnEmF5mkoA-xc
Header, Bearer 后面的token就是我們剛才下發(fā)給客戶端的不见。noauth方法內(nèi)部并沒有做任何驗證,而在 router中此條路由也沒有加auth中間件崔步,這樣請求的時候是不需要token的。如果router里面加上auth :
Route.get('noauth','UserController.noauth').middleware('auth')
,那么不管方法里有沒有驗證缎谷,如果Header中沒有Token井濒,則一樣攔截。
就這樣列林,輕松實現(xiàn)了jwt+token驗證瑞你,簡直不敢相信,簡單的令人發(fā)指希痴!
如果你沒有和我一樣的感受者甲,那我想貼一張springboot jwt實現(xiàn)的貼圖:
當(dāng)時寫這個差點沒吐血。
adonis砌创,真的是一個優(yōu)美簡單的框架虏缸。