- 4 表设计: permissions, roles, role_permissions(m2m), user_roles - 多租户隔离: 角色和用户角色分配按 tenant_id 隔离 - 权限并集: 多角色用户取权限并集,无继承 - 系统角色保护: is_system 角色不可修改/删除 - 种子数据: 7 个默认权限 + 3 个系统角色(super_admin/tenant_admin/member) - 权限中间件: RequirePermission 支持按路由粒度控制 - API 路由: /api/v1/rbac/ 下完整 CRUD 端点 - fx 注册: RBAC Module 集成到 app.go
216 lines
4.6 KiB
Go
216 lines
4.6 KiB
Go
package interfaces
|
|
|
|
import (
|
|
"strconv"
|
|
|
|
"mengstack/internal/kernel/response"
|
|
"mengstack/internal/modules/rbac/application"
|
|
"mengstack/internal/modules/rbac/domain"
|
|
|
|
"github.com/gin-gonic/gin"
|
|
)
|
|
|
|
type Handler struct {
|
|
svc *application.Service
|
|
}
|
|
|
|
func NewHandler(svc *application.Service) *Handler {
|
|
return &Handler{svc: svc}
|
|
}
|
|
|
|
func (h *Handler) ListPermissions(c *gin.Context) {
|
|
module := c.Query("module")
|
|
|
|
var (
|
|
dtos []domain.PermissionDTO
|
|
err error
|
|
)
|
|
|
|
if module != "" {
|
|
dtos, err = h.svc.ListPermissionsByModule(c.Request.Context(), module)
|
|
} else {
|
|
dtos, err = h.svc.ListPermissions(c.Request.Context())
|
|
}
|
|
|
|
if err != nil {
|
|
response.HandleError(c, err)
|
|
return
|
|
}
|
|
|
|
response.Success(c, dtos)
|
|
}
|
|
|
|
func (h *Handler) CreateRole(c *gin.Context) {
|
|
var req domain.CreateRoleRequest
|
|
if err := c.ShouldBindJSON(&req); err != nil {
|
|
response.Fail(c, response.NewBadRequest("invalid request body"))
|
|
return
|
|
}
|
|
|
|
dto, err := h.svc.CreateRole(c.Request.Context(), req)
|
|
if err != nil {
|
|
response.HandleError(c, err)
|
|
return
|
|
}
|
|
|
|
response.Success(c, dto)
|
|
}
|
|
|
|
func (h *Handler) ListRoles(c *gin.Context) {
|
|
dtos, err := h.svc.ListRoles(c.Request.Context())
|
|
if err != nil {
|
|
response.HandleError(c, err)
|
|
return
|
|
}
|
|
|
|
response.Success(c, dtos)
|
|
}
|
|
|
|
func (h *Handler) GetRole(c *gin.Context) {
|
|
id, err := strconv.ParseUint(c.Param("id"), 10, 64)
|
|
if err != nil {
|
|
response.Fail(c, response.NewBadRequest("invalid role id"))
|
|
return
|
|
}
|
|
|
|
dto, err := h.svc.GetRole(c.Request.Context(), uint(id))
|
|
if err != nil {
|
|
response.HandleError(c, err)
|
|
return
|
|
}
|
|
|
|
response.Success(c, dto)
|
|
}
|
|
|
|
func (h *Handler) UpdateRole(c *gin.Context) {
|
|
id, err := strconv.ParseUint(c.Param("id"), 10, 64)
|
|
if err != nil {
|
|
response.Fail(c, response.NewBadRequest("invalid role id"))
|
|
return
|
|
}
|
|
|
|
var req domain.UpdateRoleRequest
|
|
if err := c.ShouldBindJSON(&req); err != nil {
|
|
response.Fail(c, response.NewBadRequest("invalid request body"))
|
|
return
|
|
}
|
|
|
|
dto, err := h.svc.UpdateRole(c.Request.Context(), uint(id), req)
|
|
if err != nil {
|
|
response.HandleError(c, err)
|
|
return
|
|
}
|
|
|
|
response.Success(c, dto)
|
|
}
|
|
|
|
func (h *Handler) DeleteRole(c *gin.Context) {
|
|
id, err := strconv.ParseUint(c.Param("id"), 10, 64)
|
|
if err != nil {
|
|
response.Fail(c, response.NewBadRequest("invalid role id"))
|
|
return
|
|
}
|
|
|
|
if err := h.svc.DeleteRole(c.Request.Context(), uint(id)); err != nil {
|
|
response.HandleError(c, err)
|
|
return
|
|
}
|
|
|
|
response.Success(c, nil)
|
|
}
|
|
|
|
func (h *Handler) SetRolePermissions(c *gin.Context) {
|
|
id, err := strconv.ParseUint(c.Param("id"), 10, 64)
|
|
if err != nil {
|
|
response.Fail(c, response.NewBadRequest("invalid role id"))
|
|
return
|
|
}
|
|
|
|
var req domain.SetRolePermissionsRequest
|
|
if err := c.ShouldBindJSON(&req); err != nil {
|
|
response.Fail(c, response.NewBadRequest("invalid request body"))
|
|
return
|
|
}
|
|
|
|
if err := h.svc.SetRolePermissions(c.Request.Context(), uint(id), req); err != nil {
|
|
response.HandleError(c, err)
|
|
return
|
|
}
|
|
|
|
response.Success(c, nil)
|
|
}
|
|
|
|
func (h *Handler) GetRolePermissions(c *gin.Context) {
|
|
id, err := strconv.ParseUint(c.Param("id"), 10, 64)
|
|
if err != nil {
|
|
response.Fail(c, response.NewBadRequest("invalid role id"))
|
|
return
|
|
}
|
|
|
|
dto, err := h.svc.GetRole(c.Request.Context(), uint(id))
|
|
if err != nil {
|
|
response.HandleError(c, err)
|
|
return
|
|
}
|
|
|
|
response.Success(c, dto.Permissions)
|
|
}
|
|
|
|
func (h *Handler) AssignRole(c *gin.Context) {
|
|
userID, err := strconv.ParseUint(c.Param("userId"), 10, 64)
|
|
if err != nil {
|
|
response.Fail(c, response.NewBadRequest("invalid user id"))
|
|
return
|
|
}
|
|
|
|
var req domain.AssignRoleRequest
|
|
if err := c.ShouldBindJSON(&req); err != nil {
|
|
response.Fail(c, response.NewBadRequest("invalid request body"))
|
|
return
|
|
}
|
|
|
|
if err := h.svc.AssignRoleToUser(c.Request.Context(), uint(userID), req); err != nil {
|
|
response.HandleError(c, err)
|
|
return
|
|
}
|
|
|
|
response.Success(c, nil)
|
|
}
|
|
|
|
func (h *Handler) RemoveRole(c *gin.Context) {
|
|
userID, err := strconv.ParseUint(c.Param("userId"), 10, 64)
|
|
if err != nil {
|
|
response.Fail(c, response.NewBadRequest("invalid user id"))
|
|
return
|
|
}
|
|
|
|
roleID, err := strconv.ParseUint(c.Param("roleId"), 10, 64)
|
|
if err != nil {
|
|
response.Fail(c, response.NewBadRequest("invalid role id"))
|
|
return
|
|
}
|
|
|
|
if err := h.svc.RemoveRoleFromUser(c.Request.Context(), uint(userID), uint(roleID)); err != nil {
|
|
response.HandleError(c, err)
|
|
return
|
|
}
|
|
|
|
response.Success(c, nil)
|
|
}
|
|
|
|
func (h *Handler) GetUserRoles(c *gin.Context) {
|
|
userID, err := strconv.ParseUint(c.Param("userId"), 10, 64)
|
|
if err != nil {
|
|
response.Fail(c, response.NewBadRequest("invalid user id"))
|
|
return
|
|
}
|
|
|
|
dtos, err := h.svc.GetUserPermissions(c.Request.Context(), uint(userID))
|
|
if err != nil {
|
|
response.HandleError(c, err)
|
|
return
|
|
}
|
|
|
|
response.Success(c, dtos)
|
|
}
|