FedCM 更新:IdP Sign-In Status API、Login Hint 等

Chrome 116 也會提供 FedCM 功能 (例如 Login Hint API、User Info API 和 RP Context API),並開始為 IdP Sign-In Status API 進行來源試用。

在 Chrome 116 版中,Chrome 推出了下列三項全新聯合憑證管理 (FedCM) 功能:

  • Login Hint API:指定要登入的偏好使用者帳戶。
  • User Info API:擷取回訪使用者的資訊,讓識別資訊提供者 (IdP) 在 iframe 中顯示個人化登入按鈕。
  • RP Context API:使用與 FedCM 對話方塊中的「登入」不同的標題。

此外,Chrome 正在啟動 IdP Sign-In Status API來源試用。IdP Sign-in Status API 為必要項目,一旦出貨,就會發生破壞性變更。如果您已實作 FedCM,請務必參與來源試用計畫。

登入提示 API

叫用 FedCM 時,瀏覽器會顯示來自指定識別資訊提供者 (IdP) 的登入帳戶。當 IdP 支援多個帳戶時,就會列出所有登入的帳戶。

顯示多個使用者帳戶的 FedCM 對話方塊。
FedCM 對話方塊顯示多個使用者帳戶

使用者登入後,依賴方 (RP) 有時會要求使用者重新驗證。但使用者可能不知道自己登入的是哪個帳戶。 如果 RP 能夠指定登入的帳戶,使用者會比較容易挑選帳戶。登入提示在 Chrome 116 中是運送,在這種情況下,RP 可將清單範圍縮小為一。

這項擴充功能會在 IdP 的帳戶清單端點回應中新增 login_hints 陣列,以及 IdP 支援的所有可能篩選器類型。舉例來說,如果 IdP 支援依電子郵件和 ID 篩選資料,帳戶回應看起來可能會像這樣:

{
  "accounts": [{
    "id": "demo1",
    "email": "demo1@example.com",
    "name": "John Doe",
    "login_hints": ["demo1", "demo1@example.com"],
    ...
  }, {
    "id": "demo2",
    "email": "demo2@example.com",
    "name": "Jane Doe",
    "login_hints": ["demo2", "demo2@example.com"],
    ...
  }, ...]
}

透過在帳戶清單中傳遞 login_hints,RP 可以使用 loginHint 屬性叫用 navigator.credentials.get(),如下列程式碼範例所示,選擇性顯示指定帳戶:

return await navigator.credentials.get({
  identity: {
    providers: [{
      configURL: "https://idp.example/manifest.json",
      clientId: "123",
      nonce: nonce,
      loginHint : "demo1@example.com"
    }]
  }
});

使用者資訊 API

以 IdP 標誌裝飾的登入按鈕,現在可讓使用者透過身分聯盟登入。不過,透過使用者的個人資料圖示裝飾按鈕,加上使用者資訊會更好地登入,特別是在使用者之前透過 IdP 註冊這個網站時。

「使用 Google 帳戶登入」按鈕。
「使用 Google 帳戶登入」按鈕
個人化的「使用 Google 帳戶登入」按鈕,
個人化的「使用 Google 帳戶登入」按鈕

其中的挑戰在於,個人化按鈕仰賴 iframe 中 IdP 網域上的第三方 Cookie,來識別登入使用者來顯示按鈕,但第三方 Cookie 淘汰後就無法使用。

在 Chrome 116 中推出的 User Info API 可讓 IdP 從伺服器取得回訪者的資訊,而不必依賴第三方 Cookie。

IdP 預期需要從 RP 網站內嵌的 iframe 中呼叫 API,以便擷取使用者資訊並呈現個人化按鈕,就像是 RP 介面的一部分。透過 API 呼叫,瀏覽器會向帳戶清單端點發出要求,然後在下列情況傳回使用者資訊陣列:

  • 使用者過去在同一個瀏覽器執行個體上透過 FedCM 登入 RP,且資料並未清除。
  • 使用者在同一個瀏覽器執行個體上登入 IdP。
// Iframe displaying a page from the https://idp.example origin
const user_info = await IdentityProvider.getUserInfo({
    configUrl: "https://idp.example/fedcm.json",
    clientId: "client1234"
});

