AppAuth Android 第二次尝试时不关闭浏览器重定向响应(为什么它不是幂等操作)

AppAuth Android not closing browser redirect response on second try (why it is not idempotent action)

我正在使用 Android 的 AppAuth 库连接到 OIDC 服务器,该服务器不在 Okta、Google 等知名供应商列表中

该供应商不支持自定义 url 模式。它只支持 https 重定向。

我根据 AppAuth-Android github 存储库中的文档和示例应用配置了我的应用。

我已经从我的 Android清单文件中的库中添加了 AppLink activity:

<activity android:name="net.openid.appauth.RedirectUriReceiverActivity">
   <intent-filter>
       <action android:name="android.intent.action.VIEW"/>
       <category android:name="android.intent.category.DEFAULT"/>
       <category android:name="android.intent.category.BROWSABLE"/>
       <data android:scheme="https"
             android:host="example.com"
             android:path="/redirect.html"/>
   </intent-filter>
</activity>

我没有将以下代码放入我的 build.gradle 文件中,因为我没有使用自定义 url 模式:

manifestPlaceholders = [
                'appAuthRedirectScheme': 'net.openid.appauthdemo'
        ]

下面是我的auth_config.json文件,所以你可以看到我的配置。我修改了真实值以不泄漏私人数据。

{
  "client_id": "MY_CLIENT_ID",
  "redirect_uri": "https://example.com/redirect.html",
  "end_session_uri":"https://example.com/redirect.html",
  "authorization_scope": "openid email profile",
  "discovery_uri": "https://my-idp.com/.well-known/openid-configuration",
  "authorization_endpoint_uri": "",
  "token_endpoint_uri": "",
  "registration_endpoint_uri": "",
  "user_info_endpoint_uri": "",
  "https_required": true
}

我的问题是:为什么浏览器标签关闭不是幂等的?我将在下面解释我所说的幂等。

当我启动应用程序并单击“登录”时,它会打开“自定义”选项卡并将我重定向到 IDP。我成功登录服务器,IDP 将我发送回(重定向)到 https://example.com/redirect.html?code=XXXXXXX&state=XXXXXX。该应用程序捕获响应并交换令牌代码,到目前为止一切正常。

当我再次尝试登录时,浏览器已经有了有效会话的 cookie,并将我直接重定向到 https://example.com/redirect.html?code=XXXXXXX&state=XXXXXX。这次浏览器卡住了,应用程序没有捕捉到回调。在正常的 OIDC 流程中,此操作是幂等的。应用程序应该像第一次一样捕获响应并提取要交换新令牌的代码。我不确定这是 android 本身没有按预期捕获 URL 的问题,还是 AppAuth 库中发生了抛出异常但未关闭浏览器的问题。第一次和第二次重定向的重定向 URL 完全相同(除了代码查询参数值不同)。

提前致谢

这是一个特定于浏览器的问题 - 由于在第二次登录尝试时 Chrome 自定义选项卡中缺少用户手势 - 并且可能是间歇性的。

使用声明的 HTTPS 方案有细微差别,iOS 上也存在同样的问题。解决方案是使用插页式网页,以便在每次重定向时都有用户手势,这样应用程序的 return 是确定性的。

我的资源

您应该能够在您的 PC 上克隆以下存储库和 运行 示例,以便进行比较。博文更深入地描述了这些问题。