在 Azure Active Directory B2C 中设置密码重置流

开始之前,请使用此页顶部的“选择策略类型”选择器来选择要设置的策略类型。 Azure Active Directory B2C 提供了两种定义用户如何与应用程序交互的方法:通过预定义的用户流,或者通过可完全配置的自定义策略。 对于每种方法,本文中所需的步骤都不同。

注册和登录历程中,用户可以使用“忘记密码?”链接重置自己的密码。 此自助式密码重置流适用于 Azure Active Directory B2C (Azure AD B2C) 中使用电子邮件地址用户名与密码进行登录的本地帐户。

提示

如果用户忘记了密码并想要重置密码,则可以使用自助式密码重置流更改其密码。 还可选择以下用户流选项之一以更改用户的密码:

  • 如果用户知道自己的密码并想要更改密码,可使用密码更改流
  • 如果你想要强制用户重置密码(例如,当用户首次登录时,当用户的密码被管理员重置时,或者在用户使用随机密码迁移到 Azure AD B2C 之后),请使用强制密码重置流。

密码重置流涉及以下步骤:

  1. 在注册和登录页上,用户选择“忘记密码?”链接。 Azure AD B2C 启动密码重置流。
  2. 在出现的下一个对话框中,用户输入其电子邮件地址,然后选择“发送验证码”。 Azure AD B2C 将验证码发送到用户的电子邮件帐户。 用户复制电子邮件中的验证码,将其输入到 Azure AD B2C 密码重置对话框中,然后选择“验证代码”。
  3. 然后,用户可以输入新密码。 (验证电子邮件后,用户仍可选择“更改电子邮件”按钮;如果想要将其删除,请参阅隐藏“更改电子邮件”按钮。)

显示密码重置流中的三个对话框的关系图。

selfAsserted.html 中“更改电子邮件”按钮的默认名称为“changeclaims”。 若要查找按钮名称,请在注册页上,使用“检查”等浏览器工具检查页面源。

先决条件

新的密码重置体验现在是注册或登录策略的一部分。 当用户选择“忘记密码?”链接时,该用户会立即转到“忘记密码”体验。 应用程序不再需要处理 AADB2C90118 错误代码,并且你不需要单独的密码重置策略。

以下部分介绍如何将自助式服务密码体验添加到自定义策略。 示例基于自定义策略初学者包中包含的策略文件。

提示

可在 GitHub 上找到“使用密码重置注册和登录”策略的完整示例。

若要向策略指示用户选择了“忘记密码?”链接,请定义一个布尔声明。 使用此声明将用户旅程定向到“忘记密码”技术配置文件。 也可以向令牌发出此声明,使应用程序检测到用户是使用“忘记密码”用户流登录的。

声明架构中宣布声明。 打开策略的扩展文件,例如,在 SocialAndLocalAccounts/TrustFrameworkExtensions.xml 中。

  1. 搜索 BuildingBlocks 元素。 如果该元素不存在,请添加该元素。

  2. 找到 ClaimsSchema 元素。 如果该元素不存在,请添加该元素。

  3. 将以下声明添加到 ClaimsSchema 元素。

    <!-- 
    <BuildingBlocks>
      <ClaimsSchema> -->
        <ClaimType Id="isForgotPassword">
          <DisplayName>isForgotPassword</DisplayName>
          <DataType>boolean</DataType>
          <AdminHelpText>Whether the user has selected Forgot your Password</AdminHelpText>
        </ClaimType>
      <!--
      </ClaimsSchema>
    </BuildingBlocks> -->
    

升级页面布局版本

需要页面布局版本 2.1.2 才能在注册或登录历程中启用自助式密码重置流。 若要升级页面布局版本,请执行以下操作:

  1. 打开策略的基本文件,例如 SocialAndLocalAccounts/TrustFrameworkBase.xml。

  2. 搜索 BuildingBlocks 元素。 如果该元素不存在,请添加该元素。

  3. 找到 ContentDefinitions 元素。 如果该元素不存在,请添加该元素。

  4. 将 ContentDefinition 元素内的 DataURI 元素修改为具有 ID

    <!-- 
    <BuildingBlocks>
      <ContentDefinitions> -->
        <ContentDefinition Id="api.signuporsignin">
          <DataUri>urn:com:microsoft:aad:b2c:elements:contract:unifiedssp:2.1.2</DataUri>
        </ContentDefinition>
      <!-- 
      </ContentDefinitions>
    </BuildingBlocks> -->
    

