feat: LDAP-User-Sync in Mandanten-Benutzerliste
Neuer Endpoint POST /api/admin/tenants/{id}/ldap/sync importiert alle
LDAP-User (source=ldap) per UpsertLDAPUser in die Tenant-Benutzerliste.
Im Nutzer-Dialog erscheint ein "LDAP-Benutzer synchronisieren"-Button
wenn LDAP für den Mandanten aktiv ist. Unterstützt Univention UCS
(mailPrimaryAddress, inetOrgPerson). Benutzertabelle zeigt jetzt auch
die Quelle (local/ldap).
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -186,6 +186,66 @@ func queryRootDSE(conn *ldapv3.Conn) string {
|
||||
return strings.Join(parts, " ")
|
||||
}
|
||||
|
||||
// FetchUsers connects to LDAP and returns all user objects (up to 2000) for
|
||||
// bulk import / synchronisation. Unlike TestConnection it does not cap the
|
||||
// preview at 50 entries.
|
||||
func FetchUsers(cfg Config) ([]LDAPUser, error) {
|
||||
conn, err := dial(cfg)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("ldapauth: dial: %w", err)
|
||||
}
|
||||
defer conn.Close()
|
||||
|
||||
if err := conn.Bind(cfg.BindDN, cfg.BindPassword); err != nil {
|
||||
return nil, fmt.Errorf("ldapauth: service bind: %w", err)
|
||||
}
|
||||
|
||||
filter := cfg.UserFilter
|
||||
if filter == "" {
|
||||
filter = "(|(objectClass=person)(objectClass=user)(objectClass=inetOrgPerson))"
|
||||
} else {
|
||||
// If the UserFilter is a login filter like (uid=%s), make it a wildcard search.
|
||||
filter = strings.ReplaceAll(filter, "%s", "*")
|
||||
}
|
||||
|
||||
req := ldapv3.NewSearchRequest(
|
||||
cfg.BaseDN,
|
||||
ldapv3.ScopeWholeSubtree,
|
||||
ldapv3.NeverDerefAliases,
|
||||
2000, 60, false,
|
||||
filter,
|
||||
[]string{"dn", "uid", "cn", "displayName", "mail", "mailPrimaryAddress"},
|
||||
nil,
|
||||
)
|
||||
res, err := conn.Search(req)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("ldapauth: search users: %w", err)
|
||||
}
|
||||
|
||||
users := make([]LDAPUser, 0, len(res.Entries))
|
||||
for _, e := range res.Entries {
|
||||
mail := e.GetAttributeValue("mail")
|
||||
if mail == "" {
|
||||
mail = e.GetAttributeValue("mailPrimaryAddress")
|
||||
}
|
||||
displayName := e.GetAttributeValue("displayName")
|
||||
if displayName == "" {
|
||||
displayName = e.GetAttributeValue("cn")
|
||||
}
|
||||
uid := e.GetAttributeValue("uid")
|
||||
if uid == "" {
|
||||
continue // skip entries without a uid
|
||||
}
|
||||
users = append(users, LDAPUser{
|
||||
DN: e.DN,
|
||||
UID: uid,
|
||||
DisplayName: displayName,
|
||||
Mail: mail,
|
||||
})
|
||||
}
|
||||
return users, nil
|
||||
}
|
||||
|
||||
// listUsers searches for person/user objects and returns the total count (max 500)
|
||||
// plus a preview slice of up to 50 entries. Supports both AD (mail) and
|
||||
// Univention UCS (mailPrimaryAddress) mail attributes.
|
||||
|
||||
Reference in New Issue
Block a user