{
  "title": "How to Automate Compliance for NIST SP 800-171 REV.2 / CMMC 2.0 Level 2 - Control - IA.L2-3.5.6 Using Azure AD and Conditional Access to Disable Inactive Identifiers",
  "date": "2026-04-16",
  "author": "Lakeridge Technologies",
  "featured_image": "/assets/images/blog/2026/4/how-to-automate-compliance-for-nist-sp-800-171-rev2-cmmc-20-level-2-control-ial2-356-using-azure-ad-and-conditional-access-to-disable-inactive-identifiers.jpg",
  "content": {
    "full_html": "<p>NIST SP 800-171 / CMMC 2.0 IA.L2-3.5.6 requires organizations to disable inactive identifiers to reduce the risk of unauthorized access from stale or orphaned accounts; this post explains a practical, automated approach using Azure AD (Microsoft Entra) and Conditional Access, with step-by-step options for small businesses to detect, quarantine, and disable inactive users while keeping auditors satisfied.</p>\n\n<h2>Why disabling inactive identifiers matters for Compliance Framework</h2>\n<p>Inactive accounts (former employees, contractors, orphaned service accounts) are a common attack vector — credentials can be re-used or compromised long after the owner stops using them. For Compliance Framework requirements such as IA.L2-3.5.6, you must show technical controls and repeatable processes to identify inactivity and remove access. Automation reduces human error, creates auditable logs, and provides the evidence auditors expect.</p>\n\n<h2>High-level implementation overview</h2>\n<p>The recommended pattern is: (1) collect sign-in telemetry, (2) run periodic detection to flag accounts with last-sign-in older than the organizational threshold, (3) add flagged accounts to a quarantine group, (4) apply Conditional Access or directly disable the accounts after an approval or notification window, and (5) log actions for audit. You can implement detection using Azure AD sign-in logs (Kusto queries in Log Analytics) or Microsoft Graph (signInActivity), and action via Microsoft Graph PowerShell, Logic Apps, or Azure Functions.</p>\n\n<h3>Prerequisites and platform considerations</h3>\n<p>Licensing and telemetry setup matter: Conditional Access requires Azure AD Premium P1; Access Reviews and entitlement governance require P2 if you want review-based removal workflows. To use sign-in logs in Log Analytics you must enable Diagnostic Settings to stream AuditLogs and SigninLogs to a Log Analytics workspace. Microsoft Graph's user signInActivity property is available in beta and requires AuditLog permissions. Also identify and exclude break-glass/emergency accounts and service principals — those must be handled by a separate documented process.</p>\n\n<h3>Detecting inactivity — practical queries and scripts</h3>\n<p>Two common detection approaches: (A) Kusto query against SigninLogs in Log Analytics: <code>SigninLogs | summarize LastSignIn = max(TimeGenerated) by UserPrincipalName | where LastSignIn < ago(60d)</code> — this returns users with no sign-ins in the last 60 days. (B) Microsoft Graph (beta) signInActivity: call <code>GET /users?$select=id,displayName,userPrincipalName,signInActivity</code>, then filter where <code>signInActivity.lastSignInDateTime</code> is older than your threshold or null. For automation, run these queries daily in an Azure Logic App, Azure Function, or runbook and capture the result set to feed into your action workflow.</p>\n\n<h3>Actioning disables with Conditional Access and Graph automation</h3>\n<p>There are two safe operational patterns: (1) use a quarantine Azure AD group and a Conditional Access policy that blocks sign-in for members of that group; (2) automatically disable the account directly via Microsoft Graph (set <code>accountEnabled</code> to <code>false</code>). Pattern (1) is reversible and auditable — create a group (e.g., <code>quarantine-inactive-identifiers</code>), have your automation add users to it, and a Conditional Access policy scoped to that group that blocks all cloud app sign-ins (put policy into \"Report-only\" first). Pattern (2) is cleaner but more disruptive and should include an automated notification and manager approval window. Example Graph PowerShell steps (simplified): <code>Connect-MgGraph -Scopes \"User.ReadWrite.All\"</code>; retrieve stale users; <code>Update-MgUser -UserId &lt;id&gt; -AccountEnabled:$false</code>. Always log who/what process performed the change with timestamps for audit.</p>\n\n<h2>Small business real-world scenario</h2>\n<p>Example: a 50-person small business sets policy: contractors disabled after 30 days inactivity, employees after 90 days. Implementation: stream SignInLogs to Log Analytics, run daily Kusto query to find inactive users, push matches to an Azure Logic App that (a) emails the manager with a 7-day notice, (b) if no response, adds the user to <code>quarantine-inactive-identifiers</code>. A Conditional Access policy blocks sign-in for that group. After 30 more days in quarantine, the Logic App calls Graph to set <code>accountEnabled</code> to <code>false</code>. All actions are logged to a storage account and an Azure Monitor workbook for auditors.</p>\n\n<h2>Compliance tips and best practices</h2>\n<p>Do these to strengthen your control and audit posture: maintain a written inactivity policy (define thresholds by identity class), keep an exceptions register for service and break-glass accounts, test automation in a non-production tenant or with a small pilot group, use role-based approvals (manager or identity owner), retain logs for the period required by Compliance Framework rules, and enforce separation of duties so the person who approves disablement is different from the automation operator. Use Conditional Access \"Report-only\" mode first to validate impact.</p>\n\n<h2>Risks of not implementing automated disables</h2>\n<p>Without automated disabling of inactive identifiers you increase exposure to credential reuse, lateral movement, and insider threat risk. For CMMC / NIST auditors, lacking a demonstrable, repeatable process can lead to findings or failed assessments, which can affect contract eligibility. Operational risks include unauthorized data access, regulatory penalties, and the operational cost of incident response and remediation after an account compromise.</p>\n\n<p>In summary, implementing IA.L2-3.5.6 using Azure AD and Conditional Access is a practical, automatable control that reduces risk and satisfies Compliance Framework expectations: stream sign-in telemetry, detect inactivity with Kusto or Graph, quarantine via group + Conditional Access or directly disable accounts using Microsoft Graph, and ensure manager notifications, logging, and exception handling are in place — start small, test carefully, and document every step for auditors.</p>",
    "plain_text": "NIST SP 800-171 / CMMC 2.0 IA.L2-3.5.6 requires organizations to disable inactive identifiers to reduce the risk of unauthorized access from stale or orphaned accounts; this post explains a practical, automated approach using Azure AD (Microsoft Entra) and Conditional Access, with step-by-step options for small businesses to detect, quarantine, and disable inactive users while keeping auditors satisfied.\n\nWhy disabling inactive identifiers matters for Compliance Framework\nInactive accounts (former employees, contractors, orphaned service accounts) are a common attack vector — credentials can be re-used or compromised long after the owner stops using them. For Compliance Framework requirements such as IA.L2-3.5.6, you must show technical controls and repeatable processes to identify inactivity and remove access. Automation reduces human error, creates auditable logs, and provides the evidence auditors expect.\n\nHigh-level implementation overview\nThe recommended pattern is: (1) collect sign-in telemetry, (2) run periodic detection to flag accounts with last-sign-in older than the organizational threshold, (3) add flagged accounts to a quarantine group, (4) apply Conditional Access or directly disable the accounts after an approval or notification window, and (5) log actions for audit. You can implement detection using Azure AD sign-in logs (Kusto queries in Log Analytics) or Microsoft Graph (signInActivity), and action via Microsoft Graph PowerShell, Logic Apps, or Azure Functions.\n\nPrerequisites and platform considerations\nLicensing and telemetry setup matter: Conditional Access requires Azure AD Premium P1; Access Reviews and entitlement governance require P2 if you want review-based removal workflows. To use sign-in logs in Log Analytics you must enable Diagnostic Settings to stream AuditLogs and SigninLogs to a Log Analytics workspace. Microsoft Graph's user signInActivity property is available in beta and requires AuditLog permissions. Also identify and exclude break-glass/emergency accounts and service principals — those must be handled by a separate documented process.\n\nDetecting inactivity — practical queries and scripts\nTwo common detection approaches: (A) Kusto query against SigninLogs in Log Analytics: SigninLogs | summarize LastSignIn = max(TimeGenerated) by UserPrincipalName | where LastSignIn  — this returns users with no sign-ins in the last 60 days. (B) Microsoft Graph (beta) signInActivity: call GET /users?$select=id,displayName,userPrincipalName,signInActivity, then filter where signInActivity.lastSignInDateTime is older than your threshold or null. For automation, run these queries daily in an Azure Logic App, Azure Function, or runbook and capture the result set to feed into your action workflow.\n\nActioning disables with Conditional Access and Graph automation\nThere are two safe operational patterns: (1) use a quarantine Azure AD group and a Conditional Access policy that blocks sign-in for members of that group; (2) automatically disable the account directly via Microsoft Graph (set accountEnabled to false). Pattern (1) is reversible and auditable — create a group (e.g., quarantine-inactive-identifiers), have your automation add users to it, and a Conditional Access policy scoped to that group that blocks all cloud app sign-ins (put policy into \"Report-only\" first). Pattern (2) is cleaner but more disruptive and should include an automated notification and manager approval window. Example Graph PowerShell steps (simplified): Connect-MgGraph -Scopes \"User.ReadWrite.All\"; retrieve stale users; Update-MgUser -UserId &lt;id&gt; -AccountEnabled:$false. Always log who/what process performed the change with timestamps for audit.\n\nSmall business real-world scenario\nExample: a 50-person small business sets policy: contractors disabled after 30 days inactivity, employees after 90 days. Implementation: stream SignInLogs to Log Analytics, run daily Kusto query to find inactive users, push matches to an Azure Logic App that (a) emails the manager with a 7-day notice, (b) if no response, adds the user to quarantine-inactive-identifiers. A Conditional Access policy blocks sign-in for that group. After 30 more days in quarantine, the Logic App calls Graph to set accountEnabled to false. All actions are logged to a storage account and an Azure Monitor workbook for auditors.\n\nCompliance tips and best practices\nDo these to strengthen your control and audit posture: maintain a written inactivity policy (define thresholds by identity class), keep an exceptions register for service and break-glass accounts, test automation in a non-production tenant or with a small pilot group, use role-based approvals (manager or identity owner), retain logs for the period required by Compliance Framework rules, and enforce separation of duties so the person who approves disablement is different from the automation operator. Use Conditional Access \"Report-only\" mode first to validate impact.\n\nRisks of not implementing automated disables\nWithout automated disabling of inactive identifiers you increase exposure to credential reuse, lateral movement, and insider threat risk. For CMMC / NIST auditors, lacking a demonstrable, repeatable process can lead to findings or failed assessments, which can affect contract eligibility. Operational risks include unauthorized data access, regulatory penalties, and the operational cost of incident response and remediation after an account compromise.\n\nIn summary, implementing IA.L2-3.5.6 using Azure AD and Conditional Access is a practical, automatable control that reduces risk and satisfies Compliance Framework expectations: stream sign-in telemetry, detect inactivity with Kusto or Graph, quarantine via group + Conditional Access or directly disable accounts using Microsoft Graph, and ensure manager notifications, logging, and exception handling are in place — start small, test carefully, and document every step for auditors."
  },
  "metadata": {
    "description": "Practical guide to automating IA.L2-3.5.6 (disable inactive identifiers) using Azure AD, Microsoft Graph, Conditional Access, and automation to meet NIST SP 800-171 / CMMC 2.0 Level 2 requirements.",
    "permalink": "/how-to-automate-compliance-for-nist-sp-800-171-rev2-cmmc-20-level-2-control-ial2-356-using-azure-ad-and-conditional-access-to-disable-inactive-identifiers.json",
    "categories": [],
    "tags": []
  }
}