Webauthn 条件 ui 在 chrome 中不起作用

Webauthn conditional ui not working in chrome

提问人:Trond 提问时间:10/2/2023 最后编辑:Trond 更新时间:10/4/2023 访问量:152

问:

我正在尝试使用 Webauthn 实现身份验证。在使用建议的方法验证平台和浏览器支持后,我将待处理的请求添加到 navigator.credentials:window.PublicKeyCredential.isUserVerifyingPlatformAuthenticatorAvailable()await window.PublicKeyCredential.isConditionalMediationAvailable()

let credentials = await window.navigator.credentials.get({
            signal: abortSignal,
            publicKey: {
                // Don't do this in production!
                challenge: new Uint8Array([1, 2, 3, 4]),
                allowCredentials: []
            },
            mediation: "conditional"
        });

我的表格:

<form>
    <label for="login-username">Username:</label>
    <input name="username" id="login-username" value="" autocomplete="username webauthn" autofocus/>
    <label for="password">Fake password:</label>
    <input id="password" value="" required type="password" autocomplete="password webauthn"/>
    <div class="button-box">
      <button id="login" type="submit">
        <strong>Log-in</strong>
      </button>
    </div>
</form>

我希望在单击用户名或密码输入字段后立即从浏览器看到一个下拉列表/弹出窗口,该字段允许我从其他设备选择密钥,但我在 Chrome(版本 117.0.5938.132)中看不到这一点。

但是,Safari 可以按预期工作。我在这里错过了什么?

更新:所以我使用一个简单的索引.html文件测试了它,其中包含所需的所有代码,它看起来像这样:

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>Conditional UI</title>
    <script>
      window.PublicKeyCredential.isUserVerifyingPlatformAuthenticatorAvailable().then(
              result => {
                if (!result) {
                  console.log("No platform authenticator found. If your OS does not come with one, try using devtools to set one up.");
                }
              }
      );


      let abortController;
      let abortSignal;

      let startConditionalRequest = async () => {
        if (window.PublicKeyCredential.isConditionalMediationAvailable) {
          console.log("Conditional UI is understood by the browser");
          if (!await window.PublicKeyCredential.isConditionalMediationAvailable()) {
            console.log("Conditional UI is understood by your browser but not available");
            return;
          }
        } else {
          if (!navigator.credentials.conditionalMediationSupported) {
            console.log("Your browser does not implement Conditional UI (are you running the right chrome/safari version with the right flags?)");
            return;
          } else {
            console.log("This browser understand the old version of Conditional UI feature detection");
          }
        }
        abortController = new AbortController();
        abortSignal = abortController.signal;

        try {
          let credential = await window.navigator.credentials.get({
            signal: abortSignal,
            publicKey: {
              // Don't do this in production!
              challenge: new Uint8Array([1, 2, 3, 4]),
              allowCredentials: []
            },
            mediation: "conditional"
          });
          if (credential) {
            let username = String.fromCodePoint(...new Uint8Array(credential.response.userHandle));
            console.log(username);
          } else {
            console.log("Credential returned null");
          }
        } catch (error) {
          if (error.name == "AbortError") {
            console.log("request aborted");
            return;
          }
          console.log(error.toString());
        }
      }

      startConditionalRequest();
    </script>
  </head>
  <body>
  <form>
    <label for="login-username">Username:</label>
    <input name="username" id="login-username" value="" autocomplete="username webauthn" autofocus/>
    <label for="password">Fake password:</label>
    <input id="password" value="" required type="password" autocomplete="password webauthn"/>
    <div class="button-box">
      <button id="login" type="submit">
        <strong>Log-in</strong>
      </button>
    </div>
  </form>
  </body>
</html>

现在,当我在任何浏览器中打开它时,它都可以完美运行。但是,如果我尝试使用 vite dev-server 进行相同的托管,或者如果我构建一个 react-app,它可以在 Safari 中工作,但不能在 chrome 中工作。这和影子统治什么的有什么关系吗?

有没有人在 chrome 中为 react-app 工作?很想听听你是怎么做到的。

Google-Chrome Safari WebAuthn 密钥

评论


答:

0赞 agl 10/4/2023 #1

这和影子统治什么的有什么关系吗?

据我所知,Chrome 密码自动填充目前在影子 DOM 中不起作用:https://bugs.chromium.org/p/chromium/issues/detail?id=1404106

评论

0赞 Trond 10/5/2023
看起来是这样。希望他们能尽快解决这个问题,这对现代应用程序来说是一个完全的障碍。 谢谢。