← Back to articles Security

9 Conditional Access Policies Most Admins Miss

9 Conditional Access Policies Most Admins Miss

The Scenario

A mid-size financial services client called us after their SOC flagged an impossible travel alert at 2 AM. A senior finance manager's account had authenticated from the Netherlands — the user was asleep in Manchester. The attacker had used a device code phishing email to steal a valid OAuth token, bypassed MFA entirely, and spent forty minutes in Exchange Online before the alert fired.

When we pulled the tenant's Conditional Access policy set the next morning, the gaps were immediately visible. Forty-three policies — and not one of them blocked device code flow. No MFA registration protection under risk conditions. No token protection. The tenant had a dense CA policy set that looked thorough on a spreadsheet and was full of holes in practice.

That incident is why this article exists. Below are the nine policies we now deploy in every engagement as a baseline hardening layer — policies that are frequently absent even in tenants with mature security programmes.

Why This Matters

Conditional Access is only effective as a complete policy set. A single missing policy is not a minor gap — it is a documented, exploitable attack lane. Modern identity attacks chain techniques together: steal a token here, register a new authenticator there, pivot to Graph API to enumerate mailboxes. A fragmented CA posture gives adversaries exactly the room they need.

The consequences are concrete. According to Microsoft's 2024 Digital Defense Report, over 99% of compromised accounts lacked MFA — but token theft attacks specifically target accounts where MFA is enabled. Blocking MFA registration under risk, eliminating legacy OAuth flows, and binding tokens to compliant devices are the controls that address the post-MFA attack surface. Ignoring them in 2025 is the equivalent of requiring MFA on sign-in and leaving password spray unthrottled.

The configuration effort for all nine policies is under three hours in a clean tenant. The blast radius of leaving them out can be your entire Microsoft 365 environment.

Root Cause — Understanding the WHY

Most CA policy sets are built reactively — a policy gets added when an incident happens or when a compliance framework asks for it. The result is a policy set optimised around the threats that were visible at the time it was built, not the current threat landscape.

Three architectural realities drive the specific gaps below:

  • User Actions are treated separately from Cloud Apps. A policy scoped to "All cloud apps" does not cover the "Register security information" User Action. These are distinct targets in the CA engine, which is why MFA registration protection requires its own explicit policies.
  • Authentication flows are opt-in conditions. Device code flow and Authentication Transfer are not blocked by default. They exist as legitimate OAuth flows, and Entra ID will happily honour them unless you explicitly target them in a CA policy. Most policy templates do not include them.
  • Token lifetime and binding are decoupled from MFA. Completing MFA at sign-in issues a token, but that token's validity and device-binding are governed separately. An attacker who steals a refresh token from a browser cache on an unmanaged machine can replay it from a different device. Token Protection addresses this by cryptographically binding the token to the issuing device — but it requires a specific CA session control that most tenants have never configured.

Understanding this architecture is what separates a policy set that looks complete from one that actually is.

The Fix — Step by Step

Policy 1 & 2: Block MFA Registration Under Any Risk Condition

If a user or their sign-in is flagged at any risk level, an attacker who has compromised that account must not be allowed to register their own authenticator. These two policies target the Register security information User Action — a target that is invisible to policies scoped to "All cloud apps".

Deploy both — one targeting User Risk (High, Medium, Low), one targeting Sign-in Risk (High, Medium, Low). Sign-in risk is evaluated in real time and catches anomalous session characteristics even before the user account itself is flagged.

# Export existing CA policies to audit for Register Security Information coverage
Connect-MgGraph -Scopes "Policy.Read.All"

$policies = Get-MgIdentityConditionalAccessPolicy
$policies | Where-Object {
    $_.Conditions.Applications.IncludeUserActions -contains "urn:user:registersecurityinfo"
} | Select-Object DisplayName, State | Format-Table -AutoSize

# If this returns nothing, you have no MFA registration protection policies.

