mirror of
https://github.com/coder/coder.git
synced 2025-07-08 11:39:50 +00:00
chore: support multi-org group sync with runtime configuration (#14578)
- Implement multi-org group sync - Implement runtime configuration to change sync behavior - Legacy group sync migrated to new package
This commit is contained in:
70
enterprise/coderd/enidpsync/groups.go
Normal file
70
enterprise/coderd/enidpsync/groups.go
Normal file
@ -0,0 +1,70 @@
|
||||
package enidpsync
|
||||
|
||||
import (
|
||||
"context"
|
||||
"net/http"
|
||||
|
||||
"github.com/golang-jwt/jwt/v4"
|
||||
|
||||
"github.com/coder/coder/v2/coderd/idpsync"
|
||||
"github.com/coder/coder/v2/codersdk"
|
||||
)
|
||||
|
||||
func (e EnterpriseIDPSync) GroupSyncEnabled() bool {
|
||||
return e.entitlements.Enabled(codersdk.FeatureTemplateRBAC)
|
||||
}
|
||||
|
||||
// ParseGroupClaims parses the user claims and handles deployment wide group behavior.
|
||||
// Almost all behavior is deferred since each organization configures it's own
|
||||
// group sync settings.
|
||||
// GroupAllowList is implemented here to prevent login by unauthorized users.
|
||||
// TODO: GroupAllowList overlaps with the default organization group sync settings.
|
||||
func (e EnterpriseIDPSync) ParseGroupClaims(ctx context.Context, mergedClaims jwt.MapClaims) (idpsync.GroupParams, *idpsync.HTTPError) {
|
||||
if !e.GroupSyncEnabled() {
|
||||
return e.AGPLIDPSync.ParseGroupClaims(ctx, mergedClaims)
|
||||
}
|
||||
|
||||
if e.GroupField != "" && len(e.GroupAllowList) > 0 {
|
||||
groupsRaw, ok := mergedClaims[e.GroupField]
|
||||
if !ok {
|
||||
return idpsync.GroupParams{}, &idpsync.HTTPError{
|
||||
Code: http.StatusForbidden,
|
||||
Msg: "Not a member of an allowed group",
|
||||
Detail: "You have no groups in your claims!",
|
||||
RenderStaticPage: true,
|
||||
}
|
||||
}
|
||||
parsedGroups, err := idpsync.ParseStringSliceClaim(groupsRaw)
|
||||
if err != nil {
|
||||
return idpsync.GroupParams{}, &idpsync.HTTPError{
|
||||
Code: http.StatusBadRequest,
|
||||
Msg: "Failed read groups from claims for allow list check. Ask an administrator for help.",
|
||||
Detail: err.Error(),
|
||||
RenderStaticPage: true,
|
||||
}
|
||||
}
|
||||
|
||||
inAllowList := false
|
||||
AllowListCheckLoop:
|
||||
for _, group := range parsedGroups {
|
||||
if _, ok := e.GroupAllowList[group]; ok {
|
||||
inAllowList = true
|
||||
break AllowListCheckLoop
|
||||
}
|
||||
}
|
||||
|
||||
if !inAllowList {
|
||||
return idpsync.GroupParams{}, &idpsync.HTTPError{
|
||||
Code: http.StatusForbidden,
|
||||
Msg: "Not a member of an allowed group",
|
||||
Detail: "Ask an administrator to add one of your groups to the allow list.",
|
||||
RenderStaticPage: true,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return idpsync.GroupParams{
|
||||
SyncEnabled: true,
|
||||
MergedClaims: mergedClaims,
|
||||
}, nil
|
||||
}
|
Reference in New Issue
Block a user