2017-10-18 160 views
12

我們使用B2C並將客戶編號作爲擴展字段存儲在用戶上。一個用戶可以擁有一個或多個客戶,並且它們以逗號分隔的字符串存儲。通過用戶的自定義屬性搜索Active Directory B2C

我現在正在做的效率非常低: 1.獲取所有用戶 2.獲取擴展性能上的每個用戶 3.檢查他們是否有所需的擴展屬性,如果它包含了我想要的客戶。 4.構建我想要的用戶列表。

AdClient的IActiveDirectoryClient

var users = (await GetAllElementsInPagedCollection(await AdClient.Users.ExecuteAsync())).ToList(); 
var customersUsers = users.Where(user => user.AccountEnabled.HasValue && user.AccountEnabled.Value).Where(user => 
    { 
     var extendedProperty = ((User) user).GetExtendedProperties().FirstOrDefault(extProp => extProp.Key == customersExtendedProperty.Name).Value?.ToString(); 
     return extendedProperty != null && extendedProperty.Contains(customerId); 
    }).ToList(); 

我希望能夠使用的AdClient在一個查詢中這樣做是爲了ActiveDirectory中。如果我嘗試這樣做,我得到的錯誤,方法不支持,這是有道理的,因爲我假設查詢是在幕後構建查詢Active Directory。

編輯 - 額外的信息:

我能夠查詢圖API是這樣的:

var authContext = await ActiveDirectoryClientFactory.GetAuthenticationContext(AuthConfiguration.Tenant, 
AuthConfiguration.GraphUrl, AuthConfiguration.ClientId, AuthConfiguration.ClientSecret); 
var url = $"https://graph.windows.net:443/hansaborgb2c.onmicrosoft.com/users?api-version=1.6&$filter={customersExtendedProperty.Name} eq '{customerId}'"; 
var users = await _graphApiHttpService.GetAll<User>(url, authContext.AccessToken); 

然而,在我的例子中,我需要使用substringof過濾,但這不支持通過Azure圖形API。

+0

,是它具有的格式爲「extension_guid_someName」名稱的extenion財產?如何擴展屬性放在用戶帳戶上呢?那是通過Graph API嗎? (即用戶是由AD B2C創建的,然後使用圖形API來更新它?) –

+0

是的,擴展字段I是指具有該格式的擴展屬性。它們是使用圖形API創建的,或者更準確地說,我使用的是ActiveDirectoryClient類,我假設這是在後臺使用Graph API – ruffen

+0

是的,ActiveDirectoryClient包裝圖形API。您可以通過ActiveDirectoryClient.Context.ExecuteAsync 訪問原始界面,以執行來自@ nboettcher答案的查詢。但是,有一個問題:$ filter不支持'contains'操作,只有'startswith'和'any'用於多值屬性(並且你不能創建多值擴展屬性):(可能將來會有希望(但不是在Azure AD Graph API中 - 微軟宣佈移動到Microsoft Graph API) – Aloraman

回答

4

我沒有使用該庫,但我們正在使用Graph API進行非常類似的搜索。我已經構建了一個過濾器,用於查找匹配兩個我正在尋找的擴展屬性值的用戶。該過濾器如下所示:

var filter = $"$filter={idpExtensionAttribute} eq '{userType.ToString()}' and {emailExtensionAttribute} eq '{emailAddress}'"; 

我們還通過PowerShell使用REST調用Graph API來返回所需的用戶。具有關聯過濾器的URI如下所示:

https://graph.windows.net/$AzureADDomain/users?`$filter=extension_d2fbadd878984184ad5eab619d33d016_idp eq '$idp' and extension_d2fbadd878984184ad5eab619d33d016_email eq '$email'&api-version=1.6 

這兩個選項都會返回任何符合過濾條件的用戶。

+0

終於有時間來測試這個了,我設法查詢擴展屬性,但是我發現你不能搜索屬性的一部分字符串(子串),你有這個想法嗎? – ruffen

3

當你說「擴展」字段,我會用正常的DirectorySearcher類,從的System.DirectoryServices

private void Search() 
{ 
    // GetDefaultDomain as start point is optional, you can also pass a specific 
    // root object like new DirectoryEntry ("LDAP://OU=myOrganisation,DC=myCompany,DC=com"); 
    // not sure if GetDefaultDomain() works in B2C though :(
    var results = FindUser("extPropName", "ValueYouAreLookingFor", GetDefaultDomain()); 

    foreach (SearchResult sr in results) 
    { 
     // query the other properties you want for example Accountname 
     Console.WriteLine(sr.Properties["sAMAccountName"][0].ToString()); 
    } 
    Console.ReadKey(); 
} 

private DirectoryEntry GetDefaultDomain() 
{ // Find the default domain 
    using (var dom = new DirectoryEntry("LDAP://rootDSE")) 
    { 
     return new DirectoryEntry("LDAP://" + dom.Properties["defaultNamingContext"][0].ToString()); 
    } 
} 

private SearchResultCollection FindUser(string extPropName, string searchValue, DirectoryEntry startNode) 
{ 
    using (DirectorySearcher dsSearcher = new DirectorySearcher(startNode)) 
    { 
     dsSearcher.Filter = $"(&(objectClass=user)({extPropName}={searchValue}))"; 
     return dsSearcher.FindAll(); 
    } 
} 
相關問題