package handler import ( "errors" "net/http" "strconv" "strings" "github.com/freefire/jiang13-bbs/middleware" "github.com/freefire/jiang13-bbs/service" "github.com/gin-gonic/gin" "gorm.io/gorm" ) // ===== 用户管理(RequireAdmin 兜底,前端不做权限判定) ===== // AdminListUsers 用户分页列表(搜索/角色/状态筛选 + 全站汇总) func (h *Handlers) AdminListUsers(c *gin.Context) { page, _ := strconv.Atoi(c.DefaultQuery("page", "1")) size, _ := strconv.Atoi(c.DefaultQuery("size", "20")) res, err := h.AdminUser.List(service.AdminUserListQuery{ Page: page, Size: size, Keyword: strings.TrimSpace(c.Query("q")), Role: c.Query("role"), Status: c.Query("status"), }) if err != nil { c.JSON(http.StatusInternalServerError, gin.H{"error": "获取用户列表失败"}) return } c.JSON(http.StatusOK, gin.H{ "users": res.Users, "total": res.Total, "page": res.Page, "size": res.Size, "summary": res.Summary, }) } // adminUserActionBody 角色/封禁变更的通用请求体 type adminUserRoleBody struct { Role string `json:"role"` } type adminUserBanBody struct { Banned bool `json:"banned"` } // AdminUpdateUserRole 设置用户角色(user / admin) func (h *Handlers) AdminUpdateUserRole(c *gin.Context) { id, ok := parseAdminUserID(c) if !ok { return } var body adminUserRoleBody if err := c.ShouldBindJSON(&body); err != nil { c.JSON(http.StatusBadRequest, gin.H{"error": "请求参数无效"}) return } user, err := h.AdminUser.SetRole(middleware.CurrentUser(c).ID, id, body.Role) if err != nil { respondAdminUserError(c, err) return } c.JSON(http.StatusOK, gin.H{"user": user}) } // AdminSetUserBan 封禁 / 解封用户 func (h *Handlers) AdminSetUserBan(c *gin.Context) { id, ok := parseAdminUserID(c) if !ok { return } var body adminUserBanBody if err := c.ShouldBindJSON(&body); err != nil { c.JSON(http.StatusBadRequest, gin.H{"error": "请求参数无效"}) return } user, err := h.AdminUser.SetBanned(middleware.CurrentUser(c).ID, id, body.Banned) if err != nil { respondAdminUserError(c, err) return } c.JSON(http.StatusOK, gin.H{"user": user}) } // parseAdminUserID 解析路径中的用户 ID,失败时直接写出 400 func parseAdminUserID(c *gin.Context) (uint, bool) { id, err := strconv.ParseUint(c.Param("id"), 10, 64) if err != nil || id == 0 { c.JSON(http.StatusBadRequest, gin.H{"error": "无效的用户 ID"}) return 0, false } return uint(id), true } // respondAdminUserError 统一映射用户管理业务错误到 HTTP 状态码 func respondAdminUserError(c *gin.Context, err error) { switch { case errors.Is(err, gorm.ErrRecordNotFound): c.JSON(http.StatusNotFound, gin.H{"error": "用户不存在"}) case errors.Is(err, service.ErrAdminSelfAction), errors.Is(err, service.ErrLastAdmin), errors.Is(err, service.ErrInvalidUserRole): c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()}) default: c.JSON(http.StatusInternalServerError, gin.H{"error": "操作失败"}) } }