1

我在尝试使用 Azure 的活动目录 b2c 快速对用户进行身份验证时遇到问题。看来我可以在 webview 中成功登录AD 能够找到我的用户并在密码错误时返回错误,但在我“登录”后我被重定向到我的应用程序并出现以下错误:

无法获取令牌:错误域=MSALErrorDomainCode=-41205"null" Userinfo={MSALErrorDescriptionKey=令牌响应缺少访问令牌}

let kSignupOrSigninPolicy = "b2c_1_signupandsignin" // Your signup and sign-in policy you created in the portal
let kScopes: [String] = [""]
let kEndpoint = "https://login.microsoftonline.com/tfp/%@/%@"
let kTenantName = "sampleapp.onmicrosoft.com" // Your tenant name




@IBAction func authorizationButton(_ sender: UIButton) {


    let kAuthority = String(format: kEndpoint, kTenantName, kSignupOrSigninPolicy)


    do {
        let application = try MSALPublicClientApplication.init(clientId: kClientID, authority: kAuthority)
        application.acquireToken(forScopes: kScopes) { (result, error) in
                if  error == nil {
                    self.accessToken = (result?.accessToken)!
                    self.loggingText.text = "Access token is \(self.accessToken)"
                    self.signoutButton.isEnabled = true;
                    self.callGraphApiButton.isEnabled = true;
                    self.editProfileButton.isEnabled = true;
                    self.refreshTokenButton.isEnabled = true;


                } else {
                    self.loggingText.text = "Could not acquire token: \(error ?? "No error informarion" as! Error)"
                }
        }
    } catch {
        self.loggingText.text = "Unable to create application \(error)"
    }
}

我怀疑我如何在前端列出范围的后端范围配置有问题。据我所知,我们在后端没有自定义范围配置。我为 kScopes 变量尝试了一些不同的字符串:

"openid"
""
"https://graph.windows.net/openid"
"https://graph.windows.com/openid"
"https://graph.microsoft.com/openid"
4

1 回答 1

3

有帮助的地方之一是我们的公共MSALError 类。它通常有助于调试此类问题。

B2C 目前不支持 Microsoft Graph

您遇到的问题是您正在请求对 Microsoft 的 Graph API 的访问和范围。尚不支持通过 B2C 租户访问 Microsoft 的 Graph API。

B2C 旨在为您提供一个访问令牌,您可以将其用于您自己的后端 Web API,以及您希望传递给该服务以限制对该服务的访问的范围。如果没有后端服务可以访问,您将不会获得 access_token。

示例中的文档中对此进行了引用:

let kGraphURI = "<Your backend API>" // This is your backend API that you've configured to accept your app's tokens let kScopes: [String] = ["<Your backend API>/demo.read"] // This is a scope that you've configured your backend API to look for.

如果您考虑一下,这是有道理的 - B2C 是企业对消费者。我们的用例是您希望使用您拥有并为您的消费者控制的身份系统。在这种情况下,您很可能会向客户提供您希望限制访问的实际服务(这是身份系统的重点)。即使他们使用 Google 或 Facebook(我们的产品支持)登录也是如此,因为您需要告诉后端服务用户身份,以便为他们创建帐户或让他们访问您的服务。

您得到的确切错误是您正在请求访问 Microsoft Graph API,这是不可能的,因此无法获得同意。B2C 服务知道这一点并返回没有 access_token 的响应。我们的 MSAL 库正在向您报告这种情况,并且授权失败。

但我确实想将 Microsoft Graph API 与我自己的身份系统一起使用!

这是一个有趣的用例,随着 Microsoft Graph 的发展,我们越来越多地将其视为一个问题。我们正在努力增强 B2C 以在未来支持这一点。请务必查看 GitHub 主页和发行说明,以了解何时添加。

如果您希望仅允许用户使用 Microsoft Graph API,则应利用通用 MSAL SDK 并通过https://apps.dev.microsoft.com载入应用程序。

但我只想让某人登录,根本不访问任何 API!

您可能就是这种情况,因为您尝试访问 Microsoft Graph 但似乎没有对其进行任何操作。

签到某人有两个部分:

OpenID Connect(身份验证) - 身份系统告诉您,是的,该用户存在于我们的系统中,仅此而已。这通常通过给你一个 id_token 来表示。没有任何访问权限。如果您只想在登录您自己的身份系统之前检查用户是否合法,这可能会很有用。

OAuth2(授权) - 您要求身份系统授予您对其控制的资源的访问权限。通过向您提供访问令牌,您可以将此访问权移交给资源。您确实需要向身份系统提供身份以查看用户是否应该有权访问资源,但这不一定是使用 OpenID Connect,它甚至可能不是人类!(例如使用 API 密钥/客户端机密的服务到服务连接,这些只是文本字符串)

大多数开发人员都使用 OpenID Connect 和 OAuth2,因为他们希望让某人登录然后访问资源。例如,Microsoft Graph API 的正常流程就是这样工作的。您希望用户登录(使用 Microsoft 帐户),然后访问 Graph API(使用该 Microsoft 帐户)。

正如我所说,有时您只是希望身份系统说用户存在,仅此而已。

我们有一个流程来做到这一点,这在此处进行了讨论。简而言之,您需要将您的范围更改为,&scope=openid%20offline_access但您绝对应该阅读该文档并确保您完全理解该场景。

于 2017-08-08T22:35:04.157 回答