Validez des entrées utilisateur en utilisant une stratégie Azure Active Directory B2C personnalisée
La stratégie Azure Active Directory B2C (Azure AD B2C) personnalisée vous permet non seulement de rendre les entrées utilisateur obligatoires, mais également de les valider. Vous pouvez marquer des entrées utilisateur comme requises, telles que <DisplayClaim ClaimTypeReferenceId="givenName" Required="true"/>
, mais cela ne signifie pas que vos utilisateurs entreront des données valides. Azure AD B2C fournit différentes façons de valider une entrée utilisateur. Dans cet article, vous apprenez à écrire une stratégie personnalisée qui collecte et valide des entrées utilisateur à l’aide des approches suivantes :
Limitez les données entrées par un utilisateur en fournissant une liste d’options parmi lesquelles choisir. Cette approche utilise une Énumération de valeurs, que vous ajoutez quand vous déclarez une revendication.
Définissez un modèle auquel une entrée utilisateur doit correspondre. Cette approche utilise des Expressions régulières, que vous ajoutez quand vous déclarez une revendication.
Définissez un ensemble de règles et exigez qu’une entrée utilisateur obéisse à une ou plusieurs règles. Cette approche utilise Prédicats que vous ajoutez quand vous déclarez une revendication.
Utilisez le type de revendication spécial reenterPassword pour vérifier que l’utilisateur a correctement saisi de nouveau son mot de passe lors de la collecte des entrées utilisateur.
Configurez un Profil technique de validation qui définit des règles d’entreprise complexes qui sont impossibles à définir au niveau de la déclaration de revendication. Par exemple, vous collectez une entrée utilisateur qui doit être validée par rapport à une valeur ou à un ensemble de valeurs dans une revendication différente.
Prérequis
Si vous n’en avez pas, créez un locataire Azure AD B2C qui est lié à votre abonnement Azure.
Inscrivez une application web et activez l’octroi implicite de jeton d’ID. Pour l’URI de redirection, utilisez https://jwt.ms.
Visual Studio Code (VS Code) doit être installé sur votre ordinateur.
Effectuez les étapes décrites dans Collecter et manipuler des entrées utilisateur en utilisant une stratégie Azure AD B2C personnalisée. Cet article fait partie de la série de guides pratiques Créer et exécuter vos propres stratégies personnalisées.
Notes
Cet article fait partie de la série de guides pratiques Créer et exécuter vos propres stratégies personnalisées dans Azure Active Directory B2C. Nous vous recommandons de commencer cette série par le premier article.
Étape 1 : valider des entrées utilisateur en limitant les options d’entrée utilisateur
Si vous connaissez toutes les valeurs possibles qu’un utilisateur peut saisir pour une entrée donnée, vous pouvez fournir un ensemble fini de valeurs qu’un utilisateur doit sélectionner. Vous pouvez utiliser DropdownSinglSelect, CheckboxMultiSelect et RadioSingleSelectUserInputType dans cet objectif. Dans cet article, vous allez utiliser un type d’entrée RadioSingleSelect :
Dans VS Code, ouvrez le fichier
ContosoCustomPolicy.XML
.Dans l’élément
ClaimsSchema
du fichierContosoCustomPolicy.XML
, déclarez le type de revendication suivant :<ClaimType Id="accountType"> <DisplayName>Account Type</DisplayName> <DataType>string</DataType> <UserHelpText>The type of account used by the user</UserHelpText> <UserInputType>RadioSingleSelect</UserInputType> <Restriction> <Enumeration Text="Contoso Employee Account" Value="work" SelectByDefault="true"/> <Enumeration Text="Personal Account" Value="personal" SelectByDefault="false"/> </Restriction> </ClaimType>
Nous avons déclaré la revendication accountType . Lorsque la valeur de la revendication est collectée auprès de l’utilisateur, celui-ci doit sélectionner Compte d’employé Contoso pour une valeur travail ou Compte personnel pour une valeur personnel.
Azure AD B2C vous permet également d’adapter votre stratégie à différentes langues et fournit des restrictions de type de compte pour de multiples langues. Pour en savoir plus, consultez l’article Localiser l’interface utilisateur de l’article Ajouter des attributs utilisateur.
Localisez le profil technique avec
Id="UserInformationCollector"
, ajoutez la revendication accountType comme revendication d’affichage en utilisant le code suivant :<DisplayClaim ClaimTypeReferenceId="accountType" Required="true"/>
Dans le profil technique avec
Id="UserInformationCollector"
, ajoutez la revendication accountType comme revendication de sortie en utilisant le code suivant :<OutputClaim ClaimTypeReferenceId="accountType"/>
Pour inclure la revendication de type de compte dans le jeton d’accès, recherchez l’élément
RelyingParty
, ajoutez la revendication accountType en tant que revendication de jeton en utilisant le code suivant :<OutputClaim ClaimTypeReferenceId="accountType" />
Étape 2 : valider des entrées utilisateur en utilisation des expressions régulières
Quand il n’est pas possible de connaître toutes les valeurs d’entrée utilisateur possibles à l’avance, vous autorisez l’utilisateur à saisir les données lui-même. Dans ce cas, vous pouvez utiliser des expressions régulières (regex) ou un modèle pour imposer la façon dont une entrée utilisateur doit être mise en forme. Par exemple, un e-mail doit avoir le symbole at (@) et un point (.) dans son texte.
Lorsque vous déclarez une revendication, la stratégie personnalisée vous permet de définir une regex à laquelle l’entrée utilisateur doit correspondre. Vous pouvez éventuellement fournir un message qui s’affiche à l’utilisateur lorsque son entrée ne correspond pas à l’expression.
Localisez l’élément
ClaimsSchema
et déclarez la revendication e-mail en utilisant le code suivant :<ClaimType Id="email"> <DisplayName>Email Address</DisplayName> <DataType>string</DataType> <DefaultPartnerClaimTypes> <Protocol Name="OpenIdConnect" PartnerClaimType="email"/> </DefaultPartnerClaimTypes> <UserHelpText>Your email address. </UserHelpText> <UserInputType>TextBox</UserInputType> <Restriction> <Pattern RegularExpression="^[a-zA-Z0-9.!#$%&'^_`{}~-]+@[a-zA-Z0-9-]+(?:\.[a-zA-Z0-9-]+)*$" HelpText="Please enter a valid email address something like maurice@contoso.com"/> </Restriction> </ClaimType>
Recherchez le profil technique avec
Id="UserInformationCollector"
, ajoutez la revendication e-mail comme revendication d’affichage en utilisant le code suivant :<DisplayClaim ClaimTypeReferenceId="email" Required="true"/>
Dans le profil technique avec
Id="UserInformationCollector"
, ajoutez la revendication e-mail comme revendication de sortie en utilisant le code suivant :<OutputClaim ClaimTypeReferenceId="email"/>
Recherchez l’élément
RelyingParty
et ajoutez e-mail comme revendication de jeton en utilisant le code suivant :<OutputClaim ClaimTypeReferenceId="email" />
Étape 3 : valider des entrées utilisateur à l’aide des prédicats
Vous avez utilisé une regex pour valider des entrées utilisateur. Toutefois, la regex a une faiblesse, c’est-à-dire que le message d’erreur s’affiche tant que vous n’avez pas corrigé l’entrée sans vous montrer l’exigence particulière que l’entrée est manquante.
Les validations de prédicats vous permettent de résoudre ce problème en vous autorisant à définir un ensemble de règles (prédicats) et un message d’erreur indépendant pour chaque règle. Dans les stratégies personnalisées, le prédicat a une méthode intégrée qui définit les vérifications que vous souhaitez effectuer. Par exemple, vous pouvez utiliser la méthode de prédicat IsLengthRange pour vérifier si un mot de passe utilisateur se trouve dans la plage des paramètres minimaux et maximaux (valeurs) spécifiés.
Bien que les Prédicats définissent la validation à effectuer par rapport à un type de revendication, les PredicateValidations regroupent un jeu de prédicats pour former une validation d’entrée utilisateur qui peut être appliquée à un type de revendication. Par exemple, vous créez un groupe de prédicats de validation qui valide plusieurs types de caractères autorisés pour un mot de passe. Les éléments Prédicats et PredicateValidations sont des éléments enfants de la section BuildingBlocks
de votre fichier de stratégie.
Localisez l’élément
ClaimsSchema
et déclarez la revendication mot de passe en utilisant le code suivant :<ClaimType Id="password"> <DisplayName>Password</DisplayName> <DataType>string</DataType> <AdminHelpText>Enter password</AdminHelpText> <UserHelpText>Enter password</UserHelpText> <UserInputType>Password</UserInputType> </ClaimType>
Ajoutez un élément
Predicates
en tant qu’enfant de la sectionBuildingBlocks
en utilisant le code suivant. Vous ajoutez l’élémentPredicates
sous l’élémentClaimsSchema
:<Predicates> </Predicates>
Dans l’élément
Predicates
, définissez des prédicats à l’aide du code suivant :<Predicate Id="IsLengthBetween8And64" Method="IsLengthRange" HelpText="The password must be between 8 and 64 characters."> <Parameters> <Parameter Id="Minimum">8</Parameter> <Parameter Id="Maximum">64</Parameter> </Parameters> </Predicate> <Predicate Id="Lowercase" Method="IncludesCharacters" HelpText="a lowercase letter"> <Parameters> <Parameter Id="CharacterSet">a-z</Parameter> </Parameters> </Predicate> <Predicate Id="Uppercase" Method="IncludesCharacters" HelpText="an uppercase letter"> <Parameters> <Parameter Id="CharacterSet">A-Z</Parameter> </Parameters> </Predicate> <Predicate Id="Number" Method="IncludesCharacters" HelpText="a digit"> <Parameters> <Parameter Id="CharacterSet">0-9</Parameter> </Parameters> </Predicate> <Predicate Id="Symbol" Method="IncludesCharacters" HelpText="a symbol"> <Parameters> <Parameter Id="CharacterSet">@#$%^&*\-_+=[]{}|\\:',.?/`~"();!</Parameter> </Parameters> </Predicate> <Predicate Id="PIN" Method="MatchesRegex" HelpText="The password must be numbers only."> <Parameters> <Parameter Id="RegularExpression">^[0-9]+$</Parameter> </Parameters> </Predicate> <Predicate Id="AllowedCharacters" Method="MatchesRegex" HelpText="An invalid character was provided."> <Parameters> <Parameter Id="RegularExpression">(^([0-9A-Za-z\d@#$%^&*\-_+=[\]{}|\\:',?/`~"();! ]|(\.(?!@)))+$)|(^$)</Parameter> </Parameters> </Predicate> <Predicate Id="DisallowedWhitespace" Method="MatchesRegex" HelpText="The password must not begin or end with a whitespace character."> <Parameters> <Parameter Id="RegularExpression">(^\S.*\S$)|(^\S+$)|(^$)</Parameter> </Parameters> </Predicate>
Nous avons défini plusieurs règles, qui, lorsqu’elles sont réunies, décrivent un mot de passe acceptable. Ensuite, vous pouvez regrouper des prédicats afin de former un jeu de stratégies de mot de passe que vous pouvez utiliser dans votre stratégie.
Ajoutez un élément
PredicateValidations
en tant qu’enfant de la sectionBuildingBlocks
en utilisant le code suivant. Vous ajoutez l’élémentPredicateValidations
en tant qu’enfant de la sectionBuildingBlocks
, mais en dessous de l’élémentPredicates
:<PredicateValidations> </PredicateValidations>
Dans l’élément
PredicateValidations
, définissez PredicateValidations à l’aide du code suivant :<PredicateValidation Id="SimplePassword"> <PredicateGroups> <PredicateGroup Id="DisallowedWhitespaceGroup"> <PredicateReferences> <PredicateReference Id="DisallowedWhitespace"/> </PredicateReferences> </PredicateGroup> <PredicateGroup Id="AllowedCharactersGroup"> <PredicateReferences> <PredicateReference Id="AllowedCharacters"/> </PredicateReferences> </PredicateGroup> <PredicateGroup Id="LengthGroup"> <PredicateReferences> <PredicateReference Id="IsLengthBetween8And64"/> </PredicateReferences> </PredicateGroup> </PredicateGroups> </PredicateValidation> <PredicateValidation Id="StrongPassword"> <PredicateGroups> <PredicateGroup Id="DisallowedWhitespaceGroup"> <PredicateReferences> <PredicateReference Id="DisallowedWhitespace"/> </PredicateReferences> </PredicateGroup> <PredicateGroup Id="AllowedCharactersGroup"> <PredicateReferences> <PredicateReference Id="AllowedCharacters"/> </PredicateReferences> </PredicateGroup> <PredicateGroup Id="LengthGroup"> <PredicateReferences> <PredicateReference Id="IsLengthBetween8And64"/> </PredicateReferences> </PredicateGroup> <PredicateGroup Id="CharacterClasses"> <UserHelpText>The password must have at least 3 of the following:</UserHelpText> <PredicateReferences MatchAtLeast="3"> <PredicateReference Id="Lowercase"/> <PredicateReference Id="Uppercase"/> <PredicateReference Id="Number"/> <PredicateReference Id="Symbol"/> </PredicateReferences> </PredicateGroup> </PredicateGroups> </PredicateValidation> <PredicateValidation Id="CustomPassword"> <PredicateGroups> <PredicateGroup Id="DisallowedWhitespaceGroup"> <PredicateReferences> <PredicateReference Id="DisallowedWhitespace"/> </PredicateReferences> </PredicateGroup> <PredicateGroup Id="AllowedCharactersGroup"> <PredicateReferences> <PredicateReference Id="AllowedCharacters"/> </PredicateReferences> </PredicateGroup> </PredicateGroups> </PredicateValidation>
Nous avons défini trois prédicats de validation, StrongPassword, CustomPassword et SimplePassword. En fonction des caractéristiques du mot de passe que vous souhaitez que vos utilisateurs saisissent, vous pouvez utiliser n’importe quel mot de passe sur les validations de prédicat. Dans cet article, nous allons utiliser un mot de passe fort.
Recherchez la déclaration de type de revendication du mot de passe et ajoutez la validation du prédicat StrongPassword juste après la déclaration d’élément UserInputType qu’elle contient en utilisant le code suivant :
<PredicateValidationReference Id="StrongPassword" />
Recherchez le profil technique avec
Id="UserInformationCollector"
, ajoutez la revendication mot de passe comme revendication d’affichage en utilisant le code suivant :<DisplayClaim ClaimTypeReferenceId="password" Required="true"/>
Dans le profil technique avec
Id="UserInformationCollector"
, ajoutez la revendication mot de passe comme revendication de sortie en utilisant le code suivant :<OutputClaim ClaimTypeReferenceId="password"/>
Notes
Pour des raisons de sécurité, nous n’ajouterons pas le mot de passe d’un utilisateur en tant que revendication dans le jeton généré par votre stratégie. Nous n’ajoutons donc pas la revendication de mot de passe à l’élément de la partie de confiance.
Étape 4 : valider le mot de passe et confirmer le mot de passe
Vous pouvez demander à vos utilisateurs d’entrer leur mot de passe deux fois pour confirmer que l’utilisateur se souvient du mot de passe qu’il a entré. Dans ce cas, vous devez vérifier la correspondance des deux valeurs entrées. La stratégie personnalisée offre une méthode simple pour répondre à cette exigence. Les types de revendications mot de passe et reenterPassword sont considérés comme spéciaux. Par conséquent, lorsqu’ils sont utilisés pour collecter des entrées utilisateur, l’interface utilisateur vérifie que l’utilisateur a correctement entré de nouveau son mot de passe.
Procédez comme suit pour valider la nouvelle entrée du mot de passe dans votre stratégie personnalisée :
Dans la section
ClaimsSchema
de votre fichierContosoCustomPolicy.XML
, déclarez la revendication reenterPassword juste après la revendication de mot de passe en utilisant le code suivant :<ClaimType Id="reenterPassword"> <DisplayName>Confirm new password</DisplayName> <DataType>string</DataType> <AdminHelpText>Confirm new password</AdminHelpText> <UserHelpText>Reenter password</UserHelpText> <UserInputType>Password</UserInputType> </ClaimType>
Pour collecter les entrées de confirmation de mot de passe de l’utilisateur, recherchez le profil technique
UserInformationCollector
autodéclaré, ajoutez la revendication reenterPassword en tant que revendication d’affichage à l’aide du code suivant :<DisplayClaim ClaimTypeReferenceId="reenterPassword" Required="true"/>
Dans votre fichier
ContosoCustomPolicy.XML
, localisez le profil techniqueUserInformationCollector
autodéclaré, ajoutez la revendication reenterPassword en tant que revendication de sortie à l’aide du code suivant :<OutputClaim ClaimTypeReferenceId="reenterPassword"/>
Étape 5 : charger un fichier de stratégie personnalisée
À ce point, vous avez créé votre stratégie pour répondre aux trois premières approches de validation des entrées utilisateur.
Suivez les étapes décrites dans Charger un fichier de stratégie personnalisée. Si vous chargez un fichier portant le même nom que celui déjà présent dans le portail, veillez à sélectionner Remplacer la stratégie personnalisée si elle existe déjà.
Étape 6 : Tester la stratégie personnalisée
Sous les Stratégies personnalisées, sélectionnez B2C_1A_CONTOSOCUSTOMPOLICY.
Pour l’élément Sélectionner une application dans la page de vue d’ensemble de la stratégie personnalisée, sélectionnez l’application web telle que webapp1 que vous avez précédemment inscrite. Vérifiez que l’élément Sélectionner l’URL de réponse est défini sur
https://jwt.ms
.Sélectionnez le bouton Exécuter maintenant.
Entrez le Prénom et le Nom.
Sélectionner Type de compte.
Pour l’élément Adresse e-mail, entrez une valeur d’e-mail qui n’est pas correctement mise en forme, par exemple maurice@contoso.
Pour l’élément Mot de passe, entrez la valeur de mot de passe qui n’obéit pas à toutes les caractéristiques d’un mot de passe fort tel que défini.
Sélectionnez le bouton Continuer. Un écran similaire à celui ci-dessous s’affiche :
Vous devez corriger vos entrées avant de continuer.
Entrez les valeurs correctes comme suggéré par les messages d’erreur, puis sélectionnez à nouveau le bouton Continuer. Une fois l’exécution de la stratégie terminée, vous êtes redirigé vers
https://jwt.ms
et le jeton JWT décodé s’affiche. Le jeton ressemble à l’extrait de jeton JWT suivant :
{
"typ": "JWT",
"alg": "RS256",
"kid": "pxLOMWFg...."
}.{
...
"sub": "c7ae4515-f7a7....",
...
"acr": "b2c_1a_contosocustompolicy",
"accountType": "work",
...
"email": "maurice@contoso.com",
"name": "Maurice Paulet",
"message": "Hello Maurice Paulet"
}.[Signature]
Étape 7 : valider des entrées utilisateur à l’aide des profils techniques de validation
Les techniques de validation que nous avons utilisées aux étapes 1, 2 et 3 ne s’appliquent pas à tous les scénarios. Si vos règles d’entreprise sont complexes à définir au niveau de la déclaration de revendication, vous pouvez configurer une Validation technique, puis l’appeler à partir d’un Profil technique autodéclaré.
Notes
Seuls les profils techniques à déclaration automatique peuvent utiliser des profils techniques de validation. En savoir plus sur les profils techniques de validation
Présentation du scénario
Il est nécessaire que, si le Type de compte de l’utilisateur est Compte d’employé Contoso, nous devions vérifier que son domaine de courrier est basé sur un jeu de domaines prédéfinis. Ces domaines sont contoso.com, fabrikam.com et woodgrove.com. Sinon, nous affichons une erreur à l’utilisateur jusqu’à ce qu’il utilise un Compte d’employé Contoso valide ou bascule vers Compte personnel.
Utilisez les règles suivantes pour découvrir comment valider des entrées utilisateur à l’aide des profils techniques de validation. Vous utilisez un profil technique de validation du type de transformation de revendications, mais vous pouvez également appeler un service d’API REST pour valider des données, comme vous allez le découvrir plus loin dans cette série.
Dans la section
ClaimsSchema
de votre fichierContosoCustomPolicy.XML
, déclarez les revendications domaine et domainStatus à l’aide du code suivant :<ClaimType Id="domain"> <DataType>string</DataType> </ClaimType> <ClaimType Id="domainStatus"> <DataType>string</DataType> </ClaimType>
Recherchez la section
ClaimsTransformations
et configurez les transformations de revendications à l’aide du code suivant :<ClaimsTransformation Id="GetDomainFromEmail" TransformationMethod="ParseDomain"> <InputClaims> <InputClaim ClaimTypeReferenceId="email" TransformationClaimType="emailAddress"/> </InputClaims> <OutputClaims> <OutputClaim ClaimTypeReferenceId="domain" TransformationClaimType="domain"/> </OutputClaims> </ClaimsTransformation> <ClaimsTransformation Id="LookupDomain" TransformationMethod="LookupValue"> <InputClaims> <InputClaim ClaimTypeReferenceId="domain" TransformationClaimType="inputParameterId"/> </InputClaims> <InputParameters> <InputParameter Id="contoso.com" DataType="string" Value="valid"/> <InputParameter Id="fabrikam.com" DataType="string" Value="valid"/> <InputParameter Id="woodgrove.com" DataType="string" Value="valid"/> <InputParameter Id="errorOnFailedLookup" DataType="boolean" Value="true"/> </InputParameters> <OutputClaims> <OutputClaim ClaimTypeReferenceId="domainStatus" TransformationClaimType="outputClaim"/> </OutputClaims> </ClaimsTransformation>
La transformation de la revendication GetDomainFromEmail extrait un domaine de l’adresse e-mail en utilisant la méthode ParseDomain et le stocke dans la revendication du domaine. La transformation de la revendication LookupDomain utilise le domaine extrait pour vérifier s’il est valide en le recherchant dans les domaines prédéfinis et en affectant l’élément valide à la revendication domainStatus.
Utilisez le code suivant pour ajouter un profil technique dans le même fournisseur de revendications que le profil technique avec
Id=UserInformationCollector
:<TechnicalProfile Id="CheckCompanyDomain"> <DisplayName>Check Company validity </DisplayName> <Protocol Name="Proprietary" Handler="Web.TPEngine.Providers.ClaimsTransformationProtocolProvider, Web.TPEngine, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null"/> <InputClaimsTransformations> <InputClaimsTransformation ReferenceId="GetDomainFromEmail"/> </InputClaimsTransformations> <OutputClaims> <OutputClaim ClaimTypeReferenceId="domain"/> </OutputClaims> <OutputClaimsTransformations> <OutputClaimsTransformation ReferenceId="LookupDomain"/> </OutputClaimsTransformations> </TechnicalProfile>
Nous avons déclaré le profil technique de transformation des revendications qui exécute les transformations de revendications GetDomainFromEmail et LookupDomain.
Recherchez le profil technique avec
Id=UserInformationCollector
et unValidationTechnicalProfile
juste après l’élémentOutputClaims
en utilisant le code suivant :<ValidationTechnicalProfiles> <ValidationTechnicalProfile ReferenceId="CheckCompanyDomain"> <Preconditions> <Precondition Type="ClaimEquals" ExecuteActionsIf="false"> <Value>accountType</Value> <Value>work</Value> <Action>SkipThisValidationTechnicalProfile</Action> </Precondition> </Preconditions> </ValidationTechnicalProfile> </ValidationTechnicalProfiles>
Nous avons ajouté un profil technique de validation au profil technique autodéclaré UserInformationCollector. Le profil technique est ignoré uniquement si la valeur accountType n’est pas égale à travail. Si le profil technique s’exécute et que le domaine de l’adresse e-mail n’est pas valide, une erreur est générée.
Localisez le profil technique avec
Id=UserInformationCollector
, puis ajoutez le code suivant dans la balisemetadata
.<Item Key="LookupNotFound">The provided email address isn't a valid Contoso Employee email.</Item>
Nous avons configuré une erreur personnalisée au cas où l’utilisateur n’utiliserait pas une adresse e-mail valide.
Suivez les instructions décrites dans Charger un fichier de stratégie personnalisée pour charger votre fichier de stratégie.
Suivez les instructions de l’étape 6 pour tester votre stratégie personnalisée :
- Pour l’élément Type de compte, sélectionnez Compte d’employé Contoso
- Pour l’élément Adresse e-mail, entrez une adresse e-mail non valide telle que maurice@fourthcoffee.com.
- Saisissez le reste des détails comme demandé, puis sélectionnez Continuer
Étant donné que l’élément maurice@fourthcoffee.com n’est pas un e-mail valide, vous verrez une erreur similaire à celle présentée dans la capture d’écran ci-dessous. Vous devez utiliser une adresse e-mail valide pour exécuter correctement la stratégie personnalisée et recevoir un jeton JWT.
Étapes suivantes
En savoir plus sur les profils techniques de validation.
Découvrez comment Activer ou désactiver de manière conditionnelle les profils techniques dans des stratégies personnalisées Azure AD B2C