簡體   English   中英

如何最好地從 Active Directory 中檢索用戶數據以及 SQL Server 數據

[英]How best to retrieve user data from Active Directory in conjunction with SQL Server data

我有一個 Web 應用程序,它將它的數據存儲在 Azure SQL 數據庫中,並將有關經過身份驗證的用戶的數據存儲在 Azure Active Directory B2C 中。 SQL 數據庫中的數據通過 AD 用戶的“oid” (GUID) 與 AD 用戶相關聯。 這意味着獲取數據庫不允許任何人識別特定用戶。

但是,當我查詢 SQL 數據以向訪問者創建表格或圖表時,我顯然希望顯示與擁有數據的用戶相關的數據(即顯示用戶的全名,而不是他們的 oid!)。

我知道在網頁上呈現 SQL 查詢的結果時,我可以使用Azure Graph API來獲取用戶數據,但這似乎是一種非常低效的方法。 除此之外,我不確定如何傳入一批 oid 以在不使用長得可笑的查詢字符串過濾器的情況下取回所有用戶對象!

我可以創建某種同步過程來查詢整個 AD)並在定時過程(可能是 Azure 函數)上更新 SQL 表,但這似乎也非常低效?

我查看了 Microsoft Graph API webhooks,但目前似乎沒有任何訂閱我可以掛鈎用戶對象更改,他們不推薦 Graph with B2C。

我想另一個選擇是在某處有一個緩存來存儲數據以加快查找速度,但這必須更新到。

任何建議,不勝感激。

實際上非常簡單(假設您已經通過身份驗證)。 將其用作 GET 請求的模板:

{baseUrl}/{tenantId}/users/{oid}?api-version={api-version}

不要忘記將您的不記名令牌添加到 Authorization 標頭中:

Authorization: Bearer {accessToken}

此外,這里是您可能用於響應的對象示例(在 Java 中),其中包含一些用於檢索注冊電子郵件的有用方法(假設您使用的是內置 B2C 用戶而不是第三方,例如谷歌):

import com.fasterxml.jackson.annotation.JsonIgnore;
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
import com.fasterxml.jackson.annotation.JsonProperty;

import java.util.ArrayList;
import java.util.List;

@JsonIgnoreProperties(ignoreUnknown = true)
public class GraphApiUserExample{

    @JsonProperty("objectId")
    private String id;

    private Boolean accountEnabled;

    private com.brmic.azure.graph.api.client.model.PasswordProfile PasswordProfile;

    private List<SignInName> signInNames;

    private String surname;

    private String displayName;

    private String givenName;

    @JsonProperty("userPrincipalName")
    private String userPrincipalName;

    public String getId(){

        return id;
    }

    public void setId(final String id){

        this.id = id;
    }

    public Boolean getAccountEnabled(){

        return accountEnabled;
    }

    public void setAccountEnabled(final Boolean accountEnabled){

        this.accountEnabled = accountEnabled;
    }

    public com.brmic.azure.graph.api.client.model.PasswordProfile getPasswordProfile(){

        return PasswordProfile;
    }

    public void setPasswordProfile(final com.brmic.azure.graph.api.client.model.PasswordProfile passwordProfile){

        PasswordProfile = passwordProfile;
    }

    public List<SignInName> getSignInNames(){

        return signInNames;
    }

    public void setSignInNames(final List<SignInName> signInNames){

        this.signInNames = signInNames;
    }

    public String getSurname(){

        return surname;
    }

    public void setSurname(final String surname){

        this.surname = surname;
    }

    public String getDisplayName(){

        return displayName;
    }

    public void setDisplayName(final String displayName){

        this.displayName = displayName;
    }

    public String getGivenName(){

        return givenName;
    }

    public void setGivenName(final String givenName){

        this.givenName = givenName;
    }

    public String getUserPrincipalName(){

        return userPrincipalName;
    }

    public void setUserPrincipalName(final String userPrincipalName){

        this.userPrincipalName = userPrincipalName;
    }

    @JsonIgnore
    public String getSignInEmail(){

        String email = "";
        if(signInNames != null){
            for(SignInName signInName : signInNames){
                if(signInName.getType().equals("emailAddress")){
                    email = signInName.getValue();
                    break;
                }
            }
        }
        return email;
    }

    @JsonIgnore
    public void setSignInEmail(String signInEmail){

        if(signInNames == null){
            signInNames = new ArrayList<>();
            signInNames.add(new SignInName("emailAddress", signInEmail));
            return;
        }

        for(SignInName signInName : signInNames){
            if(signInName.getType().equals("emailAddress")){
                signInName.setValue(signInEmail);
                break;
            }
        }
    }
}

如果您想拉取多個用戶,您可以添加一個查詢而不是 'oid' 來過濾和分頁結果。

{baseUrl}/{tenantId}/users?api-version={api-version}&$skiptoken={skiptoken}&$top={top}&$filter={attributeOne} eq '{valueOne}'
{baseUrl}/{tenantId}/users?api-version={api-version}&$skiptoken={skiptoken}&$top={top}$filter=signInNames/any(x:x/value eq '{email}')

它返回一個像這樣的 JSON 對象:

{
    "users":[...],
    "odata":{
        "nextLink": "{baseUrl}/{tenantId}/users?api-version={api-version}&$skiptoken={skiptoken}&$top={top}&$filter={attributeOne} eq '{valueOne}'"
        "metadata": "I forget if this is just a string or a parsable JSON object."
    }

}

您仍然會遇到將查詢結果與數據庫結果進行匹配的問題,這將是一項繁重的操作。 如果您需要運行更快的操作,我建議您使用緩存表中的結果進行連接。 它確實感覺很笨拙,但只是因為它是。

您還可以使用 B2C azure powershell 模塊中的一些 powershell 命令,並且您可以使用 ADAL 在 SQL Server 中創建作業以更新表或視圖的內容。

文檔在這里: https : //docs.microsoft.com/en-us/azure/active-directory-b2c/active-directory-b2c-devquickstarts-graph-dotnet

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM