148 lines
3.7 KiB
Go
148 lines
3.7 KiB
Go
package main
|
|
|
|
import (
|
|
"sort"
|
|
)
|
|
|
|
func (server *Server) memberOfAdd(member string, group string) {
|
|
// Retreive previous memberOf value
|
|
memberGroups, err := server.getAttribute(member, ATTR_MEMBEROF)
|
|
if err != nil {
|
|
server.logger.Warnf("Could not add %s to memberOf of %s: %s", group, member, err)
|
|
return
|
|
}
|
|
|
|
// Return early if group is already in memberOf
|
|
for _, mb := range memberGroups {
|
|
if mb == group {
|
|
server.logger.Warnf("Inconsistency detected, %s was memberOf %s at a time when it didn't exist! (not an issue anymore)",
|
|
member, group)
|
|
return
|
|
}
|
|
}
|
|
|
|
// Add group to memberOf
|
|
memberGroups = append(memberGroups, group)
|
|
err = server.addElements(member, Entry{
|
|
ATTR_MEMBEROF: memberGroups,
|
|
})
|
|
if err != nil {
|
|
server.logger.Warnf("Could not add %s to memberOf of %s: %s", group, member, err)
|
|
}
|
|
}
|
|
|
|
func (server *Server) memberOfRemove(member string, group string) {
|
|
// Retreive previous memberOf value
|
|
memberOf, err := server.getAttribute(member, ATTR_MEMBEROF)
|
|
if err != nil || memberOf == nil {
|
|
server.logger.Warnf("Could not remove %s from memberOf of %s: %s", group, member, err)
|
|
return
|
|
}
|
|
|
|
// Filter out group
|
|
newMemberOf := []string{}
|
|
for _, mb := range memberOf {
|
|
if mb != group {
|
|
newMemberOf = append(newMemberOf, group)
|
|
}
|
|
}
|
|
|
|
// Return early if group already not in memberOf
|
|
if len(newMemberOf) == len(memberOf) {
|
|
server.logger.Warnf("Inconsistency detected, %s was not memberOf %s at a time when it should have been! (not an issue anymore)",
|
|
member, group)
|
|
return
|
|
}
|
|
|
|
// Update value of memberOf
|
|
err = server.addElements(member, Entry{
|
|
ATTR_MEMBEROF: newMemberOf,
|
|
})
|
|
if err != nil {
|
|
server.logger.Warnf("Could not remove %s from memberOf of %s: %s", group, member, err)
|
|
}
|
|
}
|
|
|
|
func (server *Server) memberOfResync() error {
|
|
server.logger.Warnf("Starting resync of member/memberOf values")
|
|
|
|
// Load the whole LDAP database
|
|
basePath, err := dnToConsul(server.config.Suffix)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
|
|
data, _, err := server.kv.List(basePath, nil)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
|
|
entries, err := parseConsulResult(data)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
|
|
// Check member values for all objects, and remove deleted objects
|
|
// Calculate new memberOf sets for all objects
|
|
newMemberOf := make(map[string][]string)
|
|
for dn := range entries {
|
|
newMemberOf[dn] = []string{}
|
|
}
|
|
|
|
for dn, entry := range entries {
|
|
member, ok := entry[ATTR_MEMBER]
|
|
if !ok {
|
|
continue
|
|
}
|
|
keepMember := []string{}
|
|
for _, mem := range member {
|
|
if _, exists := entries[mem]; exists {
|
|
keepMember = append(keepMember, mem)
|
|
newMemberOf[mem] = append(newMemberOf[mem], dn)
|
|
} else {
|
|
server.logger.Warnf("Fixing: %s had as member %s which doesn't exist", dn, mem)
|
|
}
|
|
}
|
|
if len(keepMember) != len(member) {
|
|
server.logger.Warnf("Writing new member list for %s", dn)
|
|
err = server.addElements(dn, Entry{
|
|
ATTR_MEMBER: keepMember,
|
|
})
|
|
if err != nil {
|
|
return err
|
|
}
|
|
}
|
|
}
|
|
|
|
// Write updated memberOf values
|
|
for dn, newMemberOfV := range newMemberOf {
|
|
prevMemberOf := []string{}
|
|
if v, ok := entries[dn][ATTR_MEMBEROF]; ok {
|
|
prevMemberOf = v
|
|
}
|
|
different := (len(prevMemberOf) != len(newMemberOfV))
|
|
if !different {
|
|
sort.Strings(newMemberOfV)
|
|
sort.Strings(prevMemberOf)
|
|
for i := range newMemberOfV {
|
|
if newMemberOfV[i] != prevMemberOf[i] {
|
|
different = true
|
|
break
|
|
}
|
|
}
|
|
}
|
|
if different {
|
|
server.logger.Warnf("Fixing memberOf for %s (%d -> %d)",
|
|
dn, len(prevMemberOf), len(newMemberOfV))
|
|
err = server.addElements(dn, Entry{
|
|
ATTR_MEMBEROF: newMemberOfV,
|
|
})
|
|
if err != nil {
|
|
return err
|
|
}
|
|
}
|
|
}
|
|
|
|
server.logger.Warnf("Done resyncing member/memberOf values")
|
|
return nil
|
|
}
|