Go?WEB框架使用攔截器驗(yàn)證用戶登錄狀態(tài)實(shí)現(xiàn)
wego攔截器
wego攔截器是一個(gè)action(處理器函數(shù))之前或之后被調(diào)用的函數(shù),通常用于處理一些公共邏輯。攔截器能夠用于以下常見問題:
- 請(qǐng)求日志記錄
- 錯(cuò)誤處理
- 身份驗(yàn)證處理
wego中有以下攔截器:
- before_exec :執(zhí)行action之前攔截器
- after_exec :執(zhí)行action之后攔截器
本文用一個(gè)例子來說明如何使用攔截器來實(shí)現(xiàn)用戶登錄狀態(tài)的判定。在這個(gè)例子中,用戶訪問login_get來顯示登錄頁面,并調(diào)用login_post頁面來提交登錄信息。
在login_post頁面中判定用戶登錄信息是否合法,并將登錄賬號(hào)保存在session中。用戶訪問其他需要登錄驗(yàn)證的頁面(例如:index頁面)前首先執(zhí)行攔截器:handler.BeforeExec。
在攔截器中獲取用戶賬號(hào),若沒有獲取到用戶賬號(hào),則跳轉(zhuǎn)到登錄頁面:login_get。使用攔截器來進(jìn)行用戶登錄狀態(tài)的檢查的有點(diǎn)是,不用在每個(gè)處理器函數(shù)中都包含用戶登錄狀態(tài)的檢查邏輯。只要將登錄邏輯獨(dú)立出來,并實(shí)現(xiàn)為before_exec攔截器即可。
以下時(shí)main函數(shù)的主要內(nèi)容:
main函數(shù)
package main
import (
"demo/handler"
"github.com/haming123/wego"
log "github.com/haming123/wego/dlog"
)
func main() {
web, err := wego.InitWeb()
if err != nil {
log.Error(err)
return
}
wego.SetDebugLogLevel(wego.LOG_DEBUG)
web.Config.SessionParam.SessionOn = true
web.Config.SessionParam.HashKey = "demohash"
web.BeforExec(handler.BeforeExec)
web.GET("/login_get", handler.HandlerLoginGet).SkipHook()
web.POST("/login_post", handler.HandlerLoginPost).SkipHook()
web.GET("/index", handler.HandlerIndex)
err = web.Run("0.0.0.0:8080")
if err != nil {
log.Error(err)
}
}說明:
- 本例子中使用基于cookie的session數(shù)據(jù)存儲(chǔ)引擎,用于存儲(chǔ)用戶登錄賬號(hào)。
- 調(diào)用
web.BeforExec(handler.BeforeExec)來設(shè)置攔截器,在handler.BeforeExec攔截器中實(shí)現(xiàn)了登錄狀態(tài)的檢查邏輯。 - 由于login_get頁面、login_post頁面不需要進(jìn)行登錄檢驗(yàn),使用
SkipHook()來忽略攔截器。
登錄邏輯
用戶訪問需要進(jìn)行登錄驗(yàn)證的頁面時(shí),首先會(huì)檢查session的登錄賬號(hào),若沒有登錄賬號(hào),則跳轉(zhuǎn)到登錄頁面:login_get, 登錄頁面的處理器實(shí)現(xiàn)如下:
func HandlerLoginGet(c *wego.WebContext) {
c.WriteHTML(http.StatusOK, "./view/login.html", nil)
}login.html的內(nèi)容如下:
<!doctype html>
<html>
<head>
<meta charset="UTF-8">
<title>登錄頁面</title>
</head>
<body>
<h2>用戶登陸</h2>
<form action="/login_post" method="post">
<div>用戶賬號(hào):</div>
<div>
<input type="text" name="account" placeholder="請(qǐng)輸入用戶賬號(hào)" />
</div>
<br />
<div>登錄密碼:</div>
<div>
<input type="password" name="password" placeholder="請(qǐng)輸入登錄密碼"/>
</div>
<br />
<div>
<input type="submit" value="立即登錄" />
</div>
</form>
</body>
</html>用戶點(diǎn)擊"立即登錄"后項(xiàng)服務(wù)器發(fā)送post請(qǐng)求到login_post, login_post處理器的實(shí)現(xiàn)如下:
func HandlerLoginPost(c *wego.WebContext) {
account := c.Param.MustString("account")
password := c.Param.MustString("password")
if account == "admin" && password == "demo" {
c.Session.Set("account", account)
c.Session.Save()
c.Redirect(302, "/index")
} else {
c.Session.Set("account", "")
c.Session.Save()
c.Redirect(302, "/login_get")
}
}說明:
- 在HandlerLoginPost調(diào)用c.Session.Set將賬號(hào)寫入session。
登錄攔截器的實(shí)現(xiàn)
登錄檢查的邏輯采用before_exec攔截器來實(shí)現(xiàn),以下是before_exec攔截器的代碼:
func GetAccount(c *wego.WebContext) string {
account, _ := c.Session.GetString("account")
return account
}
func BeforeExec(c *wego.WebContext) {
login_path := "/login_get"
if GetAccount(c) == "" && c.Path != login_path {
c.Redirect(302, login_path)
return
}
}說明:
- 實(shí)現(xiàn)GetAccount函數(shù)來獲取session數(shù)據(jù),若用戶成功登錄了系統(tǒng),則session中保存有用戶的登錄賬號(hào)。在處理器函數(shù)中可以調(diào)用GetAccount函數(shù)來獲取登錄的登錄賬號(hào)。
- BeforeExec函數(shù)是before_exec攔截器的一個(gè)實(shí)現(xiàn)。在BeforeExec函數(shù)中首先調(diào)用GetAccount函數(shù)來獲取登錄的登錄賬號(hào),若不存在用戶賬號(hào),則跳轉(zhuǎn)到登錄頁面:login_get,否則執(zhí)行處理去函數(shù)。
index頁面的實(shí)現(xiàn)
index頁面需要驗(yàn)證用戶是否登錄,由于執(zhí)行index頁面的處理器前會(huì)執(zhí)行before_exec攔截器, 因此在index頁面的處理器函數(shù)中不需要再進(jìn)行登錄檢查了,程序員只需要實(shí)現(xiàn)業(yè)務(wù)邏輯即可。index頁面的處理器函數(shù)的實(shí)現(xiàn)代碼如下:
func HandlerIndex(c *wego.WebContext) {
c.WriteHTML(http.StatusOK, "./view/index.html", GetAccount(c))
}在HandlerIndex中讀取index.html模板,并使用調(diào)用 GetAccount(c)獲取用戶賬號(hào),然后及進(jìn)行渲染。其中index.html模板的內(nèi)容如下:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<body>
hello : {{.}}
</body>
</html>wego代碼的下載
go get https://github.com/haming123/wego
以上就是Go WEB框架使用攔截器驗(yàn)證用戶登錄狀態(tài)實(shí)現(xiàn)的詳細(xì)內(nèi)容,更多關(guān)于Go WEB驗(yàn)證用戶登錄狀態(tài)的資料請(qǐng)關(guān)注腳本之家其它相關(guān)文章!
相關(guān)文章
Go語言中init函數(shù)與匿名函數(shù)使用淺析
這篇文章主要介紹了Go語言中init函數(shù)與匿名函數(shù)使用淺析,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)吧2023-01-01
go語言使用Chromedp實(shí)現(xiàn)二維碼登陸教程示例源碼
golang數(shù)組和切片作為參數(shù)和返回值的實(shí)現(xiàn)
解決Go中使用seed得到相同隨機(jī)數(shù)的問題
golang包循環(huán)引用的幾種解決方案總結(jié)

