forked from danderson/provision
/
roles.go
123 lines (108 loc) · 2.38 KB
/
roles.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
package backend
import (
"github.com/digitalrebar/provision/backend/index"
"github.com/digitalrebar/provision/models"
"github.com/digitalrebar/store"
)
type Role struct {
*models.Role
validate
cachedClaims models.Claims
}
func (r *Role) SaveClean() store.KeySaver {
mod := *r.Role
mod.ClearValidation()
return ModelToBackend(&mod)
}
func (r *Role) CompiledClaims() models.Claims {
if r.cachedClaims == nil {
r.cachedClaims = r.Role.Compile()
}
return r.cachedClaims
}
func AsRole(r models.Model) *Role {
return r.(*Role)
}
func AsRoles(o []models.Model) []*Role {
res := make([]*Role, len(o))
for i := range o {
res[i] = AsRole(o[i])
}
return res
}
func (r *Role) New() store.KeySaver {
res := &Role{Role: &models.Role{}}
res.Fill()
res.rt = r.rt
return res
}
func (r *Role) Indexes() map[string]index.Maker {
fix := AsRole
res := index.MakeBaseIndexes(r)
res["Name"] = index.Make(
true,
"string",
func(i, j models.Model) bool {
return fix(i).Name < fix(j).Name
},
func(ref models.Model) (gte, gt index.Test) {
name := fix(ref).Name
return func(s models.Model) bool {
return fix(s).Name >= name
},
func(s models.Model) bool {
return fix(s).Name > name
}
},
func(s string) (models.Model, error) {
res := fix(r.New())
res.Name = s
return res, nil
})
return res
}
var roleLockMap = map[string][]string{
"get": []string{"roles"},
"create": []string{"roles"},
"update": []string{"roles"},
"patch": []string{"roles"},
"delete": []string{"users", "roles"},
"actions": []string{"roles"},
}
func (r *Role) Locks(action string) []string {
return roleLockMap[action]
}
func (r *Role) Validate() {
r.Role.Validate()
r.AddError(index.CheckUnique(r, r.rt.stores("roles").Items()))
r.SetValid()
r.SetAvailable()
}
func (r *Role) BeforeSave() error {
r.Validate()
if !r.Validated {
return r.MakeError(422, ValidationError, r)
}
return nil
}
func (r *Role) AfterSave() {
r.cachedClaims = nil
}
func (r *Role) OnLoad() error {
defer func() { r.rt = nil }()
r.Fill()
return r.BeforeSave()
}
func (r *Role) BeforeDelete() error {
e := &models.Error{Code: 409, Type: StillInUseError, Model: r.Prefix(), Key: r.Key()}
for _, u := range r.rt.d("users").Items() {
user := AsUser(u)
for _, name := range user.Roles {
if name == r.Name {
e.Errorf("In use by User %s", user.Name)
break
}
}
}
return e.HasError()
}