如何用声明解析器转换处理Azure B2C IdP URL 提取域名构建动态LoadUri
Azure B2C 提取redirect_uri指定片段动态拼接LoadUri落地方案
Azure AD B2C 自定义策略不支持直接在LoadUri节点内做字符串截取操作,必须按照「声明解析器取原始值→声明转换提取目标片段→转换后的值传入内容定义参数→拼接生成最终加载地址」的流程实现,具体步骤如下:
步骤1:声明所需的自定义Claim类型
在扩展策略文件TrustFrameworkExtensions.xml的ClaimsSchema节点下,新增两个声明分别存储原始redirect_uri和提取后的目标域名段:
<ClaimsSchema> <!-- 存储从OIDC请求上下文获取的原始redirect_uri值 --> <ClaimType Id="redirectUriRaw"> <DisplayName>Raw redirect URI from OIDC request</DisplayName> <DataType>string</DataType> </ClaimType> <!-- 存储从redirect_uri中提取的目标域名段(示例中为somedomain) --> <ClaimType Id="redirectDomainSegment"> <DisplayName>Extracted target domain segment from redirect URI</DisplayName> <DataType>string</DataType> </ClaimType> </ClaimsSchema>
步骤2:配置字符串解析的声明转换
在同文件的ClaimsTransformations节点下,新增两个转换规则,完成原始值赋值和正则提取目标字段:
<ClaimsTransformations> <!-- 从OIDC上下文读取原始redirect_uri,赋值给自定义声明 --> <ClaimsTransformation Id="SetRawRedirectUri" TransformationMethod="CreateStringClaim"> <InputParameters> <InputParameter Id="value" DataType="string" Value="{OIDC:RedirectUri}" /> </InputParameters> <OutputClaims> <OutputClaim ClaimTypeReferenceId="redirectUriRaw" TransformationClaimType="createdClaim" /> </OutputClaimsTransformation> </ClaimsTransformation> <!-- 正则匹配提取目标域名段,适配https://xxx.targetdomain.com格式 --> <ClaimsTransformation Id="ExtractTargetDomainSegment" TransformationMethod="RegexReplace"> <InputClaims> <InputClaim ClaimTypeReferenceId="redirectUriRaw" TransformationClaimType="inputClaim" /> </InputClaims> <InputParameters> <InputParameter Id="regularExpression" DataType="string" Value="^https?:\/\/[^\/]+\.([^.]+)\.[^.]+(\/.*)?$" /> <InputParameter Id="replacementValue" DataType="string" Value="$1" /> </InputParameters> <OutputClaims> <OutputClaim ClaimTypeReferenceId="redirectDomainSegment" TransformationClaimType="outputClaim" /> </OutputClaims> </ClaimsTransformation> </ClaimsTransformations>
步骤3:注册声明转换对应的技术配置文件
在同文件的ClaimsProviders节点下,新增声明转换工具类的技术配置,供用户旅程调用:
<ClaimsProvider> <DisplayName>Claims Transformation Utilities</DisplayName> <TechnicalProfiles> <TechnicalProfile Id="ClaimsTransformation-SetRawRedirectUri"> <DisplayName>Set raw redirect uri claim</DisplayName> <Protocol Name="Proprietary" Handler="Web.TPEngine.Providers.ClaimsTransformationProtocolProvider, Web.TPEngine, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null" /> <OutputClaimsTransformations> <OutputClaimsTransformation ReferenceId="SetRawRedirectUri" /> </OutputClaimsTransformations> </TechnicalProfile> <TechnicalProfile Id="ClaimsTransformation-ExtractTargetDomainSegment"> <DisplayName>Extract target domain segment from redirect uri</DisplayName> <Protocol Name="Proprietary" Handler="Web.TPEngine.Providers.ClaimsTransformationProtocolProvider, Web.TPEngine, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null" /> <InputClaims> <InputClaim ClaimTypeReferenceId="redirectUriRaw" /> </InputClaims> <OutputClaimsTransformations> <OutputClaimsTransformation ReferenceId="ExtractTargetDomainSegment" /> </OutputClaimsTransformations> </TechnicalProfile> </TechnicalProfiles> </ClaimsProvider>
步骤4:在用户旅程最前置节点挂载转换逻辑
修改SignUpOrSignIn用户旅程,将声明转换作为第一个编排步骤执行,确保内容加载前完成值计算:
<UserJourney Id="SignUpOrSignIn"> <OrchestrationSteps> <!-- 前置步骤:执行redirect_uri解析转换 --> <OrchestrationStep Order="1" Type="ClaimsExchange"> <ClaimsExchanges> <ClaimsExchange Id="SetRawRedirectUriExchange" TechnicalProfileReferenceId="ClaimsTransformation-SetRawRedirectUri" /> <ClaimsExchange Id="ExtractDomainSegmentExchange" TechnicalProfileReferenceId="ClaimsTransformation-ExtractTargetDomainSegment" /> </ClaimsExchanges> </OrchestrationStep> <!-- 原有编排步骤序号整体向后顺延1位,其余内容保持不变 --> </OrchestrationSteps> </UserJourney>
注意:原有用户旅程的编排步骤序号需要整体顺推1位,避免步骤顺序冲突
步骤5:修改信赖方配置与LoadUri拼接规则
首先修改信赖方(RP)文件的ContentDefinitionParameters配置,传入提取完成的域名段,而非原始redirect_uri:
<RelyingParty> <DefaultUserJourney ReferenceId="SignUpOrSignIn" /> <UserJourneyBehaviors> <ContentDefinitionParameters> <!-- 替换原有OIDC:RedirectUri参数,传入提取后的域名段 --> <Parameter Name="domainSegment">{Claim:redirectDomainSegment}</Parameter> </ContentDefinitionParameters> </UserJourneyBehaviors> <!-- 其余RP原有配置保持不变 --> </RelyingParty>
再修改api.selfasserted内容定义的LoadUri节点,拼接参数生成最终动态地址:
<ContentDefinition Id="api.selfasserted"> <LoadUri>https://somestoragaccount/{Context:ContentDefinitionParameter:domainSegment}/unified.html</LoadUri> <RecoveryUri>~/common/default_page_error.html</RecoveryUri> <DataUri>urn:com:microsoft:aad:b2c:elements:contract:selfasserted:2.0.0</DataUri> <Metadata> <Item Key="DisplayName">Collect information from user page</Item> </Metadata> </ContentDefinition>
按照示例请求URL,最终拼接生成的LoadUri为https://somestoragaccount/somedomain/unified.html,符合动态加载要求。
验证与注意事项
- 上述正则默认适配
http(s)://[业务前缀].[目标提取段].通用顶级域名格式,如果业务存在.com.cn、.co.jp这类二级后缀域名,需调整正则捕获规则,避免取值错误 - 声明转换必须配置为用户旅程的第一个执行步骤,确保内容定义加载前完成值计算,否则会出现占位符替换为空的问题
- 联调阶段可接入Application Insights采集B2C策略运行日志,确认
redirectDomainSegment声明的输出值是否符合预期
内容的提问来源于stack exchange,提问作者bibhu mishra
相关产品推荐
相关产品推荐