// IdentityProvider.getUserInfo returns an array of user information.
if (user_info.length > 0) {
  // Chrome puts returning accounts first, so the first account received is guaranteed to be a returning account.
  const name = user_info[0].name;
  const given_name = user_info[0].given_name;
  const display_name = given_name ? given_name : name;
  const picture = user_info[0].picture;
  const email = user_info[0].email;
  // Renders the personalized sign-in button with the information above.
}

請注意,如要允許從與 IdP 相同的 iframe 內呼叫 IdentityProvider.getUserInfo(),嵌入的 HTML 必須明確允許其使用 identity-credentials-get 權限政策

<iframe src="https://fedcm-idp-demo.glitch.me" allow="identity-credentials-get"></iframe>

您可以在 https://fedcm-rp-demo.glitch.me/button 中查看實際運作情形。

RP Context API

在 Chrome 116 中推出的 RP Context API 可讓 RP 修改 FedCM 對話方塊 UI 中的字串,使其符合預先定義的驗證環境。請參閱以下螢幕截圖,瞭解不同的選項:

FedCM 對話方塊轉譯完成
顯示「登入 ****」的 FedCM 對話方塊。如果未指定 RP Context,這是預設選項。
FedCM 對話方塊轉譯完成
含有「Sign up to ****」字樣的 FedCM 對話方塊
FedCM 對話方塊轉譯完成
含有「Continue to ****」的 FedCM 對話方塊
FedCM 對話方塊轉譯完成
含有「使用 ****」的 FedCM 對話方塊

使用方法非常簡單;提供 "signin" (預設)、"signup""use""continue" 中的 identity.context 屬性。

const credential = await navigator.credentials.get({
  identity: {
    // "signin" is the default, "signup", "use" and "continue" 
    // can also be used
    context: "signup", 
    providers: [{
      configURL: "https://idp.example/fedcm.json",
      clientId: "1234",
    }],
  }
});

IdP Sign-In Status API 來源試用

Chrome 會在桌面上從 Chrome 116 啟動 IdP Sign-In Status API 來源試用,隨後在 Android Chrome 的版本中運作。來源試用可讓您使用全新或實驗性功能,在向所有使用者開放該功能之前的限定期間試用功能。

IdP Sign-In Status API 是一種機制,IdP 會通知瀏覽器使用者在 IdP 上的登入狀態。透過這個 API,瀏覽器可減少對 IdP 不必要的要求,並降低潛在的時間攻擊。

通知瀏覽器使用者登入狀態

IdP 可以傳送 HTTP 標頭、呼叫 JavaScript API、使用者在 IdP 上登入,或是使用者從所有 IdP 帳戶中登出,藉此向瀏覽器告知使用者登入狀態。瀏覽器會將狀態記錄為「登入」、「登出」或「不明」(預設)。

如要告知使用者已登入,請在頂層導覽或相同來源子資源要求中傳送 IdP-SignIn-Status: action=signin HTTP 標頭:

IdP-SignIn-Status: action=signin

或者,您也可以從 IdP 來源呼叫 JavaScript API IdentityProvider.login()

IdentityProvider.login()

這些事件會將使用者的登入狀態記錄為「登入」。當使用者的登入狀態設為「登入」時,PR 呼叫 FedCM 會向 IdP 的帳戶清單端點發出要求,並在 FedCM 對話方塊中向使用者顯示可用帳戶。

如要告知使用者已登出所有帳戶,請在頂層導覽或相同來源子資源要求中傳送 IdP-SignIn-Status: action=signout-all HTTP 標頭:

IdP-SignIn-Status: action=signout-all

或者,您也可以從 IdP 來源呼叫 JavaScript API IdentityProvider.logout()

IdentityProvider.logout()

進而將使用者的登入狀態記錄為「登出」。如果使用者的登入狀態為「登出」,則呼叫 FedCM 會失敗,而不會向 IdP 的帳戶清單端點發出要求。

根據預設,IdP 登入狀態會設為「不明」。此狀態會在 IdP 使用 IdP Sign-In Status API 傳送信號之前使用。之所以導入這個狀態是為了改善轉換作業,是因為我們發布這個 API 時,使用者可能已經登入了 IdP,而且 IdP 在首次叫用 FedCM 時可能沒有機會向瀏覽器發出信號。在這種情況下,我們會向 IdP 的帳戶清單端點發出要求,並根據帳戶清單端點的回應更新狀態:

  • 如果端點傳回有效帳戶清單,請將狀態更新為「登入」並開啟 FedCM 對話方塊,即可顯示這些帳戶。
  • 如果端點未傳回任何帳戶,請將狀態更新為「登出」,並失敗 FedCM 呼叫。