添加技术配置文件

声明转换技术配置文件访问 isForgotPassword 声明。 稍后将引用技术配置文件。 调用时,它会将 isForgotPassword 声明的值设置为 true

  1. 打开策略的扩展文件,例如,在 SocialAndLocalAccounts/TrustFrameworkExtensions.xml 中。
  2. 找到“ClaimsProviders”元素(如果该元素不存在,请创建它),然后添加以下声明提供程序:
<!-- 
<ClaimsProviders> -->
  <ClaimsProvider>
    <DisplayName>Local Account</DisplayName>
    <TechnicalProfiles>
      <TechnicalProfile Id="ForgotPassword">
        <DisplayName>Forgot your password?</DisplayName>
        <Protocol Name="Proprietary" Handler="Web.TPEngine.Providers.ClaimsTransformationProtocolProvider, Web.TPEngine, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null"/>
        <OutputClaims>
          <OutputClaim ClaimTypeReferenceId="isForgotPassword" DefaultValue="true" AlwaysUseDefaultValue="true"/>
        </OutputClaims>
        <UseTechnicalProfileForSessionManagement ReferenceId="SM-Noop" />
      </TechnicalProfile>
      <TechnicalProfile Id="SelfAsserted-LocalAccountSignin-Email">
        <Metadata>
          <Item Key="setting.forgotPasswordLinkOverride">ForgotPasswordExchange</Item>
        </Metadata>
      </TechnicalProfile>
      <TechnicalProfile Id="LocalAccountWritePasswordUsingObjectId">
        <UseTechnicalProfileForSessionManagement ReferenceId="SM-AAD" />
      </TechnicalProfile>
    </TechnicalProfiles>
  </ClaimsProvider>
<!-- 
</ClaimsProviders> -->

SelfAsserted-LocalAccountSignin-Email 技术配置文件 setting.forgotPasswordLinkOverride 定义了用户旅程中要执行的密码重置声明交换。

用户需要 LocalAccountWritePasswordUsingObjectId 技术配置文件 UseTechnicalProfileForSessionManagement SM-AAD 会话管理器才能在 SSO 条件下成功执行后续登录。

添加密码重置子历程

用户现在可以在用户旅程中登录、注册和执行密码重置。 为了更好地组织用户旅程,可以使用子历程来处理密码重置流。

子历程将从用户旅程中进行调用,并将执行特定的步骤以向用户提供密码重置体验。 使用 Call 类型的子历程,以便在子历程完成后,控制权将返回给启动了子历程的业务流程步骤。

  1. 打开策略的扩展文件,例如 SocialAndLocalAccounts/TrustFrameworkExtensions.xml。
  2. 找到 SubJourneys元素。 如果该元素不存在,请将其添加到 User Journeys 元素之后。 然后添加以下子历程:
<!--
<SubJourneys>-->
  <SubJourney Id="PasswordReset" Type="Call">
    <OrchestrationSteps>
      <!-- Validate user's email address. -->
      <OrchestrationStep Order="1" Type="ClaimsExchange">
        <ClaimsExchanges>
          <ClaimsExchange Id="PasswordResetUsingEmailAddressExchange" TechnicalProfileReferenceId="LocalAccountDiscoveryUsingEmailAddress" />
        </ClaimsExchanges>
      </OrchestrationStep>

      <!-- Collect and persist a new password. -->
      <OrchestrationStep Order="2" Type="ClaimsExchange">
        <ClaimsExchanges>
          <ClaimsExchange Id="NewCredentials" TechnicalProfileReferenceId="LocalAccountWritePasswordUsingObjectId" />
        </ClaimsExchanges>
      </OrchestrationStep>
    </OrchestrationSteps>
  </SubJourney>
<!--
</SubJourneys>-->

准备用户旅程

接下来,若要将“忘记密码?”链接连接到“忘记密码”子旅程,需要在 CombinedSignInAndSignUp 步骤的 ClaimsProviderSelection 元素中引用“忘记密码”子旅程 ID。

如果没有带有 CombinedSignInAndSignUp 步骤的自定义用户旅程,请完成以下步骤复制现有的注册或登录用户旅程。 否则,请继续下一部分。

  1. 在启动包中,打开 TrustFrameworkBase.xml 文件,例如 SocialAndLocalAccounts/TrustFrameworkBase.xml。
  2. 找到并复制包含 Id="SignUpOrSignIn"UserJourney 元素的完整内容。
  3. 打开 TrustFrameworkExtensions.xml 文件,例如 SocialAndLocalAccounts/TrustFrameworkExtensions.xml ,找到 UserJourneys 元素。 如果元素不存在,请创建一个。
  4. 通过粘贴在步骤 2 中复制的 UserJourney 元素的全部内容,创建 UserJourneys 元素的子元素 。
  5. 重命名用户旅程的 ID。 例如,Id="CustomSignUpSignIn"

