|
|
|
@ -247,53 +247,9 @@ func basicRoleBindingsCollector(store db.DB) legacyTupleCollector { |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
func teamRoleBindingsCollector(store db.DB) legacyTupleCollector { |
|
|
|
|
func roleBindingsCollector(store db.DB) legacyTupleCollector { |
|
|
|
|
return func(ctx context.Context, orgID int64) (map[string]map[string]*openfgav1.TupleKey, error) { |
|
|
|
|
query := ` |
|
|
|
|
SELECT t.uid AS team_uid, r.uid AS role_uid |
|
|
|
|
FROM team_role tr |
|
|
|
|
INNER JOIN team t ON tr.team_id = t.id |
|
|
|
|
INNER JOIN role r ON tr.role_id = r.id |
|
|
|
|
WHERE t.org_id = ? |
|
|
|
|
AND r.name NOT LIKE 'managed:%' |
|
|
|
|
` |
|
|
|
|
type Binding struct { |
|
|
|
|
TeamUID string `xorm:"team_uid"` |
|
|
|
|
RoleUID string `xorm:"role_uid"` |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
var bindings []Binding |
|
|
|
|
err := store.WithDbSession(ctx, func(sess *db.Session) error { |
|
|
|
|
return sess.SQL(query, orgID).Find(&bindings) |
|
|
|
|
}) |
|
|
|
|
|
|
|
|
|
if err != nil { |
|
|
|
|
return nil, err |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
tuples := make(map[string]map[string]*openfgav1.TupleKey) |
|
|
|
|
|
|
|
|
|
for _, b := range bindings { |
|
|
|
|
tuple := &openfgav1.TupleKey{ |
|
|
|
|
User: zanzana.NewTupleEntry(zanzana.TypeTeam, b.TeamUID, zanzana.RelationTeamMember), |
|
|
|
|
Relation: zanzana.RelationAssignee, |
|
|
|
|
Object: zanzana.NewTupleEntry(zanzana.TypeRole, b.RoleUID, ""), |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
if tuples[tuple.Object] == nil { |
|
|
|
|
tuples[tuple.Object] = make(map[string]*openfgav1.TupleKey) |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
tuples[tuple.Object][tuple.String()] = tuple |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
return tuples, nil |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
func userRoleBindingsCollector(store db.DB) legacyTupleCollector { |
|
|
|
|
return func(ctx context.Context, orgID int64) (map[string]map[string]*openfgav1.TupleKey, error) { |
|
|
|
|
query := ` |
|
|
|
|
userQuery := ` |
|
|
|
|
SELECT u.uid AS user_uid, u.is_service_account as is_service_account, r.uid AS role_uid |
|
|
|
|
FROM user_role ur |
|
|
|
|
INNER JOIN ` + store.GetDialect().Quote("user") + ` u ON ur.user_id = u.id |
|
|
|
@ -304,97 +260,66 @@ func userRoleBindingsCollector(store db.DB) legacyTupleCollector { |
|
|
|
|
type Binding struct { |
|
|
|
|
UserUID string `xorm:"user_uid"` |
|
|
|
|
IsServiceAccount bool `xorm:"is_service_account"` |
|
|
|
|
TeamUID string `xorm:"team_uid"` |
|
|
|
|
RoleUID string `xorm:"role_uid"` |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
var bindings []Binding |
|
|
|
|
bindings := make([]Binding, 0) |
|
|
|
|
var userBindings []Binding |
|
|
|
|
err := store.WithDbSession(ctx, func(sess *db.Session) error { |
|
|
|
|
return sess.SQL(query, orgID).Find(&bindings) |
|
|
|
|
return sess.SQL(userQuery, orgID).Find(&userBindings) |
|
|
|
|
}) |
|
|
|
|
|
|
|
|
|
if err != nil { |
|
|
|
|
return nil, err |
|
|
|
|
} |
|
|
|
|
bindings = append(bindings, userBindings...) |
|
|
|
|
|
|
|
|
|
tuples := make(map[string]map[string]*openfgav1.TupleKey) |
|
|
|
|
|
|
|
|
|
for _, b := range bindings { |
|
|
|
|
userType := zanzana.TypeUser |
|
|
|
|
if b.IsServiceAccount { |
|
|
|
|
userType = zanzana.TypeServiceAccount |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
tuple := &openfgav1.TupleKey{ |
|
|
|
|
User: zanzana.NewTupleEntry(userType, b.UserUID, ""), |
|
|
|
|
Relation: zanzana.RelationAssignee, |
|
|
|
|
Object: zanzana.NewTupleEntry(zanzana.TypeRole, b.RoleUID, ""), |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
if tuples[tuple.Object] == nil { |
|
|
|
|
tuples[tuple.Object] = make(map[string]*openfgav1.TupleKey) |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
tuples[tuple.Object][tuple.String()] = tuple |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
return tuples, nil |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
func rolePermissionsCollector(store db.DB) legacyTupleCollector { |
|
|
|
|
return func(ctx context.Context, orgID int64) (map[string]map[string]*openfgav1.TupleKey, error) { |
|
|
|
|
var query = ` |
|
|
|
|
SELECT r.uid as role_uid, p.action, p.kind, p.identifier |
|
|
|
|
FROM permission p |
|
|
|
|
INNER JOIN role r ON p.role_id = r.id |
|
|
|
|
LEFT JOIN builtin_role br ON r.id = br.role_id |
|
|
|
|
WHERE (r.org_id = 0 OR r.org_id = ?) |
|
|
|
|
teamQuery := ` |
|
|
|
|
SELECT t.uid AS team_uid, r.uid AS role_uid |
|
|
|
|
FROM team_role tr |
|
|
|
|
INNER JOIN team t ON tr.team_id = t.id |
|
|
|
|
INNER JOIN role r ON tr.role_id = r.id |
|
|
|
|
WHERE t.org_id = ? |
|
|
|
|
AND r.name NOT LIKE 'managed:%' |
|
|
|
|
AND r.name NOT LIKE 'fixed:%' |
|
|
|
|
` |
|
|
|
|
|
|
|
|
|
type Permission struct { |
|
|
|
|
Action string `xorm:"action"` |
|
|
|
|
Kind string |
|
|
|
|
Identifier string |
|
|
|
|
RoleUID string `xorm:"role_uid"` |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
var permissions []Permission |
|
|
|
|
err := store.WithDbSession(ctx, func(sess *db.Session) error { |
|
|
|
|
return sess.SQL(query, orgID).Find(&permissions) |
|
|
|
|
var teamBindings []Binding |
|
|
|
|
err = store.WithDbSession(ctx, func(sess *db.Session) error { |
|
|
|
|
return sess.SQL(teamQuery, orgID).Find(&teamBindings) |
|
|
|
|
}) |
|
|
|
|
if err != nil { |
|
|
|
|
return nil, err |
|
|
|
|
} |
|
|
|
|
bindings = append(bindings, teamBindings...) |
|
|
|
|
|
|
|
|
|
tuples := make(map[string]map[string]*openfgav1.TupleKey) |
|
|
|
|
for _, b := range bindings { |
|
|
|
|
var tuple *openfgav1.TupleKey |
|
|
|
|
|
|
|
|
|
for _, p := range permissions { |
|
|
|
|
tuple, ok := zanzana.TranslateToResourceTuple( |
|
|
|
|
zanzana.NewTupleEntry(zanzana.TypeRole, p.RoleUID, zanzana.RelationAssignee), |
|
|
|
|
p.Action, |
|
|
|
|
p.Kind, |
|
|
|
|
p.Identifier, |
|
|
|
|
) |
|
|
|
|
if !ok { |
|
|
|
|
continue |
|
|
|
|
} |
|
|
|
|
if b.UserUID != "" { |
|
|
|
|
userType := zanzana.TypeUser |
|
|
|
|
if b.IsServiceAccount { |
|
|
|
|
userType = zanzana.TypeServiceAccount |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
if tuples[tuple.Object] == nil { |
|
|
|
|
tuples[tuple.Object] = make(map[string]*openfgav1.TupleKey) |
|
|
|
|
} |
|
|
|
|
tuple = &openfgav1.TupleKey{ |
|
|
|
|
User: zanzana.NewTupleEntry(userType, b.UserUID, ""), |
|
|
|
|
Relation: zanzana.RelationAssignee, |
|
|
|
|
Object: zanzana.NewTupleEntry(zanzana.TypeRole, b.RoleUID, ""), |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
// For resource actions on folders we need to merge the tuples into one with combined subresources.
|
|
|
|
|
if zanzana.IsFolderResourceTuple(tuple) { |
|
|
|
|
key := tupleStringWithoutCondition(tuple) |
|
|
|
|
if t, ok := tuples[tuple.Object][key]; ok { |
|
|
|
|
zanzana.MergeFolderResourceTuples(t, tuple) |
|
|
|
|
} else { |
|
|
|
|
tuples[tuple.Object][key] = tuple |
|
|
|
|
if tuples[tuple.Object] == nil { |
|
|
|
|
tuples[tuple.Object] = make(map[string]*openfgav1.TupleKey) |
|
|
|
|
} |
|
|
|
|
} else if b.TeamUID != "" { |
|
|
|
|
tuple = &openfgav1.TupleKey{ |
|
|
|
|
User: zanzana.NewTupleEntry(zanzana.TypeTeam, b.TeamUID, zanzana.RelationTeamMember), |
|
|
|
|
Relation: zanzana.RelationAssignee, |
|
|
|
|
Object: zanzana.NewTupleEntry(zanzana.TypeRole, b.RoleUID, ""), |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
continue |
|
|
|
|
if tuples[tuple.Object] == nil { |
|
|
|
|
tuples[tuple.Object] = make(map[string]*openfgav1.TupleKey) |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
tuples[tuple.Object][tuple.String()] = tuple |
|
|
|
@ -404,15 +329,15 @@ func rolePermissionsCollector(store db.DB) legacyTupleCollector { |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
func fixedRolePermissionsCollector(store db.DB) legacyTupleCollector { |
|
|
|
|
return func(ctx context.Context, _ int64) (map[string]map[string]*openfgav1.TupleKey, error) { |
|
|
|
|
func rolePermissionsCollector(store db.DB) legacyTupleCollector { |
|
|
|
|
return func(ctx context.Context, orgID int64) (map[string]map[string]*openfgav1.TupleKey, error) { |
|
|
|
|
var query = ` |
|
|
|
|
SELECT r.uid as role_uid, p.action, p.kind, p.identifier |
|
|
|
|
FROM permission p |
|
|
|
|
INNER JOIN role r ON p.role_id = r.id |
|
|
|
|
LEFT JOIN builtin_role br ON r.id = br.role_id |
|
|
|
|
WHERE r.org_id = 0 |
|
|
|
|
AND r.name LIKE 'fixed:%' |
|
|
|
|
WHERE (r.org_id = 0 OR r.org_id = ?) |
|
|
|
|
AND r.name NOT LIKE 'managed:%' |
|
|
|
|
` |
|
|
|
|
|
|
|
|
|
type Permission struct { |
|
|
|
@ -424,7 +349,7 @@ func fixedRolePermissionsCollector(store db.DB) legacyTupleCollector { |
|
|
|
|
|
|
|
|
|
var permissions []Permission |
|
|
|
|
err := store.WithDbSession(ctx, func(sess *db.Session) error { |
|
|
|
|
return sess.SQL(query).Find(&permissions) |
|
|
|
|
return sess.SQL(query, orgID).Find(&permissions) |
|
|
|
|
}) |
|
|
|
|
if err != nil { |
|
|
|
|
return nil, err |
|
|
|
@ -455,6 +380,7 @@ func fixedRolePermissionsCollector(store db.DB) legacyTupleCollector { |
|
|
|
|
} else { |
|
|
|
|
tuples[tuple.Object][key] = tuple |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
continue |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|