Enrich AD users from SGU profile metadata
This commit is contained in:
@@ -2,6 +2,7 @@ using System.Collections.Concurrent;
|
||||
using System.DirectoryServices;
|
||||
using SGU.AuthBroker.Core.Directory;
|
||||
using SGU.AuthBroker.Core.Identity;
|
||||
using SGU.AuthBroker.Core.Profiles;
|
||||
using SGU.AuthBroker.Options;
|
||||
|
||||
namespace SGU.AuthBroker.Services;
|
||||
@@ -19,6 +20,7 @@ public sealed class ActiveDirectorySynchronizer(BrokerOptions options) : IActive
|
||||
|
||||
public async Task<DirectorySyncResult> SynchronizeAsync(
|
||||
UserIdentity identity,
|
||||
InstitutionalProfile? profile,
|
||||
string password,
|
||||
CancellationToken cancellationToken)
|
||||
{
|
||||
@@ -27,7 +29,7 @@ public sealed class ActiveDirectorySynchronizer(BrokerOptions options) : IActive
|
||||
try
|
||||
{
|
||||
return await Task.Run(
|
||||
() => Synchronize(identity, password),
|
||||
() => Synchronize(identity, profile, password),
|
||||
cancellationToken).ConfigureAwait(false);
|
||||
}
|
||||
finally
|
||||
@@ -40,7 +42,10 @@ public sealed class ActiveDirectorySynchronizer(BrokerOptions options) : IActive
|
||||
}
|
||||
}
|
||||
|
||||
private DirectorySyncResult Synchronize(UserIdentity identity, string password)
|
||||
private DirectorySyncResult Synchronize(
|
||||
UserIdentity identity,
|
||||
InstitutionalProfile? profile,
|
||||
string password)
|
||||
{
|
||||
string targetOuDn = options.GetOuDn(identity.Role);
|
||||
using DirectoryEntry root = Bind(options.BaseDn);
|
||||
@@ -95,6 +100,8 @@ public sealed class ActiveDirectorySynchronizer(BrokerOptions options) : IActive
|
||||
user.Properties["pwdLastSet"].Value = -1;
|
||||
user.CommitChanges();
|
||||
|
||||
TryApplyProfile(user, identity, profile);
|
||||
|
||||
return new DirectorySyncResult(
|
||||
options.DomainNetbios,
|
||||
identity.UserName,
|
||||
@@ -108,6 +115,54 @@ public sealed class ActiveDirectorySynchronizer(BrokerOptions options) : IActive
|
||||
}
|
||||
}
|
||||
|
||||
private static void TryApplyProfile(
|
||||
DirectoryEntry user,
|
||||
UserIdentity identity,
|
||||
InstitutionalProfile? profile)
|
||||
{
|
||||
if (profile is null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
try
|
||||
{
|
||||
SetOptionalProperty(user, "displayName", profile.DisplayName);
|
||||
SetOptionalProperty(user, "mail", profile.Email);
|
||||
SetOptionalProperty(user, "title", profile.JobTitle);
|
||||
SetOptionalProperty(user, "department", profile.Department);
|
||||
SetOptionalProperty(user, "employeeType", profile.EmployeeType);
|
||||
if (string.Equals(profile.EmployeeNumber, identity.NumericId, StringComparison.Ordinal))
|
||||
{
|
||||
SetOptionalProperty(user, "employeeID", profile.EmployeeNumber);
|
||||
}
|
||||
|
||||
user.CommitChanges();
|
||||
}
|
||||
catch
|
||||
{
|
||||
// Metadata is intentionally best-effort. User creation, password sync,
|
||||
// and account enablement have already committed successfully.
|
||||
try
|
||||
{
|
||||
user.RefreshCache();
|
||||
}
|
||||
catch
|
||||
{
|
||||
// Discarding the optional property cache must not alter the
|
||||
// already committed password synchronization result.
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private static void SetOptionalProperty(DirectoryEntry entry, string propertyName, string? value)
|
||||
{
|
||||
if (!string.IsNullOrWhiteSpace(value))
|
||||
{
|
||||
entry.Properties[propertyName].Value = value;
|
||||
}
|
||||
}
|
||||
|
||||
private DirectoryEntry BindOrCreateOu(string ouDn, DirectoryEntry root)
|
||||
{
|
||||
try
|
||||
|
||||
Reference in New Issue
Block a user