# 双重身份验证

{% hint style="info" %}
对应的[官方页面地址](https://contributing.bitwarden.com/architecture/deep-dives/authentication/two-factor-auth)
{% endhint %}

当用户账户需要双重身份验证 (2FA) 时，正常的 Bitwarden 身份验证流程将被转移以处理 2FA 请求。

## 发起身份验证请求 <a href="#initial-authentication-request" id="initial-authentication-request"></a>

当 Identity API 收到用户的身份验证请求时，[验证过程](/architecture/deep-dives/authentication.md#validating-the-request)的一部分是确保用户的账户不需要双因素身份验证。

如果账户（或用户的组织）要求 2FA，则 `/connect/token` 端点将返回带有 HTTP 状态代码 `400` 的响应，值为 `invalid_grant` 的 `Error`，以及「要求两因素」的 `ErrorMessage`。响应还将包含带有以下 JSON 数据的 `CustomResponse`：

```json
{
    { "TwoFactorProviders", [2FA provider keys] },
    { "TwoFactorProviders2", [2FA provider data] },
    { "MasterPasswordPolicy", [Master password policy] },
    // Only if the user has email 2FA
    { "SsoEmail2faSessionToken", [Token to allow email to be passed through SSO flow] }
}
```

## 在客户端处理 2FA 响应 <a href="#handling-2fa-response-on-the-client" id="handling-2fa-response-on-the-client"></a>

如果客户端在尝试登录时检测到 [`IdentityTwoFactorResponse`](https://github.com/bitwarden/clients/blob/master/libs/common/src/auth/models/response/identity-two-factor.response.ts)，则会从 `CustomResponse` 中提取可用的 2FA 提供程序并将其呈现给用户。

每个 2FA 方法都有自己的 UI，但在所有情况下，用户都会生成某种「令牌」来捕获用户的响应。当用户完成 2FA 流程时，将在 [`TwoFactorComponent`](https://github.com/bitwarden/clients/blob/master/apps/desktop/src/auth/two-factor.component.ts) 上捕获此令牌。

用户输入 2FA 后，新的身份验证请求将被 `POST` 到 `/connect/token` 端点，其内容与原始失败请求相同，并在请求正文中添加以下内容：

* `twoFactorToken` - 设置为用户的 2FA 响应生成的令牌
* `twoFactorProvider` - 设置为用于 2FA 的提供程序
* `twoFactorRemember` - 根据用户是否选择「记住」其 2FA 响应进行设置

## 使用 2FA 响应验证请求 <a href="#validating-request-with-2fa-response" id="validating-request-with-2fa-response"></a>

当验证 PI 收到包含附加 2FA 属性的第二个身份验证请求时，它会再次执行身份验证过程。

这次，服务器能够验证 2FA 响应。为此，它会针对客户端在请求中发送的 `twoFactorProvider` 的相关 `IUserTwoFactorTokenProvider` 实现调用 `ValidateAsync`。

如果令牌有效，则会[生成成功的响应并将其返回给客户端](/architecture/deep-dives/authentication.md#generating-a-response)。如果用户选择记住其 2FA 实体，则此响应会在 `TwoFactorToken` 属性中包含一个令牌，该令牌可以包含在后续请求中以绕过 2FA。


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://dev.ppgg.in/architecture/deep-dives/authentication/two-factor-auth.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