Deploy via Graph API in report-only mode first:

# Create Policy 1: Block MFA registration for High/Medium/Low User Risk
$policyBody = @{
  displayName = "[BLOCK] MFA Registration - User Risk Any"
  state = "enabledForReportingButNotEnforced"
  conditions = @{
    users = @{ includeUsers = @("All") }
    applications = @{ includeUserActions = @("urn:user:registersecurityinfo") }
    userRiskLevels = @("high", "medium", "low")
  }
  grantControls = @{
    operator = "OR"
    builtInControls = @("block")
  }
} | ConvertTo-Json -Depth 10

Invoke-MgGraphRequest -Method POST `
  -Uri "https://graph.microsoft.com/v1.0/identity/conditionalAccess/policies" `
  -Body $policyBody -ContentType "application/json"

Policy 3: Block High Risk Users — No Self-Service Password Reset as Sole Remediation

Entra ID Protection's default template prompts high-risk users to change their password. This is insufficient. If an attacker has a valid session token, a password change does not invalidate it. Block access entirely and run remediation out-of-band via your helpdesk or an automated Sentinel playbook.

# Policy 3: Block High Risk Users entirely
$highRiskBlock = @{
  displayName = "[BLOCK] High Risk Users - All Apps"
  state = "enabledForReportingButNotEnforced"
  conditions = @{
    users = @{ includeUsers = @("All") }
    applications = @{ includeApplications = @("All") }
    userRiskLevels = @("high")
  }
  grantControls = @{
    operator = "OR"
    builtInControls = @("block")
  }
} | ConvertTo-Json -Depth 10

Invoke-MgGraphRequest -Method POST `
  -Uri "https://graph.microsoft.com/v1.0/identity/conditionalAccess/policies" `
  -Body $highRiskBlock -ContentType "application/json"

Policy 4: Block Graph API and PowerShell for Unapproved Identities

Microsoft Graph and Azure PowerShell are high-value post-compromise targets. An attacker with a valid token and Graph access can enumerate your entire directory, extract mailbox contents, or tamper with Intune configurations — all without triggering endpoint detection. Restrict these to approved identities only. See the Microsoft Learn documentation on CA cloud app targeting for app IDs.

Target App IDs: de8bc8b5-d9f9-48b1-a8ad-b748da725064 (Graph Explorer), 1950a258-227b-4e31-a9cf-717495945fc2 (Azure PowerShell), 14d82eec-204b-4c2f-b7e8-296a70dab67e (Graph PowerShell SDK). Scope exclusions to a dedicated group containing only break-glass accounts and approved service principals.

Policy 5: Require Phishing-Resistant MFA for Admin Portals

Standard push MFA is not sufficient for privileged access. FIDO2 keys and Windows Hello for Business eliminate real-time phishing and MFA fatigue vectors entirely. Use the built-in Authentication Strength feature rather than a simple MFA grant — it lets you mandate specific authenticator types. Target both Microsoft Admin Portals and the Windows Azure Service Management API (797f4846-ba00-4fd7-ba43-dac1f8f63013).

