package middleware import ( "github.com/gin-gonic/gin" "icloudapp.cn/tools/entity" "icloudapp.cn/tools/model" utString "icloudapp.cn/tools/util/string" "strings" ) func RoleMiddleWare() func(c *gin.Context) { return func(ctx *gin.Context) { //获取用户的所有分组 uid := utString.ConvertInt64(ctx.GetString("uid")) if uid == 0 { accessDenied(ctx, "请先登录后再试") ctx.Abort() return } _, err := model.NewMRoles(ctx).Verify(uid, ctx.Request.URL) if err != nil { accessDenied(ctx, err.Error()) ctx.Abort() return } ctx.Next() /* url := ctx.Request.URL.String() path := ctx.Request.URL.Path userGroups := service.NewUserGroup(ctx).UserGroups(uid) splitGroups := strings.Split(userGroups.Groups, ",") var groupsID []int64 for _, v := range splitGroups { groupsID = append(groupsID, utString.ConvertInt64(v)) } if len(groupsID) == 0 { accessDenied(ctx, "无访问组权限") ctx.Abort() return } //获取分组对应的权限 groupsField, _ := service.NewGroup(ctx).Infos(groupsID...) var rolesID strings.Builder for _, v := range groupsField { if v == nil { continue } rolesID.WriteString(v.Roles + ",") } //获取权限对应的model roles := uniqueToInt64(rolesID.String(), ",") if len(roles) == 0 { accessDenied(ctx, "无权限访问") ctx.Abort() return } mRole := service.NewRoles(ctx) modelsField, _ := mRole.Infos(roles...) var modelIds strings.Builder for _, v := range modelsField { modelIds.WriteString(v.ModelIds + ",") } //获取对应的model modulesId := uniqueToInt64(modelIds.String(), ",") modules := service.NewModule(ctx) moduleField, _ := modules.Infos(modulesId...) //验证request是否有权限 matchedURL := make([]string, 0) for _, module := range moduleField { moduleURL := module.ModelURL //设置的url和请求的path一样直接通过,如果是带参数或*需要额外处理 if moduleURL == path { ctx.Next() return } else if strings.Contains(moduleURL, path) { matchedURL = append(matchedURL, moduleURL) } else if strings.Contains(moduleURL, ".*") { //如果是以.*结尾的,将modelURL才分成两部分,前半部分能匹配上当前的url就可以 urlSplit := strings.Split(moduleURL, ",") if strings.Contains(url, urlSplit[0]) { ctx.Next() return } } } if len(matchedURL) == 0 { accessDenied(ctx, "无模块访问权限") ctx.Abort() return } for _, singleURL := range matchedURL { //这里需要区分url中有没有参数,没有参数就直接过,有参数就再验证参数 parseString, _ := url2.ParseString(singleURL) queries := parseString.Query() for name, _ := range queries { if queries.Get(name) != ctx.Request.URL.Query().Get(name) { accessDenied(ctx, "权限无匹配") ctx.Abort() return } } } ctx.Next()*/ } } func accessDenied(ctx *gin.Context, msg string) { entity.ResponseNormal(ctx, entity.CodeDenied, msg, []interface{}{}) } func splitStrToInt64(str, sep string) []int64 { splitSlice := strings.Split(str, sep) var res []int64 for _, v := range splitSlice { res = append(res, utString.ConvertInt64(v)) } return res } func uniqueToInt64(str, sep string) []int64 { var res []int64 splitSlice := splitStrToInt64(str, sep) splitMap := make(map[int64]bool, 0) for _, v := range splitSlice { if v == 0 { continue } if _, ok := splitMap[v]; ok { continue } splitMap[v] = true res = append(res, v) } return res }