本頁說明如何設定多重驗證 (MFA),透過電子郵件傳送驗證碼來驗證使用者身分。這項功能可讓您驗證使用者是否擁有與帳戶相關聯的電子郵件地址。多重驗證可協助保護使用者,防範憑證填充攻擊和帳戶入侵 (ATO)。
MFA 適用於以分數為準的金鑰,不適用於核取方塊金鑰。
瞭解多重驗證的設定程序
reCAPTCHA 的 MFA 功能是在一般 reCAPTCHA 工作流程的基礎上實作。
大致來說,多重驗證工作流程如下:
- 檢測網站上的重要工作流程。
- 使用
execute()呼叫傳回的權杖和 MFA 參數,建立評估作業,取得 MFArequestToken。 - 根據要使用的管道 (僅支援電子郵件),使用
requestToken觸發多重驗證挑戰。 - 在網站上驗證使用者輸入的 PIN 碼。
- 使用驗證要求中傳回的權杖建立新的評估。
事前準備
通過安全性審查後,即可使用 MFA。在專案中新增帳單帳戶時,系統會啟動安全性審查。新增帳單帳戶,即可將網站加入這項功能。
如要啟用多重驗證的電子郵件驗證功能,請按照下列步驟操作:
前往 Google Cloud 控制台的「reCAPTCHA」reCAPTCHA頁面。
確認專案名稱顯示在資源選取器中。
如果沒有看到專案名稱,請按一下資源選取器,然後選取專案。
按一下「設定」。
在「Multi Factor Authentication」(多重驗證) 窗格中,按一下「Configure」(設定)。
在「設定多重驗證」對話方塊中,執行下列操作:
- 如要啟用電子郵件驗證,請點選「Enable email」(啟用電子郵件) 切換按鈕。
- 在「寄件者名稱」方塊中輸入您的名稱。
在「寄件者電子郵件」方塊中輸入您的電子郵件地址。
按一下 [儲存]。
設定寄件者電子郵件地址後,請設定 DNS 記錄,避免發生傳送問題。在下列步驟中,請將
example.com替換為您的網域。新增 SPF 記錄,允許 reCAPTCHA 代表您傳送電子郵件:
Host: example.com Value: v=spf1 include:_spf.recaptchamail.goog ~all加入下列 CNAME 項目,讓伺服器尋找 DKIM 簽章:
Host: recaptcha1._domainkey.example.com Value: recaptcha1._domainkey.recaptchamail.goog.Host: recaptcha2._domainkey.example.com Value: recaptcha2._domainkey.recaptchamail.goog.
檢測網站上的重要工作流程
透過 execute() 函式將必要資訊傳遞至 reCAPTCHA,進行風險評估。execute() 函式會傳回在產生權杖時解析的 Promise。
在 execute() 函式中附加額外的 twofactor 參數,如下列程式碼範例所示:
grecaptcha.enterprise.execute(KEY_ID, {
action: 'login',
twofactor: true
}).then(token => {
// Handle the generated token.
});
將 KEY_ID 替換為您為網站建立的分數型金鑰。
建立評估
使用 execute() 函式產生的權杖,透過後端的 reCAPTCHA 用戶端程式庫或 REST API 建立評估作業。
本文說明如何使用 REST API 建立 MFA 評估。如要瞭解如何使用用戶端程式庫建立評估,請參閱「為網站建立評估」。
建立評估前,請先完成下列工作:
設定 Fraud Defense 的驗證機制。
驗證方法取決於 Fraud Defense 的設定環境。下表可協助您選擇適當的驗證方法和支援的介面,以設定驗證:
環境 介面 驗證方式 Google Cloud - REST
- 用戶端程式庫
使用附加的服務帳戶。 地端部署或其他雲端服務供應商 REST 使用 API 金鑰或 Workload Identity 聯盟。 如要使用 API 金鑰,建議您套用 API 金鑰限制,確保 API 金鑰安全無虞。
用戶端程式庫 使用下列設定:
- 如果是 Python 或 Java,請使用 API 金鑰或 Workload Identity Federation。
如要使用 API 金鑰,建議您套用 API 金鑰限制,確保 API 金鑰安全無虞。
- 如為其他語言,請使用 Workload Identity 聯盟。
選擇使用者不會經常變更的穩定帳戶 ID
accountId,並在projects.assessments.create方法中提供給評估作業。對於與同一位使用者相關的所有事件,這個穩定帳戶 ID 的值應相同。您可以提供下列資訊做為帳戶 ID:使用者 ID
如果每個帳戶都能與穩定的使用者名稱、電子郵件地址或電話號碼建立專屬關聯,您就可以將這些資訊做為
accountId。當您提供這類跨網站 ID (可在不同網站重複使用的 ID) 時,Fraud Defense 會使用這項資訊,根據跨網站模型標記濫用帳戶 ID,並運用與這些 ID 相關的跨網站濫用模式知識,加強保護使用者帳戶。或者,如果每個帳戶都有專屬的內部使用者 ID,您可以將該 ID 提供為
accountId。雜湊處理或加密
如果沒有與每個帳戶唯一相關聯的內部使用者 ID,您可以將任何穩定 ID 轉換為不透明的網站專屬帳戶 ID。Fraud Defense 帳戶防護工具仍需使用這個 ID,才能瞭解使用者活動模式並偵測異常行為,但這個 ID 不會與其他網站共用。
選取任何穩定的帳戶 ID,並使用加密或雜湊函式,在傳送至 Fraud Defense 前將其設為不透明:
加密 (建議):使用確定性加密方法加密帳戶 ID,產生穩定的密文。如需詳細操作說明,請參閱「以決定性方式加密資料」。選擇對稱式加密而非雜湊處理時,您不需要保留使用者 ID 與對應不透明使用者 ID 之間的對應關係。解密 Fraud Defense 傳回的不透明 ID,將其轉換為使用者 ID。
雜湊處理:建議使用 SHA256-HMAC 方法,並搭配您選擇的自訂鹽值,對帳戶 ID 進行雜湊處理。由於雜湊值只能單向轉換,您必須保留產生的雜湊值與使用者 ID 之間的對應關係,才能將傳回的雜湊帳戶 ID 對應回原始帳戶。
在 projects.assessments.create 方法中,新增 accountId 參數和端點 (例如要在評估中驗證的電子郵件地址)。
使用任何要求資料之前,請先修改下列項目的值:
- PROJECT_ID:您的 Google Cloud 專案 ID。
- TOKEN:從
grecaptcha.enterprise.execute()呼叫傳回的權杖。 - KEY_ID:您在網站上安裝的評分式金鑰。
- ACCOUNT_ID:網站專屬的使用者帳戶 ID。
- EMAIL_ID:需要觸發驗證要求的電子郵件地址。
HTTP 方法和網址:
POST https://recaptchaenterprise.googleapis.com/v1/projects/PROJECT_ID/assessments
JSON 要求內文:
{
"event": {
"token": "TOKEN",
"siteKey": "KEY_ID",
"userInfo": {
"accountId": "ACCOUNT_ID"
}
}
"accountVerification": {
"endpoints": [{
"emailAddress": "EMAIL_ID",
}]
}
}
如要傳送要求,請選擇以下其中一個選項:
curl
將要求主體儲存在名為 request.json 的檔案中,然後執行下列指令:
curl -X POST \
-H "Authorization: Bearer $(gcloud auth print-access-token)" \
-H "Content-Type: application/json; charset=utf-8" \
-d @request.json \
"https://recaptchaenterprise.googleapis.com/v1/projects/PROJECT_ID/assessments"
PowerShell
將要求主體儲存在名為 request.json 的檔案中,然後執行下列指令:
$cred = gcloud auth print-access-token
$headers = @{ "Authorization" = "Bearer $cred" }
Invoke-WebRequest `
-Method POST `
-Headers $headers `
-ContentType: "application/json; charset=utf-8" `
-InFile request.json `
-Uri "https://recaptchaenterprise.googleapis.com/v1/projects/PROJECT_ID/assessments" | Select-Object -Expand Content
您應該會收到如下的 JSON 回覆:
{
[...],
"accountVerification": {
"endpoints": [{
"emailAddress": "foo@bar.com",
"requestToken": "tplIUFvvJUIpLaOH0hIVj2H71t5Z9mDK2RhB1SAGSIUOgOIsBv",
"lastVerificationTime": "",
}],
"latestVerificationResult": "RESULT_UNSPECIFIED"
}
}
評估結果會顯示裝置上指定端點最近一次成功驗證的日期和時間 (如有)。此外,每個端點都包含一個 requestToken 欄位,內含加密字串。如果您決定要為該端點觸發 MFA 驗證,就必須將這個加密字串傳回網頁。要求權杖的效期為 15 分鐘。
建議做法
如果專案已啟用 reCAPTCHA 帳戶防護,評估回應除了包含 MFA 相關資訊,還會提供帳戶防護相關資訊。「recommended_action」欄位會顯示在觸發 MFA 驗證前可採取的動作。
以下範例顯示建議略過多重驗證的評估結果:
{ [...], "accountDefenderAssessment": { labels: ["PROFILE_MATCH"], "recommended_action": "SKIP_2FA" } }
recommended_action 欄位可包含下列任一值:
| 值 | 說明 |
|---|---|
RECOMMENDED_ACTION_UNSPECIFIED |
表示帳戶防護無法判斷這項要求。 |
SKIP_2FA |
表示帳戶防護工具認為可以略過這次評估的 MFA。這通常表示使用者最近已在這部裝置上通過網站驗證。 |
REQUEST_2FA |
表示您為使用者觸發 MFA 驗證。詳情請參閱「帳戶防禦評估回應」。 |
在網站上觸發 MFA 驗證
如要根據評估內容中的資訊驗證使用者,請將評估結果中要驗證的端點 MFA requestToken 傳回網頁。
呼叫 challengeAccount() 觸發多重驗證挑戰。challengeAccount() 函式會傳回 promise,在完成驗證後會解析,如果發生錯誤或逾時,則會拒絕。完成後,系統會產生包含更新資訊的新權杖,並傳送該權杖以進行評估。
如要觸發多重驗證挑戰,請按照下列步驟操作:
測試 MFA 整合。
呼叫
challengeAccount()並提供下列值,觸發 MFA 驗證:- KEY_ID:您在網站上安裝的評分式金鑰。
- REQUEST_TOKEN_FROM_ASSESSMENT:評估回應中
requestToken欄位的值。 - CONTAINER_HTML_COMPONENT_ID:必須顯示驗證問題的 HTML 元件 ID。如未指定這個參數,系統會在網頁頂端的疊加層中顯示驗證問題。
以下範例說明如何呼叫
challengeAccount(),觸發多重驗證挑戰:grecaptcha.enterprise.challengeAccount(KEY_ID, { 'account-token': REQUEST_TOKEN_FROM_ASSESSMENT, 'container': CONTAINER_HTML_COMPONENT_ID }).then(newToken => { // Handle the new token. });如果
challengeAccount()要求成功,系統會顯示 HTML 元件,供您輸入收到的 PIN 碼。輸入正確的 PIN 碼後,newToken變數會傳遞至含有判決權杖的鏈結函式,以便透過後端建立的評估進行驗證。使用下列參數建立驗證控制代碼並啟動驗證:
// Initialize verification handle. const verificationHandle = grecaptcha.enterprise.eap.initTwoFactorVerificationHandle( KEY_ID, REQUEST_TOKEN_FROM_ASSESSMENT ); // Call the challenge API. verificationHandle.challengeAccount().then( (challengeResponse) => { if (challengeResponse.isSuccess()) { // Handle success: This means displaying an input for the end user to // enter the PIN that they received and then call the `verifyAccount(pin)` // method. } else { // Handle API failure } });
從網頁驗證多重驗證碼
取得使用者的 PIN 碼後,請驗證 PIN 碼是否正確。
如要驗證 PIN 碼,請使用使用者輸入的 PIN 碼呼叫 verificationHandle.verifyAccount()。
verificationHandle.verifyAccount(pin).then(
(verifyResponse) => {
if (verifyResponse.isSuccess()) {
// Handle success: Send the result of `verifyResponse.getVerdictToken()`
// to the backend in order to determine if the code was valid.
} else {
// Handle API failure
}
},
(error) => {
// Handle other errors
}
);
建立新的評估作業
使用 accountId 和 endpoints 建立新的評估作業。如需操作說明,請參閱「建立多重驗證評估」。
在用戶端完成工作流程後,您會收到新的權杖,可用於取得所觸發驗證的結果。評估結果會顯示最近一次成功驗證的時間戳記,以及成功狀態。
以下範例顯示使用從網站取得的新權杖建立新評估時,您會收到的評估範例:
{ [...], "accountVerification": { "endpoints": [{ "emailAddress": "foo@bar.com", "requestToken": "tplIUFvvJUIpLaOH0hIVj2H71t5Z9mDK2RhB1SAGSIUOgOIsBv", "lastVerificationTime": "2020-03-23 08:27:12 PST", }], "latestVerificationResult": "SUCCESS_USER_VERIFIED" } }
latestVerificationResult 欄位可能會顯示下表列出的不同狀態:
| 驗證結果狀態 | 說明 |
|---|---|
| SUCCESS_USER_VERIFIED | 使用者已成功通過驗證。 |
| ERROR_USER_NOT_VERIFIED | 使用者未通過驗證測試。 |
| ERROR_SITE_ONBOARDING_INCOMPLETE | 網站未正確導入,無法使用這項功能。 |
| ERROR_RECIPIENT_NOT_ALLOWED | 這個收件者未獲准傳送電子郵件至 (僅限測試期間)。 |
| ERROR_RECIPIENT_ABUSE_LIMIT_EXHAUSTED | 這位收件者在短時間內收到的驗證碼過多。 |
| ERROR_CUSTOMER_QUOTA_EXHAUSTED | 您已超過可用的多重驗證配額。 |
| ERROR_CRITICAL_INTERNAL | 由於系統發生內部錯誤,因此無法完成驗證。 |
| RESULT_UNSPECIFIED | 沒有最新驗證資訊 (從未驗證)。 |