在 Salesforce OAuth 流程中使用 immediate=true

Using immediate=true in Salesforce OAuth flow

之前在 Salesforce StackExchange 中问过这个问题,他们认为这是题外话,所以在这里问我是否能得到答案。


背景

我正在尝试使用 immediate 参数来检查 Salesforce 用户在通过 OAuth 2.0 Web Server Authentication Flow 中记录的 Web 服务器 OAuth 流程时是否已批准访问。我这样做的原因是我不希望出现登录或同意提示,因此如果他们尚未批准我可以拒绝访问。

一旦点击回调页面,我总是收到参数error=immediate_unsuccessful,即使用户之前已经批准申请并登录

我试图通过自定义 Google OAuth 2 Playground 并在授权端点的末尾设置 immediate=true 或 immediate=false 来检查这一点。在 =false 时,会显示同意提示,然后您可以授予访问权限。在 =true 上,此 returns 与前面列出的错误相同。

已设置的连接应用程序有api和refresh_token作为可用范围,用户可以自行授权并且没有设置ip限制。然后将此应用程序的客户端 ID 和机密传递到 OAuth 2 Playground。

下面是一个简短示例,说明我的正确应用程序如何使用 Java 和 Google OAuth 客户端库重定向到身份验证 url。我们最初在没有立即授权的情况下授权客户端,然后稍后使用 immediate=true 调用相同的代码(如示例所示)

AuthorizationCodeFlow authorizationCodeFlow = new AuthorizationCodeFlow.Builder(BearerToken.authorizationHeaderAccessMethod(), 
            httpTransport, 
            GsonFactory.getDefaultInstance(), 
            new GenericUrl("https://login.salesforce.com/services/oauth2/token"),
            new ClientParametersAuthentication(CLIENT_ID, CLIENT_SECRET), 
            CLIENT_ID,
            "https://login.salesforce.com/services/oauth2/authorize")
            .setCredentialDataStore(StoredCredential.getDefaultDataStore(MemoryDataStoreFactory.getDefaultInstance()))
            .build();

    AuthorizationCodeRequestUrl authUrl = authorizationCodeFlow.newAuthorizationUrl()
        .setRedirectUri("https://72hrn138.ngrok.io/oauth/callback")
        .setScopes(ImmutableSet.<String> of("api", "refresh_token"))
        .set("prompt", "consent")
        .set("immediate", "true");

    response.redirect(authUrl);

问题

最后我设法解决了这个问题。要允许 immediate=true 选项起作用,必须从请求中删除范围。在提供的示例中,您可以将 authUrl 修改为以下内容:

AuthorizationCodeRequestUrl authUrl = authorizationCodeFlow.newAuthorizationUrl()
    .setRedirectUri("https://72hrn138.ngrok.io/oauth/callback")
    .set("prompt", "consent")
    .set("immediate", "true");

我相信理论上定义范围意味着您正在请求使用这些范围的权限,因此需要批准这些权限。这与立即选项冲突,立即选项声明用户必须登录并且客户端 ID 已被批准才能成功。