62 lines
2.0 KiB
Go
62 lines
2.0 KiB
Go
package middleware
|
|
|
|
import (
|
|
"fmt"
|
|
"github.com/gin-gonic/gin"
|
|
"github.com/golang-jwt/jwt/v4"
|
|
"nCovTrack-Backend/global"
|
|
"nCovTrack-Backend/utils"
|
|
"net/http"
|
|
"strconv"
|
|
"time"
|
|
)
|
|
|
|
const UNAUTH_MSG = "unauthorized"
|
|
|
|
func Auth() gin.HandlerFunc {
|
|
return func(c *gin.Context) {
|
|
oldToken := c.Request.Header["Token"]
|
|
c.Writer.Header().Set("X-Token", "")
|
|
if len(oldToken) != 1 || oldToken[0] == "" {
|
|
utils.Err(c, http.StatusUnauthorized, http.StatusUnauthorized, UNAUTH_MSG)
|
|
c.Abort()
|
|
return
|
|
}
|
|
// Write the field of token to request header
|
|
claims := utils.ParseClaims(oldToken[0])
|
|
c.Request.Header.Set("role", fmt.Sprint(claims["role"]))
|
|
c.Request.Header.Set("email", claims["email"].(string))
|
|
c.Request.Header.Set("id", fmt.Sprint(claims["id"]))
|
|
|
|
// renew token, and judge the token's iat is expired or not
|
|
renewToken := utils.RenewToken(oldToken[0])
|
|
if renewToken == "" || !validAccountIssue(claims) {
|
|
utils.Err(c, http.StatusUnauthorized, http.StatusUnauthorized, UNAUTH_MSG)
|
|
c.Abort()
|
|
return
|
|
}
|
|
c.Writer.Header().Set("X-Token", renewToken)
|
|
c.Next()
|
|
}
|
|
}
|
|
|
|
// validAccountIssue validate token is valid or not
|
|
// If user change password, or logoff on all password, we need to judge use's token is valid?
|
|
// Due to the token is no status, so we need to record something on the server-end.
|
|
// We use the "IssueAt" field of token, to judge token expired or not.
|
|
// TODO: Move this to jwt utils
|
|
func validAccountIssue(claims jwt.MapClaims) bool {
|
|
iafStr := global.Redis.HGet(global.CHANGEPWD_REDIS_KEY, claims["email"].(string)).Val()
|
|
if iafStr == "" {
|
|
return true
|
|
}
|
|
iaf, _ := strconv.Atoi(iafStr)
|
|
// Due to we allow token renew, although it was expired, so the token validity period will more than token's validity period
|
|
tokenMaxValidSeconds := (global.TOKEN_EXPIRE_DAYS + global.ServerSettings.Jwt.RenewExpireDays) * 24 * 60 * 60
|
|
if time.Now().Unix()-int64(iaf) > int64(tokenMaxValidSeconds) {
|
|
global.Redis.HDel(global.CHANGEPWD_REDIS_KEY, claims["email"].(string))
|
|
return true
|
|
}
|
|
return int(claims["iat"].(float64)) > iaf
|
|
}
|