# Verify your Authentication Strength policies
Invoke-MgGraphRequest -Method GET `
  -Uri "https://graph.microsoft.com/v1.0/policies/authenticationStrengthPolicies" `
  | Select-Object -ExpandProperty value `
  | Select-Object displayName, policyType | Format-Table -AutoSize

# Look for "Phishing-resistant MFA" in the output.
# If only "MFA" and "Passwordless MFA" appear, the phishing-resistant strength
# policy exists as a built-in — confirm its ID before referencing it in CA.

Policy 6: Block Device Code Flow

Device code flow is the OAuth flow designed for input-constrained devices like smart TVs. It has been weaponised extensively in phishing campaigns: the attacker generates a device code, sends it to the target, and when the user enters it they authorise the attacker's session. Block it unless you have a documented, audited business requirement. This is the lowest-disruption, highest-impact block on this list. See the Microsoft documentation on authentication flow conditions.

# Policy 6: Block Device Code Flow
$deviceCodeBlock = @{
  displayName = "[BLOCK] Device Code Flow - All Users"
  state = "enabledForReportingButNotEnforced"
  conditions = @{
    users = @{ includeUsers = @("All") }
    applications = @{ includeApplications = @("All") }
    authenticationFlows = @{ transferMethods = "deviceCodeFlow" }
  }
  grantControls = @{
    operator = "OR"
    builtInControls = @("block")
  }
} | ConvertTo-Json -Depth 10

Invoke-MgGraphRequest -Method POST `
  -Uri "https://graph.microsoft.com/v1.0/identity/conditionalAccess/policies" `
  -Body $deviceCodeBlock -ContentType "application/json"

Policy 7: Block Authentication Transfer

Authentication Transfer allows a session authenticated on one device to transfer to another via QR code or link. It is a newer flow and already flagged as a potential attack surface. Block it proactively. The risk profile is identical to device code — high theoretical abuse potential, near-zero legitimate enterprise use.

Configure identically to Policy 6 but set transferMethods to authenticationTransfer.

Policy 8: Require Compliant Devices or PAWs for Admin Roles

Privileged tasks must originate from known, hardened devices. Privileged Access Workstations (PAWs) are the gold standard — dedicated machines used only for admin work with no general internet access. If PAWs are not yet scoped, requiring Intune device compliance is a meaningful minimum. Combine this with Policy 5 for layered protection: phishing-resistant MFA from a compliant dedicated device is materially stronger than either control alone.

Policy 9: Enforce Token Protection

Token theft is the most effective post-MFA attack technique in active use. An attacker who captures a refresh token from an unmanaged device can replay it from a different machine without re-authenticating. Token Protection binds tokens cryptographically to the issuing device, making stolen tokens useless elsewhere. Configure it under Session controls.

# Policy 9: Require Token Protection for Exchange and SharePoint
$tokenProtection = @{
  displayName = "[SESSION] Token Protection - Exchange and SharePoint"
  state = "enabledForReportingButNotEnforced"
  conditions = @{
    users = @{ includeUsers = @("All") }
    applications = @{
      includeApplications = @(
        "00000002-0000-0ff1-ce00-000000000000",  # Exchange Online
        "00000003-0000-0ff1-ce00-000000000000"   # SharePoint Online
      )
    }
  }
  sessionControls = @{
    secureSignInSession = @{ isEnabled = $true }
  }
} | ConvertTo-Json -Depth 10

Invoke-MgGraphRequest -Method POST `
  -Uri "https://graph.microsoft.com/v1.0/identity/conditionalAccess/policies" `
  -Body $tokenProtection -ContentType "application/json"

Token Protection requires compliant Windows devices. Ensure your device compliance baseline is solid before enforcing — report-only mode is not optional here, it is mandatory until you have validated device coverage.

Verification & Monitoring at Scale

Deploying policies in report-only is only useful if you actually review the data. Use the Conditional Access Insights workbook in the Entra admin centre, and supplement it with direct Log Analytics queries if you have Entra diagnostic logs forwarded.

# Query Sign-in Logs for Report-Only policy hits on MFA Registration
# Run in Log Analytics workspace connected to Entra diagnostic logs

SigninLogs
| where TimeGenerated > ago(7d)
| where ConditionalAccessStatus == "reportOnly"
| mv-expand ConditionalAccessPolicies
| where ConditionalAccessPolicies.displayName contains "MFA Registration"
| where ConditionalAccessPolicies.result == "reportOnlyFailure"
| summarize HitCount = count() by UserPrincipalName, AppDisplayName, IPAddress
| order by HitCount desc
# Audit all CA policies for Device Code Flow condition
$policies = Invoke-MgGraphRequest -Method GET `
  -Uri "https://graph.microsoft.com/v1.0/identity/conditionalAccess/policies"

