更新前后端代码
This commit is contained in:
@@ -0,0 +1,109 @@
|
||||
package middleware
|
||||
|
||||
import (
|
||||
"strings"
|
||||
|
||||
"github.com/gin-gonic/gin"
|
||||
|
||||
"filestoragesystem/internal/model"
|
||||
"filestoragesystem/internal/service"
|
||||
"filestoragesystem/internal/utils"
|
||||
"filestoragesystem/pkg/apperr"
|
||||
)
|
||||
|
||||
// 上下文键
|
||||
const (
|
||||
CtxUser = "authUser" // *model.User
|
||||
CtxUserID = "authUserID" // uint
|
||||
CtxUsername = "authUsername" // string
|
||||
CtxRoleCode = "authRoleCode" // string
|
||||
CtxPermissions = "authPermissions" // map[string]bool
|
||||
)
|
||||
|
||||
// Auth 认证中间件:支持 JWT Bearer 与 API Key HMAC-SHA256签名两种方式
|
||||
func Auth(authSvc *service.AuthService) gin.HandlerFunc {
|
||||
return func(c *gin.Context) {
|
||||
var user *model.User
|
||||
|
||||
// 1. JWT Bearer Token
|
||||
header := c.GetHeader("Authorization")
|
||||
if strings.HasPrefix(header, "Bearer ") {
|
||||
claims, err := utils.ParseToken(strings.TrimPrefix(header, "Bearer "))
|
||||
if err != nil {
|
||||
utils.Unauthorized(c, "Token无效或已过期")
|
||||
return
|
||||
}
|
||||
u, err := authSvc.LoadUserByID(claims.UserID)
|
||||
if err != nil {
|
||||
utils.Unauthorized(c, apperr.ErrUnauthorized.Error())
|
||||
return
|
||||
}
|
||||
user = u
|
||||
} else if ak := c.GetHeader("X-Access-Key"); ak != "" {
|
||||
// 2. API Key + Secret HMAC-SHA256签名
|
||||
u, err := authSvc.VerifyAPIKeySignature(
|
||||
ak,
|
||||
c.GetHeader("X-Timestamp"),
|
||||
c.GetHeader("X-Nonce"),
|
||||
c.GetHeader("X-Signature"),
|
||||
c.Request.Method,
|
||||
c.Request.URL.Path,
|
||||
)
|
||||
if err != nil {
|
||||
utils.Unauthorized(c, err.Error())
|
||||
return
|
||||
}
|
||||
user = u
|
||||
} else {
|
||||
utils.Unauthorized(c, "缺少认证信息")
|
||||
return
|
||||
}
|
||||
|
||||
if user == nil {
|
||||
utils.Unauthorized(c, apperr.ErrUnauthorized.Error())
|
||||
return
|
||||
}
|
||||
|
||||
c.Set(CtxUser, user)
|
||||
c.Set(CtxUserID, user.ID)
|
||||
c.Set(CtxUsername, user.Username)
|
||||
roleCode := ""
|
||||
if user.Role != nil {
|
||||
roleCode = user.Role.Code
|
||||
}
|
||||
c.Set(CtxRoleCode, roleCode)
|
||||
c.Set(CtxPermissions, service.PermissionCodesOf(user))
|
||||
c.Next()
|
||||
}
|
||||
}
|
||||
|
||||
// CurrentUser 从上下文获取当前用户
|
||||
func CurrentUser(c *gin.Context) *model.User {
|
||||
if v, ok := c.Get(CtxUser); ok {
|
||||
if u, ok := v.(*model.User); ok {
|
||||
return u
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// CurrentUserID 当前用户ID
|
||||
func CurrentUserID(c *gin.Context) uint {
|
||||
if v, ok := c.Get(CtxUserID); ok {
|
||||
if id, ok := v.(uint); ok {
|
||||
return id
|
||||
}
|
||||
}
|
||||
return 0
|
||||
}
|
||||
|
||||
// IsSuperAdmin 是否超级管理员
|
||||
func IsSuperAdmin(c *gin.Context) bool {
|
||||
return c.GetString(CtxRoleCode) == "super_admin"
|
||||
}
|
||||
|
||||
// IsAdmin 是否管理员(super_admin或admin)
|
||||
func IsAdmin(c *gin.Context) bool {
|
||||
rc := c.GetString(CtxRoleCode)
|
||||
return rc == "super_admin" || rc == "admin"
|
||||
}
|
||||
Reference in New Issue
Block a user