安全防護組合

本指南說明一系列功能,可傳回 Google 帳戶的其他信任訊號。帳戶管理系統可以運用這些信任信號,在註冊、建立帳戶、使用者日後回訪時,依據風險制定決策。

設定

如要接收額外聲明,應用程式必須已發布、通過驗證,並啟用安全組合功能。

如要確認應用程式已發布並通過驗證,請按照下列步驟操作:

  1. 開啟 Google Auth Platform
  2. 選取或建立應用程式專案
  3. 按一下選單中的「目標對象」
  4. 確認「發布狀態」為「已發布至正式環境」
  5. 按一下選單中的「驗證中心」
  6. 確認「驗證狀態」為「已驗證」

    詳情請參閱 OAuth 應用程式驗證說明中心

如要啟用 auth_time 聲明,請按照下列步驟操作:

  1. 開啟 Google Auth Platform
  2. 選取或建立應用程式專案
  3. 按一下選單中的「設定」
  4. 在「進階設定」下方,選取「工作階段年齡聲明」,即可啟用 auth_time

支援的功能

本節說明 Security Bundle 的各項功能。

auth_time

auth_time 聲明是 OpenID Connect 通訊協定的標準部分,可提供使用者最近一次向 Google 驗證身分的時間資訊。這是 JSON 數字,代表自 Unix 紀元 (1970 年 1 月 1 日世界標準時間 00:00:00) 經過的秒數,也是使用者上次驗證的時間。這項資訊可視為時間戳記,指出使用者上次透過目前裝置或瀏覽器登入 Google 帳戶的時間。這項聲明會納入 ID 權杖,也就是包含驗證和使用者相關驗證資訊的 JSON Web Token (JWT)。

auth_time 聲明對應用程式很有價值,因為您可以藉此判斷使用者最近在使用的裝置或瀏覽器上,主動登入 Google 帳戶的時間。這對安全防護而言尤其重要,例如:

  • 在執行敏感的使用者動作 (例如刪除帳戶、變更帳戶聯絡方式或付款) 之前,請根據情況決定應用程式是否應發出額外的升級驗證問題。Google 不支援 Google 帳戶重新驗證要求。

  • 以使用者 Google 帳戶工作階段的即時性和穩定性做為信任信號。一般來說,auth_time 值越新表示資料越即時,值越舊則表示資料越穩定。

如果是網頁應用程式,使用者登入 Google 帳戶後,瀏覽器和作業系統的組合即為工作階段。此外,您的網站也會維護獨立的使用者工作階段。較新的 auth_time 值表示使用者最近登入 Google 帳戶。這通常表示使用者活躍且參與度高,可解讀為風險較低的信號。

在 Android 等行動平台,使用者通常會直接登入裝置,方法是使用指紋或臉部掃描等生物特徵辨識方式,以及裝置專屬的 PIN 碼或解鎖圖案。行動應用程式和平台通常會使用這些平台式驗證方法,而不是透過 Google 建立新工作階段,因此 Google 帳戶登入次數較少,auth_time 的更新頻率也較低。因此,最近的 auth_time 值可能表示長期執行的 Google 帳戶工作階段發生變化,因此風險增加。

信任信號是個複雜的主題。auth_time 預計會與其他信號一併使用,例如是否已啟用多重驗證 (MFA)、使用的驗證方法,以及應用程式與平台之間的使用者工作階段持續時間。

auth_time 要求

要求 auth_time 聲明的具體方法因所用 API 而異,但每個 API 都包含選用的 claims 參數,可要求 auth_time

OIDC 通訊協定

直接使用 OAuth 平台時,請將 auth_time 新增至選用聲明要求參數,藉此要求 auth_time。將聲明 JSON 物件的 id_token 欄位值設為 {"auth_time":{"essential":true}}。例如:

https://accounts.google.com/o/oauth2/v2/auth?
response_type=id_token&
client_id=YOUR_CLIENT_ID&
scope=openid email profile&
redirect_uri=https://example.com/user-login&
nonce=123-456-7890&
claims={"id_token":{"auth_time":{"essential":true}}}

詳情請參閱「OpenID Connect」。

網頁版 GIS

網頁版「使用 Google 帳戶登入」程式庫有兩個 API:HTML 和 JavaScript,可要求額外聲明。舉例來說,使用 JavaScript API 要求 auth_time

<html>
<body>
  <script src="https://accounts.google.com/gsi/client" async></script>
  <script>
    window.onload = function () {
      google.accounts.id.initialize({
        client_id: "YOUR_WEB_CLIENT_ID",
        callback: function(rsp) { console.log(rsp.credential); },
        essential_claims: "auth_time",
      });
      google.accounts.id.renderButton(
        document.getElementById("buttonDiv"),
        { type: "standard", size: "large" }
      );
    }
  </script>
  <div id="buttonDiv"></div>