$policies.value | ForEach-Object {
  $p = $_
  if ($p.conditions.authenticationFlows) {
    [PSCustomObject]@{
      PolicyName = $p.displayName
      State      = $p.state
      Flows      = $p.conditions.authenticationFlows.transferMethods
    }
  }
} | Format-Table -AutoSize

Run the second script in every tenant you manage as part of a monthly CA audit. If it returns nothing, device code flow and authentication transfer are unblocked.

Lessons Learned & Gotchas

Break-glass accounts need careful exclusion management. Every one of these policies needs your break-glass accounts excluded — but those exclusions must be documented, reviewed quarterly, and tied to a named group that is itself monitored for membership changes. An undocumented exclusion is a future attack path.

Token Protection will fail on non-compliant devices. We enforced Token Protection on Exchange before confirming device compliance coverage and locked out a significant number of users on BYOD devices. Always validate compliance coverage in report-only before enforcing. The Intune device compliance report is not a reliable proxy — check the CA insights workbook directly.

The "Register security information" User Action is invisible in the standard policy list. When reviewing existing policies, filter specifically for User Actions in the conditions. Teams routinely audit cloud app coverage and miss this target entirely because it does not appear in the app dropdown — it is a separate configuration path in the CA conditions blade.

Sign-in risk and user risk fire on different timelines. User risk is cumulative and updated periodically. Sign-in risk is evaluated in real time at each authentication attempt. Both Policies 1 and 2 are needed because an attacker operating under a freshly compromised account may have a clean user risk score but still trigger sign-in risk signals — atypical travel, anonymous IP, token anomaly.

Do not use the default Entra ID Protection "require password change" template as your high-risk response. We have seen tenants disable our block-high-risk policy in favour of the built-in template because it felt less disruptive. It is less disruptive because it is less secure. Session tokens are not invalidated by password changes. Block and investigate.

Quick-Reference Checklist

  • Prerequisites: Entra ID P2 (for risk-based conditions and Token Protection), Microsoft Graph PowerShell SDK installed, break-glass accounts identified and documented
  • Export current CA policies and grep for urn:user:registersecurityinfo — if absent, Policies 1 and 2 are missing
  • Run authentication flow audit script — if no results, Policies 6 and 7 are missing
  • Confirm Authentication Strength policy exists with phishing-resistant MFA definition before deploying Policy 5
  • Deploy all new policies in report-only mode initially
  • Review CA Insights workbook after 5–7 days of report-only data before enforcing
  • Enforce in risk order: device code flow and authentication transfer first (lowest disruption), then risk-based registration blocks, then token protection
  • Validate Token Protection device compliance coverage before enforcing Policy 9
  • Document every exclusion with owner, justification, and review date
  • Schedule quarterly CA policy audit — use the Graph API audit script as the baseline check
  • Rollback: Set policy state to disabled via Graph or the Entra admin centre. Do not delete policies during rollback — preserve the configuration for review.

🎓 Ready to go deeper?

Practice real MD-102 exam questions, get AI feedback on your weak areas, and fast-track your Intune certification.

Start Free Practice → Book a Session
Souhaiel Morhag
Souhaiel Morhag
Microsoft Endpoint & Modern Workplace Engineer

Souhaiel Morhag is a Microsoft Intune and endpoint management specialist with hands-on experience deploying and securing enterprise environments across Microsoft 365. He founded MSEndpoint.com to share practical, real-world guides for IT admins navigating Microsoft technologies — and built the MSEndpoint Academy at app.msendpoint.com/academy, a dedicated learning platform for professionals preparing for the MD-102 (Microsoft 365 Endpoint Administrator) certification. Through in-depth articles and AI-powered practice exams, Souhaiel helps IT teams move faster and certify with confidence.

Related Articles

Popular on MSEndpoint