MFA Conditional Access Policies in AD FS 2012 R2

Hello again. The previous Multi-Factor Authentication (MFA) post on User Certificates provided an opportunity to expand and look at  some of the more interesting scenarios for MFA conditional access.  This “interest”, if I may call it that, stemmed from playing around with MFA over the last few months and looking at the role of conditional access polices therein.

Ramiro Calderon wrote a great article on MFA policy here and it comes highly recommended. As he mentions in his post, the AD FS claims engine computes MFA authentication requests (defined via the AD Management UI) in a logical OR fashion. This can be initially a little confusing and we’ll take a look at some more creative use of MFA policies, to handle more flexible access scenarios in R2.

MFA Primer

To make use of MFA, an MFA provider is required. In a vanilla AD FS R2 setup, this is limited to certificate authentication using client certificates (see previous post). For other MFA options, check with your favorite 2FA vendor to see if they’ve written an MFA adapter for AD FS R2.

In the global authentication policy, the MFA provider needs to be enabled.


Let’s have a look at what happens when MFA is enabled through the AD FS Management UI. MFA policies can be triggered either globally (applicable to all relying parties), or on the relying party itself.

In the example below, MFA is required for securing access to applications outside of the organization, what Microsoft call Extranet use.


Users connecting from outside the corporate network will be prompted after successful AD username/password authentication by the MFA handler.

When the MFA policy is set globally, this can be seen in PowerShell via the Get-AdfsAdditionalAuthenticationRule

c:[Type == "", Value == "false"] => issue(Type = "", Value = "");

If a global authentication policy is not specified, but the policy is enabled in a relying party rule, then an additional authentication rule, defined on the RP, is evaluated. This allows for a more refined use of policy and I’ll show examples of this, by way of scenarios, later in the post.

The AD FS Management UI is sufficient for applying the use of MFA in most single “context” access scenarios. By this I mean, we are able to enforce the requirement of MFA to satisfy policies, that stipulate additional authentication is required by use of one of either user/group, device or location. For example, if we determine that a MFA policy needs to be used by location only, e.g. Extranet, we simply select the Extranet location checkbox. All users connecting from outside of the corporate network must then use MFA. Conversely, if we want to enforce MFA for a specific subset of users/groups, irrespective of their location (Extranet/Intranet), by adding them via the users/groups option in the UI, this can be  also be set. Finally, we can also specify that unregistered or registered devices (a la Workplace Join) need to use MFA, via the devices checkboxes. The fact that these policies may also be applied independently on a per relying party basis, often satisfy basic access policy needs.

The challenge arises when dealing with a combination of policy, for example, when stating an MFA requirement by device and by location.


AD FS will now trigger MFA when an unregistered device (non-workplace joined) connects to AD FS AND also when users are connecting from the Internet  The policies are evaluated independently and we may unwittingly be enforcing MFA for a registered device in a Workplace Join scenario, when the desired outcome was actually to ensure that a single authentication factor (the device certificate paired with the user concerned) was sufficient for access from the outside. This is the logical OR behavior that Ramiro refers to in his post.

Similar behavior can be observed if the following settings are made.


Here we have a specific user/group requiring MFA and also the location (Extranet) checkbox is checked. Users who are members of the GU-SEC-ADFS-MFA group must always use MFA, irrespective of their location AND other users, connecting from outside of the corporate network, will be challenged by the MFA handler. Again, if the intention was to enforce MFA for a combination of outcomes; namely, by group and location outside, then this is not the outcome.