如果使用者工作階段過期,該怎麼辦?讓使用者透過動態登入流程登入

雖然 IdP 會持續通知瀏覽器使用者的登入狀態,但可能會因為工作階段到期等原因出不同步。登入狀態為「登入」時,瀏覽器會嘗試將憑證認證要求傳送至帳戶清單端點,但伺服器因工作階段已無法使用而拒絕要求。在此情況下,瀏覽器可以動態讓使用者透過彈出式視窗登入 IdP。

FedCM 對話方塊會顯示訊息,如下圖所示:

FedCM 對話方塊,建議登入 IdP。
畫面上顯示 FedCM 對話方塊,建議登入 IdP。

點選「Continue」按鈕後,瀏覽器就會開啟彈出式視窗,將使用者帶到 IdP 的登入頁面。

點選「登入 IdP」按鈕後,畫面上會出現彈出式視窗。
點選「登入 IdP」按鈕後,畫面上會出現彈出式視窗。

登入頁面網址 (必須是 IdP 的來源) 可以使用 signin_url 做為 IdP 設定檔的一部分指定。

{
  "accounts_endpoint": "/auth/accounts",
  "client_metadata_endpoint": "/auth/metadata",
  "id_assertion_endpoint": "/auth/idtokens",
  "signin_url": "/signin"
  }
}

彈出式視窗是使用第一方 Cookie 的一般瀏覽器視窗。 系統會將內容視窗中發生的情況控制在 IdP 上,但沒有任何視窗處理常式可用來向 RP 頁面提出跨來源通訊要求。使用者登入後,IdP 應會執行以下作業:

  • 傳送 IdP-SignIn-Status: action=signin 標頭或呼叫 IdentityProvider.login() API,通知瀏覽器使用者已登入。
  • 呼叫 IdentityProvider.close() 即可自行關閉 (彈出式視窗)。
// User is signed in...
// Don't forget feature detection.
if (IdentityProvider) {
  // Signal to the browser that the user has signed in.
  IdentityProvider.close();
}
使用者使用 FedCM 登入 IdP 後登入 RP

您可以在我們的示範中試用 IdP Sign-In Status API 的行為。登入示範 IdP 後,工作階段會在三分鐘後到期。然後透過彈出式視窗行為觀察 IdP 登入。

參與來源試用

只要開啟 Chrome 116 以上版本中的Chrome
旗標
chrome://flags#fedcm-idp-signin-status-api,即可在本機試用 IdP Sign-In Status API。

您也可以註冊來源試用兩次,藉此啟用 IdP Sign-In Status API:

來源試用可讓您試用新功能,並向網路標準社群的可用性、實用性和成效提供意見回饋。詳情請參閱網頁開發人員的來源試用指南

在 Chrome 116 至 Chrome 119 中,都可以使用 IdP Sign-In Status API 來源試用功能。

為 IdP 註冊來源試用

  1. 前往來源試用註冊頁面
  2. 按一下「Register」按鈕,然後填寫表單來申請權杖。
  3. 輸入 IdP 的來源做為「Web Origin」
  4. 點選「提交」
  5. 在使用 IdentityProvider.close() 的網頁標頭中加入 origin-trial <meta> 標記。例如:
    <meta http-equiv="origin-trial" content="TOKEN_GOES_HERE">

為 RP 註冊第三方來源試用

  1. 前往來源試用註冊頁面
  2. 按一下「Register」按鈕,然後填寫表單來申請權杖。
  3. 輸入 IdP 的來源做為「Web Origin」
  4. 勾選「第三方比對」,即可在其他來源上透過 JavaScript 插入權杖。
  5. 點選「提交」
  6. 將核發的權杖嵌入第三方網站。

如要在第三方網站上嵌入權杖,請將下列程式碼新增至 JavaScript 程式庫或 IdP 來源提供的 SDK。

const tokenElement = document.createElement('meta');
tokenElement.httpEquiv = 'origin-trial';
tokenElement.content = 'TOKEN_GOES_HERE';
document.head.appendChild(tokenElement);

TOKEN_GOES_HERE 改成您自己的權杖。

互動並提供意見

如要提供意見或在測試期間遇到任何問題,請前往 crbug.com

相片來源:Dan Cristian Pădure 氣氛Unsplash 上發布