在用户旅程中,可以将“忘记密码”子历程表示为 ClaimsProviderSelection。 通过添加此元素,可以将“忘记密码?”链接连接到忘记密码子历程。

  1. 打开 TrustFrameworkExtensions.xml 文件,例如 SocialAndLocalAccounts/TrustFrameworkExtensions.xml 。

  2. 在用户旅程中,查找包含 Type="CombinedSignInAndSignUp"Type="ClaimsProviderSelection" 的业务流程步骤元素。 这通常是第一个业务流程步骤。 ClaimsProviderSelections 元素包含用户可以用来登录的标识提供者列表。 添加以下行:

    <ClaimsProviderSelection TargetClaimsExchangeId="ForgotPasswordExchange" />
    
  3. 在下一个编排步骤中,通过添加以下行来添加 ClaimsExchange 元素:

    <ClaimsExchange Id="ForgotPasswordExchange" TechnicalProfileReferenceId="ForgotPassword" />
    
  4. 在当前步骤和下一步骤之间添加以下业务流程步骤。 添加的新业务流程步骤会检查 isForgotPassword 声明是否存在。 如果该声明存在,它将调用密码重置子历程

    <OrchestrationStep Order="3" Type="InvokeSubJourney">
      <Preconditions>
        <Precondition Type="ClaimsExist" ExecuteActionsIf="false">
          <Value>isForgotPassword</Value>
          <Action>SkipThisOrchestrationStep</Action>
        </Precondition>
      </Preconditions>
      <JourneyList>
        <Candidate SubJourneyReferenceId="PasswordReset" />
      </JourneyList>
    </OrchestrationStep>
    
  5. 添加新的业务流程步骤以后,请按顺序对这些步骤重新编号,不要跳过任何整数(1 到 N)。

设置要执行的用户旅程

修改或创建用户旅程后,请在“信赖方”部分指定 Azure AD B2C 将为此自定义策略执行的历程。

  1. 打开具有 Relying Party 元素的文件,例如 SocialAndLocalAccounts/SignUpOrSignin.xml。

  2. RelyingParty 元素中,找到 DefaultUserJourney 元素。

  3. 更新 DefaultUserJourney ReferenceId,使其与添加了 ClaimsProviderSelections 的用户旅程的 ID 匹配。

<RelyingParty>
  <DefaultUserJourney ReferenceId="CustomSignUpSignIn" />
  ...
</RelyingParty>

指示应用的“忘记密码”流

应用程序可能需要检测用户是否使用“忘记密码”用户流登录。 isForgotPassword 声明包含一个布尔值来指示这一行为。 该声明可以在发送给应用程序的令牌中发出。 如有必要,向“依赖方”部分的输出声明中添加 isForgotPassword。 应用程序可以检查 isForgotPassword 声明以确定用户是否重置了其密码。

<RelyingParty>
  <OutputClaims>
    ...
    <OutputClaim ClaimTypeReferenceId="isForgotPassword" DefaultValue="false" />
  </OutputClaims>
</RelyingParty>

上传自定义策略

  1. 登录 Azure 门户
  2. 如果有权访问多个租户,请选择顶部菜单中的“设置”图标,从“目录 + 订阅”菜单中切换到 Azure AD B2C 租户
  3. 在 Azure 门户中,搜索并选择“Azure AD B2C”。
  4. 在菜单中的“策略”下,选择“Identity Experience Framework”。
  5. 选择“上传自定义策略”。 按以下顺序上传已更改的策略文件:
    1. 策略的基文件,例如 TrustFrameworkBase.xml。
    2. 扩展策略,例如 TrustFrameworkExtensions.xml。
    3. 信赖方策略,例如 SignUpSignIn.xml。

隐藏“更改电子邮件”按钮(可选)

验证电子邮件后,用户仍然可以选择“更改电子邮件”,输入其他电子邮件地址,然后重复电子邮件验证过程。 如果你想要隐藏“更改电子邮件”按钮,可以修改 CSS 以在对话框中隐藏关联的 HTML 元素。 例如,可将以下 CSS 条目添加到 selfAsserted.html,然后使用 HTML 模板自定义用户界面