</body>
</html>

詳情請參閱「透過 Google 登入網頁」。

Android 版 GIS

setClaims 方法和 Claim 物件用於要求 auth_time

更新建構依附元件,使用最新版本的 androidx.credentials:credentials-play-services-authcom.google.android.libraries.identity.googleid:googleid 程式庫。

使用 setClaims 建立 auth_time 類型的 Claim 物件,將其新增至登入選項:

val googleIdOption: GetGoogleIdOption = GetGoogleIdOption.Builder()
    .setAutoSelectEnabled(true)
    .setFilterByAuthorizedAccounts(true)
    .setServerClientId(WEB_CLIENT_ID)
    .setNonce("NONCE")
    .setClaims(ImmutableList.of(new Claim("auth_time", true)))
    .build()

詳情請參閱「使用 Google 登入功能驗證使用者」。

iOS

iOS 版 Google 登入 SDK 會將 authTimeClaim 物件和 claims 參數新增至 GIDSignIn 類別,用於選擇性要求 auth_time

應用程式會使用 ASWebAuthenticationSession 更新裝置範圍內的共用 Cookie JAR。在 iOS 12 以上版本和 macOS 12.16 以上版本中,GIDSignIn 預設會使用這個方法。在這個情境中,使用者登入 Google 帳戶時會經過驗證,工作階段也會儲存在共用 Cookie 罐中。這是使用者在裝置上進行的最後一次 Google 驗證,auth_time不只是在您的應用程式中。

SFSafariViewControllerWKWebViewUIWebView 會在應用程式內的獨立沙箱中運作,因此使用 auth_time 時請避免使用這些函式庫。這裡的 auth_time 是指使用者上次登入應用程式的時間,由於這個值一律是最近的時間,因此意義不大。

如要要求 auth_time,請將 GoogleSignIn 依附元件更新至最新版本,並建立 authTimeClaim 物件,然後新增至 claims 集合。

Swift

將聲明集新增至 GIDSignIn.sharedInstance.signIn 方法:

let authTimeClaim = GIDClaim.authTime()
let claims = Set([authTimeClaim])

// Start the sign-in process GIDSignIn.sharedInstance.signIn( withPresenting: rootViewController, claims: claims ) { signInResult, error in guard let result = signInResult else { print("Error signing in: (error?.localizedDescription ?? "No error description")") return } // If sign in succeeded, display the app's main content View print("ID Token: (result.user.idToken?.tokenString ?? "No token")") }

Objective-C

將聲明集新增至 signInWithPresentingViewController 方法:

GIDClaim *authTimeClaim = [GIDClaim authTimeClaim];
NSSet *claims = [NSSet setWithObject:authTimeClaim];

// Include the claims set and start the sign-in process [GIDSignIn.sharedInstance signInWithPresentingViewController:self hint:nil claims:claims completion:^(GIDSignInResult * _Nullable signInResult, NSError * _Nullable error) { // On success signInResult.user.idToken // contains the requested claims. }];

詳情請參閱「將 Google 登入整合至 iOS 或 macOS 應用程式」。

auth_time 回應

要求中包含 auth_time 聲明時,該聲明會與其他標準聲明 (例如 iss (簽發者)、sub (主體)、aud (目標對象) 和 exp (到期時間)) 一併顯示在 ID 權杖酬載回應中。auth_time 聲明的值是 JSON 數字,代表自 Unix 紀元 (1970 年 1 月 1 日世界標準時間 00:00:00) 起,到使用者上次驗證身分時所經過的秒數。以下是已解碼的 ID 權杖範例,其中包含 auth_time 聲明:

{
  "iss": "https://accounts.google.com",
  "azp": "YOUR_CLIENT_ID",
  "aud": "YOUR_CLIENT_ID",
  "sub": "117726431651943698600",
  "email": "alice@example.com",
  "email_verified": true,
  "nonce": "123-456-7890",
  "auth_time": 1748875426,
  "nbf": 1748880889,
  "name": "Elisa Beckett",
  "picture": "https://lh3.googleusercontent.com/a/default-user=s96-c",
  "given_name": "Elisa",
  "family_name": "Beckett",
  "iat": 1748881189,
  "exp": 1748884789,
  "jti": "8b5d7ce345787d5dbf14ce6e08a8f88ee8c9b5b1"
}

ID 權杖也包含 iat (核發時間) 憑證附加資訊,指出 JWT 的核發時間。比較 iatauth_time 聲明,即可判斷使用者上次驗證後經過的時間,相對於特定 ID 權杖的建立時間。舉例來說,如果 iat 為 1748881189,而 auth_time 為 1748875426,兩者相差 5763 秒,代表經過 1 小時 36 分 3 秒。