Rules  are evaluated independently when set via the UI. Given that requirements via the UI operate this way, if there is a requirement to enforce MFA via policy where:

      • it’s an unregistered device AND
      • connecting from the Internet
                OR in the second example where:
              • user is member of group X AND
              • connecting from the Internet

            The AD FS Management  UI doesn’t support this arrangement. Instead, more refined policies can be handled with PowerShell, using combinations of authentication rules. As with the UI, this can be expressed either as a global authentication policy applicable to all relying parties (Set-AdfsAdditionalAuthenticationRule) or MFA policies defined on a per relying party basis (Set-AdfsRelyingPartyTrust).  I’ll use the latter to drum up examples of setting finer-grained access rules in the scenarios that follow. More work for us admins, but greater flexibility to boot…

                    Scenario A: Externally connecting workplace joined device (registered user)

              Requirement: Registered users on Workplace Join devices connecting from outside the corporate Internet may authenticate using the device authentication certificate. All other users/devices must use MFA.

            $rp = Get-AdfsRelyingPartyTrust –Name "WIF Test Application"
            Set-AdfsRelyingPartyTrust –TargetRelyingParty $rp –AdditionalAuthenticationRules ‘c: [Type == "
  ", Value == "false"] && [Type == "", Value == "false"] => issue(Type = "", Value = "");’

              Requirement: Users who are members of Group X are exempt from a general policy stipulating use of MFA when connecting from the outside of  the network. All other users must use MFA. Note: We flip the behavior with the Group SID claim use in Scenario B by using the NOT EXISTS evaluation.

              $rp = Get-AdfsRelyingPartyTrust –Name "WIF Test Application"
              Set-AdfsRelyingPartyTrust –TargetRelyingParty $rp –AdditionalAuthenticationRules ‘exists([Type == "
    ", Value == "false"]) && NOT EXISTS ([Type == "", Value == "S-1-5-21-Insert your Group SID here"]) => issue(Type = "", Value = "");’

              Scenario D: MFA using a custom evaluation rule

              Requirement: The Azure Sprout organization is using “vanity” UPNs to enforce MFA for non-standard UPN suffixes. Corporate users with an UPN suffix may use single factor (forms) authentication from the outside. All other UPN suffixes in the “organization” must use MFA.

              $rp = Get-AdfsRelyingPartyTrust –Name "WIF Test Application"
              Set-AdfsRelyingPartyTrust –TargetRelyingParty $rp –AdditionalAuthenticationRules ‘NOT EXISTS([Type == "
    ", Value =~ "^.*@azuresprout\.net$"]) => issue(Type = "", Value = "");’

              Scenario E: MFA based on custom claims extrapolated from an attribute store

              Requirement: An SQL attribute store is used to augment claims when accessing a business application. Values extracted  from the store are to be used as triggers for MFA.

              On the relying party, we connect to an attribute store and populate an sqlrole claim, based on running a stored procedure to find the user and the appropriate access information for user on application FOO.

              c:[Type == ""%5D => add(store = "SQL Attribute Store", types = (""), query = "EXEC dbo.GET_ACCESSTOKEN @UserID={0},@AppCode=’FOO’", param = c.Value);

            Next, on the RP pipeline, we define the MFA requirement based on value returned in the sqlrole claim .

            $rp = Get-AdfsRelyingPartyTrust –Name "WIF Test Application"
            Set-AdfsRelyingPartyTrust –TargetRelyingParty $rp –AdditionalAuthenticationRules  ‘c:[Type ==”, Value =~ "<Whatever the response we’re expecting for MFA trigger>"]) => issue(Type = "", Value = ";);’ 

              The latter scenario is a little more unusual, but I’ve used it to highlight what is possible (as with Scenario D) outside of the normal conventions provided by the UI.

              As a sneak peek into the new Window Server “10” release, it appears that Microsoft have expanded authentication support and making the nuances of policy-based access control more accessible to the end user, through the use of a new policy template editor, made available to the AD FS administrator.. more on this and another ADFS “stuff” to come…

              Here’s a snippet of the new rules editor from the pre-release.


            5 thoughts on “MFA Conditional Access Policies in AD FS 2012 R2

            1. Hi, very nice blog. Help me to understand more the conditional Access on ADFS with MFA.
              I try to use what I learned from your blog for my Scenario. I’m using ADFS 3.0 on my Server 2012 R2 in combination With Azure Multi – Factor – Authentication Server. Everything is working fine. My End-user has to use 2 Factor Authentication when not connected to Intranet. This was easy to configure because this is possible With ADFS UI. 🙂
              But now I want that MFA is only used for “External” users and the Client is not Active Sync. Because otherwise with my rule above Active Sync is not more working.
              So I translate your Input to my case. I try to make a rule like if not Active Sync user and External then use MFA.
              I try the following:
              $rp = Get-AdfsRelyingPartyTrust –Name “Microsoft Office 365 Identity Platform”
              $NewMFARule = ‘NOT EXISTS ([Type == “”, Value==”Microsoft.Exchange.ActiveSync”]) && exists ([Type == “”, Value == “false”]) => issue(Type = “”, Value =””);’
              Set-AdfsRelyingPartyTrust –TargetRelyingParty $rp -AdditionalAuthenticationRules $NewMFARule

              The command was successful, but then I my adfs crash and Login was not possible. I got an Error 80041317 from my ADFS Server“ Searching for the error I found the following link: –> This solve my Problem.

              But can you see what I’ve done wrong with my rule or have you an Idea how to implement my scenario?

              For your help and answer in advance many thanks and many Christmas.

              For sure I’m looking forward for Vnext Server. More flexibility seems to existing on the next Server Version from Microsoft. And this makes sense because outside on practical world it seems to having endless Scenarios for conditional MFA Access 🙂

              Best regards

              1. Thanks Ercan! Nice scenario for implementing MFA 🙂
                On the O365 relying party, if you ever touch it, you’ll need to update the corresponding O365 tenant as you saw when you experienced the problem and error (stale federation).
                Once you fixed the error, what is the behaviour you’re experience now? Does it completely ignore the rule?

                Merry Xmas.

                1. Hi Mylo,
                  After I follow the instruction mentioned on the link above, it created a complete new relying Party for Office 365 in ADFS. So all changes I made before was reset. I think this was the reason why it work again. 🙂
                  Let me say after this reset I just configure on ADFS what was working.  Activate MFA only for external Connection.
                  I didn’t execute the powershell above again shortly before Christmas 🙂
                  But I will do it afterwards again and just execute afterwards the following powershell command against my Office 365 subscription.
                  “Update-MsolFederatedDomain ” May this help to solve my Problem.
                  Do you see any error on my command or do I have any wrong thought on my rule for the scenario I want to have?
                  Normally I would expect it should work. Actual I can’t see my error. But I will keep you updated on my issue.
                  So long we will enjoy Christmas. 🙂

                  Best regards

                2. Hi Mylo,
                  I just take little time to test it again. Now again put the same command as I mentioned on my first command. Then I do a test before I execute “Update-MsolFederatedDomain” against my Office 365 subscription. And now it’s worked as I’m expecting also I don’t execute the “Update-MsolFederatedDomain”
                  Well I think I also know what I do wrong on my first execution.
                  The Rule was the same but on the powershell “Set-AdfsRelyingPartyTrust” the first time ( when everything goes wrong) I use the parameter -Targetname “Microsoft Office 365 Identity Platform” instead of the Parameter “–TargetRelyingParty $ rp …
                  I’m not sure if this was the Problem or something else but indeed the was the only difference before the first try and the second one.
                  Now I got my Christmas present 🙂
                  Wish you again nice and relaxed days.

                  Best regards

            Leave a Reply

            Fill in your details below or click an icon to log in:


            You are commenting using your account. Log Out /  Change )

            Facebook photo

            You are commenting using your Facebook account. Log Out /  Change )

            Connecting to %s