在Azure AD B2C中,如何在首次从社交登录登录时将社交帐户链接到任何现有本地帐户? [英] In Azure AD B2C, How do i link a social account with any existing local account during first time sign in from social login?
本文介绍了在Azure AD B2C中,如何在首次从社交登录登录时将社交帐户链接到任何现有本地帐户?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!
问题描述
如果还没有本地帐户,只需按照说明创建社交帐户和使用随机密码的本地帐户here。
已经存在一个堆栈溢出问题,该问题与here非常相似,但它始终需要登录到我不想要的本地帐户,并且谈论对我毫无意义的&qot;SQL标识服务。
推荐答案
我以Wojtekdo的TechnicalProfile为起点,仔细阅读关于自定义配置文件的MS documents,并着眼于我想要做的事情,成功地实现了这一点。我还从Jas Suri的评论中提供的link中提取了用户身份的概念。
我使用子旅程将社交帐户与本地帐户合并,只是为了将其与主要旅程分开。
请注意,我不验证或要求提供本地帐户的密码。我认为这是可以接受的,因为用户在创建Facebook帐户时已经验证了电子邮件的所有权。不过,我更愿意验证本地帐户,并且我有Stackoverflow question如何执行此操作。为实现此目的,TrustFramework扩展了XML:
<BuildingBlocks>
<ClaimsSchema>
<ClaimType Id="userIdentity">
<DisplayName>userIdentity</DisplayName>
<DataType>userIdentity</DataType>
<AdminHelpText>userIdentity</AdminHelpText>
<UserHelpText>userIdentity</UserHelpText>
</ClaimType>
<ClaimType Id="userIdentities">
<DisplayName>userIdentities</DisplayName>
<DataType>userIdentityCollection</DataType>
<AdminHelpText>userIdentities</AdminHelpText>
<UserHelpText>userIdentities</UserHelpText>
</ClaimType>
<ClaimType Id="issuers">
<DisplayName>issuers</DisplayName>
<DataType>stringCollection</DataType>
<UserHelpText>User identity providers. This information is received from alternativeSecurityIds</UserHelpText>
</ClaimType>
<ClaimType Id="signInNamesInfo.emailAddress">
<DisplayName>Email Address</DisplayName>
<DataType>string</DataType>
<AdminHelpText>Email address that the user can use to sign in.</AdminHelpText>
<UserHelpText>Email address to use for signing in.</UserHelpText>
<UserInputType>TextBox</UserInputType>
</ClaimType>
<ClaimType Id="emails">
<DisplayName>Email Addresses</DisplayName>
<DataType>stringCollection</DataType>
<AdminHelpText>Email addresses of the user.</AdminHelpText>
<UserHelpText>Your email addresses.</UserHelpText>
</ClaimType>
<ClaimType Id="strongAuthenticationEmailAddress">
<DisplayName>Email Address</DisplayName>
<DataType>string</DataType>
<AdminHelpText>Email address that the user can use for strong authentication.</AdminHelpText>
<UserHelpText>Email address to use for strong authentication.</UserHelpText>
<UserInputType>TextBox</UserInputType>
</ClaimType>
</ClaimsSchema>
<ClaimsTransformations>
<ClaimsTransformation Id="CreateEmailsFromOtherMailsAndSignInNamesInfo" TransformationMethod="AddItemToStringCollection">
<InputClaims>
<InputClaim ClaimTypeReferenceId="signInNamesInfo.emailAddress" TransformationClaimType="item" />
<InputClaim ClaimTypeReferenceId="otherMails" TransformationClaimType="collection" />
</InputClaims>
<OutputClaims>
<OutputClaim ClaimTypeReferenceId="emails" TransformationClaimType="collection" />
</OutputClaims>
</ClaimsTransformation>
<ClaimsTransformation Id="AddStrongAuthenticationEmailToEmails" TransformationMethod="AddItemToStringCollection">
<InputClaims>
<InputClaim ClaimTypeReferenceId="strongAuthenticationEmailAddress" TransformationClaimType="item" />
<InputClaim ClaimTypeReferenceId="emails" TransformationClaimType="collection" />
</InputClaims>
<OutputClaims>
<OutputClaim ClaimTypeReferenceId="emails" TransformationClaimType="collection" />
</OutputClaims>
</ClaimsTransformation>
<ClaimsTransformation Id="CreateSubjectClaimFromObjectID" TransformationMethod="CreateStringClaim">
<InputParameters>
<InputParameter Id="value" DataType="string" Value="Not supported currently. Use oid claim." />
</InputParameters>
<OutputClaims>
<OutputClaim ClaimTypeReferenceId="sub" TransformationClaimType="createdClaim" />
</OutputClaims>
</ClaimsTransformation>
<!-- Sample: On sign-in (first time) with social account, create a userIdentity claim, using issuerUserId and issuer name -->
<ClaimsTransformation Id="CreateUserIdentity" TransformationMethod="CreateUserIdentity">
<InputClaims>
<InputClaim ClaimTypeReferenceId="issuerUserId" TransformationClaimType="issuerUserId" />
<InputClaim ClaimTypeReferenceId="identityProvider" TransformationClaimType="issuer" />
</InputClaims>
<OutputClaims>
<OutputClaim ClaimTypeReferenceId="userIdentity" TransformationClaimType="userIdentity" />
</OutputClaims>
</ClaimsTransformation>
<!--Sample: Add a userIdentity to the userIdentities collection. .-->
<ClaimsTransformation Id="AppendUserIdentity" TransformationMethod="AddItemToUserIdentityCollection">
<InputClaims>
<InputClaim ClaimTypeReferenceId="userIdentity" TransformationClaimType="item" />
<InputClaim ClaimTypeReferenceId="userIdentities" TransformationClaimType="collection" />
</InputClaims>
<OutputClaims>
<OutputClaim ClaimTypeReferenceId="userIdentities" TransformationClaimType="collection" />
</OutputClaims>
</ClaimsTransformation>
<!--Sample: Extracts the list of social identity providers associated with the user -->
<ClaimsTransformation Id="ExtractIssuers" TransformationMethod="GetIssuersFromUserIdentityCollectionTransformation">
<InputClaims>
<InputClaim ClaimTypeReferenceId="userIdentities" TransformationClaimType="userIdentityCollection" />
</InputClaims>
<OutputClaims>
<OutputClaim ClaimTypeReferenceId="issuers" TransformationClaimType="issuersCollection" />
</OutputClaims>
</ClaimsTransformation>
</ClaimsTransformations>
</BuildingBlocks>
<ClaimsProviders>
<ClaimsProvider>
<DisplayName>Azure Active Directory</DisplayName>
<TechnicalProfiles>
<TechnicalProfile Id="AAD-ReadCommon">
<Metadata>
<Item Key="Operation">Read</Item>
<Item Key="RaiseErrorIfClaimsPrincipalDoesNotExist">true</Item>
</Metadata>
<OutputClaims>
<OutputClaim ClaimTypeReferenceId="userPrincipalName" />
<OutputClaim ClaimTypeReferenceId="displayName" />
<OutputClaim ClaimTypeReferenceId="otherMails" />
<OutputClaim ClaimTypeReferenceId="strongAuthenticationEmailAddress" PartnerClaimType="signInNames.emailAddress" />
</OutputClaims>
<OutputClaimsTransformations>
<OutputClaimsTransformation ReferenceId="CreateEmailsFromOtherMailsAndSignInNamesInfo" />
<OutputClaimsTransformation ReferenceId="AddStrongAuthenticationEmailToEmails" />
</OutputClaimsTransformations>
<IncludeTechnicalProfile ReferenceId="AAD-Common" />
</TechnicalProfile>
<TechnicalProfile Id="AAD-UserReadUsingEmailAddress-NoError">
<Metadata>
<Item Key="Operation">Read</Item>
<Item Key="RaiseErrorIfClaimsPrincipalDoesNotExist">false</Item>
<Item Key="UserMessageIfClaimsPrincipalDoesNotExist">An account could not be found for the provided user ID.</Item>
</Metadata>
<InputClaims>
<InputClaim ClaimTypeReferenceId="email" PartnerClaimType="logonIdentifier" Required="true" />
</InputClaims>
<OutputClaims>
<OutputClaim ClaimTypeReferenceId="objectId" />
<OutputClaim ClaimTypeReferenceId="accountEnabled" />
</OutputClaims>
<IncludeTechnicalProfile ReferenceId="AAD-ReadCommon" />
</TechnicalProfile>
<TechnicalProfile Id="AAD-AssertAccountEnabledAndCreateSubjectClaimFromObjectId">
<DisplayName>Assert account enabled</DisplayName>
<Protocol Name="Proprietary" Handler="Web.TPEngine.Providers.ClaimsTransformationProtocolProvider, Web.TPEngine, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null" />
<InputClaims>
<InputClaim ClaimTypeReferenceId="objectId" PartnerClaimType="sub" Required="true" />
</InputClaims>
<OutputClaims>
<OutputClaim ClaimTypeReferenceId="objectId" />
<OutputClaim ClaimTypeReferenceId="accountEnabled" />
<OutputClaim ClaimTypeReferenceId="authenticationSource" DefaultValue="localAccountAuthentication" />
<OutputClaim ClaimTypeReferenceId="email" />
</OutputClaims>
<OutputClaimsTransformations>
<OutputClaimsTransformation ReferenceId="AssertAccountEnabledIsTrue" />
<OutputClaimsTransformation ReferenceId="CreateSubjectClaimFromObjectID" />
</OutputClaimsTransformations>
<UseTechnicalProfileForSessionManagement ReferenceId="SM-Noop" />
</TechnicalProfile>
<TechnicalProfile Id="AAD-UserUpdateWithUserIdentities">
<Metadata>
<Item Key="api-version">1.6</Item>
<Item Key="Operation">Write</Item>
<Item Key="RaiseErrorIfClaimsPrincipalAlreadyExists">false</Item>
<Item Key="RaiseErrorIfClaimsPrincipalDoesNotExist">true</Item>
</Metadata>
<InputClaims>
<InputClaim ClaimTypeReferenceId="objectId" Required="true" />
</InputClaims>
<PersistedClaims>
<PersistedClaim ClaimTypeReferenceId="objectId" />
<PersistedClaim ClaimTypeReferenceId="userIdentities" />
<!--<PersistedClaim ClaimTypeReferenceId="extension_requiresMigrationBool" DefaultValue="false" AlwaysUseDefaultValue="true"/>-->
</PersistedClaims>
<OutputClaims>
<OutputClaim ClaimTypeReferenceId="objectId" />
<OutputClaim ClaimTypeReferenceId="userIdentities" />
</OutputClaims>
<OutputClaimsTransformations>
<OutputClaimsTransformation ReferenceId="ExtractIssuers" />
</OutputClaimsTransformations>
<IncludeTechnicalProfile ReferenceId="AAD-Common" />
<UseTechnicalProfileForSessionManagement ReferenceId="SM-Noop" />
</TechnicalProfile>
</TechnicalProfiles>
</ClaimsProvider>
<ClaimsProvider>
<DisplayName>Facebook</DisplayName>
<TechnicalProfiles>
<TechnicalProfile Id="Facebook-OAUTH">
<OutputClaimsTransformations>
<OutputClaimsTransformation ReferenceId="CreateUserIdentity" />
<OutputClaimsTransformation ReferenceId="AppendUserIdentity" />
</OutputClaimsTransformations>
</TechnicalProfile>
</TechnicalProfiles>
</ClaimsProvider>
</ClaimsProviders>
<UserJourneys>
<UserJourney Id="SignUpOrSignIn">
<OrchestrationSteps>
<!-- For social IDP authentication, attempt to find the user account in the directory. -->
<OrchestrationStep Order="4" Type="ClaimsExchange">
<Preconditions>
<Precondition Type="ClaimEquals" ExecuteActionsIf="true">
<Value>authenticationSource</Value>
<Value>localAccountAuthentication</Value>
<Action>SkipThisOrchestrationStep</Action>
</Precondition>
</Preconditions>
<ClaimsExchanges>
<ClaimsExchange Id="AADUserReadUsingAlternativeSecurityId" TechnicalProfileReferenceId="AAD-UserReadUsingAlternativeSecurityId-NoError"/>
</ClaimsExchanges>
</OrchestrationStep>
<!-- Find local account using email-->
<OrchestrationStep Order="5" Type="ClaimsExchange">
<Preconditions>
<Precondition Type="ClaimEquals" ExecuteActionsIf="true">
<Value>authenticationSource</Value>
<Value>localAccountAuthentication</Value>
<Action>SkipThisOrchestrationStep</Action>
</Precondition>
</Preconditions>
<ClaimsExchanges>
<ClaimsExchange Id="FindLocalAccount" TechnicalProfileReferenceId="AAD-UserReadUsingEmailAddress-NoError"/>
</ClaimsExchanges>
</OrchestrationStep>
<!-- start a subjourney to verify local account if one was found in previous step -->
<OrchestrationStep Order="6" Type="InvokeSubJourney">
<Preconditions>
<Precondition Type="ClaimEquals" ExecuteActionsIf="true">
<Value>authenticationSource</Value>
<Value>localAccountAuthentication</Value>
<Action>SkipThisOrchestrationStep</Action>
</Precondition>
<Precondition Type="ClaimsExist" ExecuteActionsIf="false">
<Value>objectId</Value>
<Action>SkipThisOrchestrationStep</Action>
</Precondition>
</Preconditions>
<JourneyList>
<Candidate SubJourneyReferenceId="MergeWithLocalAccount" />
</JourneyList>
</OrchestrationStep>
</OrchestrationSteps>
</UserJourney>
</UserJourneys>
<SubJourneys>
<SubJourney Id="MergeWithLocalAccount" Type="Call">
<OrchestrationSteps>
<!-- assert any found local account is enabled -->
<OrchestrationStep Order="1" Type="ClaimsExchange">
<Preconditions>
<Precondition Type="ClaimEquals" ExecuteActionsIf="true">
<Value>authenticationSource</Value>
<Value>localAccountAuthentication</Value>
<Action>SkipThisOrchestrationStep</Action>
</Precondition>
<Precondition Type="ClaimsExist" ExecuteActionsIf="false">
<Value>objectId</Value>
<Action>SkipThisOrchestrationStep</Action>
</Precondition>
</Preconditions>
<ClaimsExchanges>
<ClaimsExchange Id="AssertLocalAccountEnabled" TechnicalProfileReferenceId="AAD-AssertAccountEnabledAndCreateSubjectClaimFromObjectId"/>
</ClaimsExchanges>
</OrchestrationStep>
<!-- merge account with any existing and verified local account-->
<OrchestrationStep Order="2" Type="ClaimsExchange">
<Preconditions>
<Precondition Type="ClaimEquals" ExecuteActionsIf="true">
<Value>authenticationSource</Value>
<Value>localAccountAuthentication</Value>
<Action>SkipThisOrchestrationStep</Action>
</Precondition>
<Precondition Type="ClaimsExist" ExecuteActionsIf="false">
<Value>objectId</Value>
<Action>SkipThisOrchestrationStep</Action>
</Precondition>
<Precondition Type="ClaimsExist" ExecuteActionsIf="false">
<Value>accountVerified</Value>
<Action>SkipThisOrchestrationStep</Action>
</Precondition>
</Preconditions>
<ClaimsExchanges>
<ClaimsExchange Id="AADMergeAccount" TechnicalProfileReferenceId="AAD-UserUpdateWithUserIdentities" />
</ClaimsExchanges>
</OrchestrationStep>
</OrchestrationSteps>
</SubJourney>
</SubJourneys>
我已经包含了我为解决合并的社交帐户和本地帐户而添加的所有XML,不包括其他所有内容。我知道这不是最小的解决方案,可能不需要某些BIT,但它是一个有效的解决方案,可能会帮助其他人弄清楚。
这篇关于在Azure AD B2C中,如何在首次从社交登录登录时将社交帐户链接到任何现有本地帐户?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!
查看全文