完善角色与消息权限:收紧板管内容处置,彻底删除仅站长,并统一管理删帖/评弹窗。
Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
@@ -13,15 +13,17 @@ const (
|
||||
PermAnnouncements = "announcements" // 公告管理(管理员及以上)
|
||||
PermSettings = "settings" // 站点外观设置(超管/站长)
|
||||
PermModeration = "moderation" // 内容审核(任意管理角色,板块范围受限)
|
||||
PermMessages = "messages" // 后台消息管理(站长/超管/站点消息 flag;群管另有业务层放行)
|
||||
)
|
||||
|
||||
// Actor 当前请求操作者的实时权限快照(每次后台请求从 DB 现取,
|
||||
// 不依赖 JWT 内的 role claim,角色/授权变更立即生效)
|
||||
type Actor struct {
|
||||
ID uint
|
||||
Username string
|
||||
Role model.Role
|
||||
BoardIDs []uint // 板块管理员被授权的板块;其他角色为空
|
||||
ID uint
|
||||
Username string
|
||||
Role model.Role
|
||||
BoardIDs []uint // 板块管理员被授权的板块;其他角色为空
|
||||
CanManageMessages bool // 站点级消息管理 flag(站长授予);站长/超管不必依赖此字段
|
||||
}
|
||||
|
||||
// IsStaff 是否管理团队成员
|
||||
@@ -41,10 +43,28 @@ func (a *Actor) HasPerm(p string) bool {
|
||||
return model.RoleLevel(a.Role) >= model.RoleLevel(model.RoleAdmin)
|
||||
case PermModeration:
|
||||
return a.IsStaff()
|
||||
case PermMessages:
|
||||
return a.HasSiteMessagePerm()
|
||||
}
|
||||
return false
|
||||
}
|
||||
|
||||
// HasSiteMessagePerm 站点级消息管理:站长/超管固有,或被授予 CanManageMessages
|
||||
func (a *Actor) HasSiteMessagePerm() bool {
|
||||
if a == nil {
|
||||
return false
|
||||
}
|
||||
if a.Role == model.RoleOwner || a.Role == model.RoleSuperAdmin {
|
||||
return true
|
||||
}
|
||||
return a.CanManageMessages
|
||||
}
|
||||
|
||||
// CanPurgeContent 彻底删除帖/评:仅站长
|
||||
func (a *Actor) CanPurgeContent() bool {
|
||||
return a != nil && a.Role == model.RoleOwner
|
||||
}
|
||||
|
||||
// CanModerateBoard 是否可管理指定板块的内容:
|
||||
// 管理员及以上不限板块;板块管理员仅限被授权板块
|
||||
func (a *Actor) CanModerateBoard(boardID uint) bool {
|
||||
@@ -65,6 +85,17 @@ func (a *Actor) CanModerateBoard(boardID uint) bool {
|
||||
return false
|
||||
}
|
||||
|
||||
// CanModerateAuthor 板管不可软删/恢复管理员及以上作者的内容;其他角色不受此限
|
||||
func (a *Actor) CanModerateAuthor(authorRole model.Role) bool {
|
||||
if a == nil {
|
||||
return false
|
||||
}
|
||||
if a.Role == model.RoleBoardAdmin {
|
||||
return model.RoleLevel(authorRole) < model.RoleLevel(model.RoleAdmin)
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
||||
// CanAssignRole 操作者能否把他人设置为目标角色(站长不可被授予,仅站长可授予超管)
|
||||
func (a *Actor) CanAssignRole(target model.Role) bool {
|
||||
if a == nil {
|
||||
@@ -82,10 +113,13 @@ func (a *Actor) CanAssignRole(target model.Role) bool {
|
||||
// LoadActor 读取用户实时角色与板块授权
|
||||
func (s *AuthService) LoadActor(id uint) (*Actor, error) {
|
||||
var u model.User
|
||||
if err := s.db.Select("id", "username", "role").First(&u, id).Error; err != nil {
|
||||
if err := s.db.Select("id", "username", "role", "can_manage_messages").First(&u, id).Error; err != nil {
|
||||
return nil, err
|
||||
}
|
||||
actor := &Actor{ID: u.ID, Username: u.Username, Role: u.Role, BoardIDs: []uint{}}
|
||||
actor := &Actor{
|
||||
ID: u.ID, Username: u.Username, Role: u.Role, BoardIDs: []uint{},
|
||||
CanManageMessages: u.CanManageMessages,
|
||||
}
|
||||
if u.Role == model.RoleBoardAdmin {
|
||||
var ids []uint
|
||||
if err := s.db.Model(&model.UserBoard{}).
|
||||
@@ -99,6 +133,15 @@ func (s *AuthService) LoadActor(id uint) (*Actor, error) {
|
||||
return actor, nil
|
||||
}
|
||||
|
||||
// GetUserRole 读取用户角色(内容作者保护用);用户不存在返回 user
|
||||
func (s *AuthService) GetUserRole(id uint) (model.Role, error) {
|
||||
var u model.User
|
||||
if err := s.db.Select("role").First(&u, id).Error; err != nil {
|
||||
return model.RoleUser, err
|
||||
}
|
||||
return u.Role, nil
|
||||
}
|
||||
|
||||
// GetUserBoardIDs 读取用户被授权的板块 ID(供 /me 等场景)
|
||||
func (s *AuthService) GetUserBoardIDs(id uint) ([]uint, error) {
|
||||
var ids []uint
|
||||
|
||||
Reference in New Issue
Block a user