背景
目前系统的权限体系存储了权限,权限组,角色之间的关联关系,如下图所示,
目前的数据结构如下,
type PermissionGroup struct {
ID uint64 `gorm:"primarykey"` // 数据库ID
AppID uint64 `gorm:"uniqueIndex:idx_permission_groups_name"`
Name string `gorm:"not null;uniqueIndex:idx_permission_groups_name" yaml:"name"`
Title string `yaml:"title"`
ParentID uint64 // 父权限ID
PermissionGroupPermission []*PermissionGroupPermission `gorm:"foreignKey:GroupName;references:Name"`
}
type PermissionGroupPermission struct {
ID uint64 `gorm:"primarykey"` // 数据库ID
AppID uint64 `gorm:"uniqueIndex:idx_group_permissions"`
GroupName string `gorm:"uniqueIndex:idx_group_permissions"`
PermissionKey string `gorm:"uniqueIndex:idx_group_permissions"`
PermissionGroup *PermissionGroup `gorm:"foreignkey:Name;references:GroupName"`
Permission *Permission `gorm:"foreignkey:UniqueKey;references:PermissionKey"`
}
type Permission struct {
ID uint64 `gorm:"primarykey"` // 数据库ID
Name string `gorm:"not null;uniqueIndex:idx_permissions_name" yaml:"name"`
Action string `gorm:"uniqueIndex:idx_permissions_name" yaml:"action"`
UniqueKey string `gorm:"uniqueIndex:idx_unique_key" yaml:"unique_key"`
Title string `yaml:"title"`
}其实存在了一些问题,
- 没有必要存储 permissions, permission_group_permissions, permission_groups
- 无法调整菜单顺序
- 无法指定菜单依赖
方案
- 减少对于 permissions, permission_group_permissions, permission_groups 的数据存储
- 整份权限元数据以配置的方式进行加载
- 权限组增加依赖字段
如下图所示,
效果如下,
- 直接返回给前端树形结构,方便使用
- 权限组 key 自行保证唯一
- 服务端只需要保存权限组 key
- 权限组层级可以统一配置公共路由
- 通过读取权限组配置可以随时调整顺序
- 可以指定权限组依赖关系
数据结构如下,
type PermissionGroup struct {
Name string `yaml:"name"`
Title string `yaml:"title"`
Needs []string `yaml:"needs"`
Groups []*PermissionGroup `yaml:"groups"`
Permissions []struct {
Method string `yaml:"method"`
Path string `yaml:"path"`
} `yaml:"permissions"`
}- name: "operation-report"
title: "运营报表"
groups:
- name: "overview-data"
title: "概览数据"
groups:
- name: "overview-day"
title: "查看日概览"
permissions:
- method: GET
path: overview-new
- name: "edit-overview"
title: "编辑概览看板"
needs:
- overview-day
permissions:
- method: PUT
path: edit-overview