Files
SafeLine/management/webserver/middleware/auth.go
T
Binbim b8788c239e
MCP Docker / build-and-push (push) Has been cancelled
feat: SafeLine CE 9.3.9 with pro features
- Remove telemetry: disabled all phone-home (installation notify, false positives, behavior tracking, upgrade tips)
- Version branding: removed 'ce-' prefix, product name changed to '长亭雷池 WAF'
- Detection engine enhancement: strict preset enables all 17 modules with aggressive configs
- Multi-user RBAC: admin/operator/viewer roles with password + TOTP 2FA
- Rate limiting: nginx limit_req per website (RPS, burst, action)
- JS Challenge: browser fingerprint verification page with cookie-based bypass
- Security fixes: removed InsecureSkipVerify, hardcoded credentials, NO_AUTH backdoor
2026-07-04 07:59:04 +08:00

94 lines
2.4 KiB
Go

package middleware
import (
"net/http"
"github.com/gin-contrib/sessions"
"github.com/gin-gonic/gin"
"chaitin.cn/patronus/safeline-2/management/webserver/api/response"
"chaitin.cn/patronus/safeline-2/management/webserver/model"
"chaitin.cn/patronus/safeline-2/management/webserver/pkg/constants"
"chaitin.cn/patronus/safeline-2/management/webserver/pkg/database"
)
func AuthRequired(c *gin.Context) {
session := sessions.Default(c)
user := session.Get(constants.DefaultSessionUserKey)
if user == nil {
response.Error(c, response.ErrorLoginRequired, http.StatusUnauthorized)
c.Abort()
return
}
// Load user from database to get current role/status
db := database.GetDB()
var userModel model.User
res := db.First(&userModel, user)
if res.RowsAffected == 0 {
response.Error(c, response.ErrorLoginRequired, http.StatusUnauthorized)
c.Abort()
return
}
// Check if user is still enabled
if !userModel.IsEnabled {
session.Clear()
session.Save()
response.Error(c, response.JSONBody{Err: "account_disabled", Msg: "Account has been disabled"}, http.StatusForbidden)
c.Abort()
return
}
// Store user info in context for downstream handlers
c.Set("user_id", int(userModel.ID))
c.Set("user_role", userModel.Role)
c.Set("username", userModel.Username)
// extend session expired time
session.Options(sessions.Options{
Path: "/",
MaxAge: 3600 * 24 * 7,
})
if err := session.Save(); err != nil {
response.Error(c, response.JSONBody{Err: response.ErrInternalError, Msg: "Error occurred when creating sessions"}, http.StatusInternalServerError)
return
}
c.Next()
}
// RequireRole returns a middleware that checks if the user has one of the required roles.
func RequireRole(roles ...string) gin.HandlerFunc {
roleSet := make(map[string]bool)
for _, r := range roles {
roleSet[r] = true
}
return func(c *gin.Context) {
userRole, exists := c.Get("user_role")
if !exists {
response.Error(c, response.ErrorLoginRequired, http.StatusUnauthorized)
c.Abort()
return
}
role, ok := userRole.(string)
if !ok || !roleSet[role] {
response.Error(c, response.JSONBody{Err: "forbidden", Msg: "Insufficient permissions"}, http.StatusForbidden)
c.Abort()
return
}
c.Next()
}
}
func ReadOnly(c *gin.Context) {
if c.Request.Method != "GET" && c.Request.Method != "HEAD" && c.Request.Method != "OPTIONS" {
response.Error(c, response.ErrorReadOnly, http.StatusBadRequest)
c.Abort()
}
}