<style type="text/css">
   .changeClaims
   {
     visibility: hidden;
   }
</style>

测试密码重置流

  1. 选择想要测试的注册或登录用户流(“推荐”类型)。
  2. 选择“运行用户流”。
  3. 对于“应用程序”,请选择前面已注册的名为“webapp1”的 Web 应用程序。 “回复 URL”应显示为 https://jwt.ms
  4. 选择“运行用户流”。
  5. 在注册或登录页上,选择“忘记密码?”。
  6. 验证之前创建的帐户的电子邮件地址,然后选择“继续”。
  7. 在显示的对话框中,更改用户的密码,然后选择“继续”。 该令牌将返回到 https://jwt.ms,并且浏览器将显示该令牌。
  8. 检查返回令牌的 isForgotPassword 声明值。 如果该值存在且设置为 true,则指示用户已重置密码。

密码重置策略(旧版)

如果未启用自助式密码重置体验,选择此链接不会自动触发密码重置用户流。 而是将错误代码 AADB2C90118 返回给应用程序。 应用程序必须通过重新初始化身份验证库来验证 Azure AD B2C 密码重置用户流,从而处理此错误代码。

下图描绘了此过程:

  1. 在应用程序中,用户选择“登录”。 该应用发起授权请求并重定向到 Azure AD B2C,以便用户可以完成登录。 授权请求指定注册或登录策略名称,如 B2C_1_signup_signin。
  2. 用户选择“忘记密码?”链接。 Azure AD B2C 向应用程序返回 AADB2C90118 错误代码。
  3. 应用程序处理错误代码,并发起新的授权请求。 授权请求指定密码重置策略名称,如 B2C_1_pwd_reset。

此图显示了带编号步骤的旧密码重置用户流。

你可以在 ASP.NET 示例中看到一个基本演示,其中展示了用户流之间的关联方式。

创建密码重置用户流

若要允许应用程序用户重置其密码,请创建密码重置用户流:

  1. 在 Azure 门户中,转到 Azure AD B2C 租户概述。
  2. 在左侧菜单中的“策略”下,依次选择“用户流”、“新建用户流”。
  3. 在“创建用户流”中,选择“密码重置”用户流。
  4. 在“选择版本”下,选择“建议”,然后选择“创建” 。
  5. 对于“名称”,输入该用户流的名称。 例如 passwordreset1
  6. 对于“标识提供者”,请启用“使用用户名重置密码”或“使用电子邮件地址重置密码” 。
  7. 在“多重身份验证”下,如果你希望要求用户使用另一种身份验证方法来验证其身份,请选择方法类型,以及何时要强制执行多重身份验证。 了解详细信息
  8. 在“条件访问”下,如果已为 Azure AD B2C 租户配置条件访问策略,并且想要在此用户流中使用这些策略,请选中“强制实施条件访问策略”复选框。 无需指定策略名称。
  9. 在“应用程序声明”下,选择“显示更多”。 选择你希望在发送回应用程序的授权令牌中返回的声明。 例如,选择“用户的对象 ID”。
  10. 选择“确定”。
  11. 选择“创建”以添加用户流。 前缀 B2C_1 将自动添加到名称中。

测试用户流

若要测试用户流,请执行以下操作:

  1. 选择你创建的用户流。 在用户流概述页上,选择“运行用户流”。
  2. 在“应用程序”部分,选择要测试的 Web 应用程序,例如名为 webapp1 的应用程序(如果之前已注册)。 “回复 URL”应该为
  3. 选择“运行用户流”,验证要为其重置密码的帐户的电子邮件地址,然后选择“继续”。
  4. 更改密码,然后选择“继续”。 该令牌将返回到 https://jwt.ms,并且浏览器将显示该令牌。

创建密码重置策略

自定义策略是上传到 Azure AD B2C 租户的一组 XML 文件,用于定义用户旅程。 我们提供了初学者包,其中有多个预构建策略,包括注册和登录、密码重置以及配置文件编辑策略。 有关详细信息,请参阅 Azure AD B2C 中的自定义策略入门

Azure AD B2C 用户流和自定义策略故障排除

你的应用程序需要处理来自 Azure B2C 服务的某些错误。 了解如何对 Azure AD B2C 用户流和自定义策略进行故障排除

后续步骤

设置强制密码重置

通过嵌入的密码重置进行注册和登录