๐ก๏ธ Recipe ยท Security & Compliance
Identify Users Signing In with SMS-Based Authentication
Find every user who authenticated via SMS (text-message MFA) in the last 30 days and flag them for migration to phishing-resistant methods.
Complexity
Intermediate
Impact
security + compliance + identity + mfa + audit
Context
Why This Matters
SMS-based multi-factor authentication is widely deployed but is the weakest of the supported MFA methods. It is vulnerable to SIM-swap attacks, SS7 interception, smishing, and telecom-provider compromise. Microsoft, CISA, and NIST SP 800-63B all recommend migrating away from SMS/voice OTP toward phishing-resistant methods like FIDO2 security keys, Windows Hello for Business, certificate-based auth, or โ at minimum โ the Microsoft Authenticator app with number matching.
Before you can migrate users off SMS, you need to know who is actually using it. Run this recipe when you are:
- Planning a rollout of the Authentication Methods policy to disable SMS tenant-wide.
- Performing a quarterly MFA hygiene audit.
- Responding to a compliance requirement (PCI DSS 4.0, HIPAA, CMMC, cyber-insurance questionnaire) that asks for evidence of strong-factor adoption.
- Investigating a SIM-swap or account-takeover incident and need to scope which accounts are exposed.
The recipe combines two data sources for a complete picture: the userRegistrationDetails report (who has SMS registered) and the Entra sign-in logs (who has actually used SMS in the last 30 days).
Expected Outcomes
When you finish, you will have:
- A CSV list of every user who has SMS/text-message configured as an authentication method.
- A second CSV of users who actually completed an SMS MFA challenge in the last 30 days, with the date of their most recent SMS sign-in and a count of SMS challenges.
- A clear view of how much SMS usage exists in your tenant (often far less than admins expect once Authenticator and Windows Hello are deployed).
- A targeted migration list you can hand to your helpdesk or campaign tool to move users onto Authenticator, FIDO2, or passkeys.
- Evidence you can attach to an audit or compliance report.
Risks & Considerations
Gotchas and caveats
- Property name differences. The sign-in log resource uses
userDisplayName, notdisplayName. TheauthenticationDetailsproperty is only available on the beta Graph endpoint โ it is not selectable fromv1.0. - No server-side filter for SMS. You cannot use
$filteronauthenticationDetails/authenticationMethod. You must fetch sign-ins for the window and filter client-side. For busy tenants this can mean tens of thousands of records. - Performance. A 30-day scan of a mid-size tenant can easily exceed 100k sign-in events. Always page with
$top=999, follow@odata.nextLink, and consider narrowing the window (7 or 14 days) if runs are timing out. - Registered โ used.
userRegistrationDetailstells you who can use SMS, not who did. Cross-reference with sign-in logs for actual usage. - "Previously satisfied" noise. Many sign-ins show
authenticationMethod: "Previously satisfied"because the MFA claim was cached. Those are not SMS events โ only count entries where the method explicitly contains "SMS" or "Text". - Log retention. Entra sign-in logs are retained 7 days on free tenants, 30 days on Entra ID P1/P2. If you need longer history, ship logs to Log Analytics or a SIEM.
- Do not disable SMS tenant-wide before migrating users. Pulling SMS before users have registered an alternate method will lock them out.
Required Permissions
| Permission | Why It's Needed |
|---|---|
| AuditLog.Read.All | Read sign-in logs to detect which users completed an SMS MFA challenge. |
| UserAuthenticationMethod.Read.All | Enumerate each user's registered authentication methods (phone/SMS). |
| Reports.Read.All | Read the authenticationMethods user registration details report. |
| Directory.Read.All | Resolve user display names and UPNs referenced in sign-in events. |
The fastest way to get this done: just ask Dex. Copy the prompt below and paste it into your Dex conversation.
For IT Admins
Paste into Dex Pro
Identify SMS users from the Entra admin center
This GUI path works for spot checks and small tenants. For tenant-wide reporting, use the API or PowerShell approach.
Part A โ Who has SMS registered
- Sign in to the Microsoft Entra admin center as a Global Reader or Authentication Policy Administrator.
- Navigate to .
- Select the Registration tab. The chart at the top shows the count of users registered by method.
- Scroll to the Users registered by method table. Look for the row labelled
SMS(sometimes shown asPhone (SMS)orMobile phone). - Click the SMS row to drill into the list of users. Use Download to export the list as CSV.
Part B โ Who actually used SMS in the last 30 days
- Still in the Entra admin center, go to .
- Click Add filters and add the Authentication requirement filter set to Multi-factor authentication.
- Set the date range to Last 30 days.
- Click any sign-in entry, open the Authentication Details tab, and confirm the Authentication method column. You are looking for rows where it reads
SMS,Text message, orPhone (SMS). - Because the GUI does not filter on authentication method directly, click Download > JSON (or CSV) to export the visible window and filter in Excel/Power Query:
authenticationDetails[].authenticationMethod contains "SMS". - De-duplicate by User principal name to produce your final list.
Part C โ Act on the list
- Email affected users with instructions to register the Microsoft Authenticator app (or a FIDO2 key).
- Once migration is complete, go to and disable SMS for the migrated group.
Identify SMS users with Microsoft Graph
Two endpoints are involved. The first is a fast pre-aggregated report; the second is the raw sign-in log you scan for actual SMS challenges.
1. Pull the registration report (fast, pre-aggregated)
GET https://graph.microsoft.com/beta/reports/authenticationMethods/userRegistrationDetails?$top=999
Authorization: Bearer {token}Page through @odata.nextLink and keep any user whose methodsRegistered array contains a value starting with sms or mobilePhone. Sample response:
{
"value": [
{
"id": "6fe78db5-dfbf-4565-ab38-dbfbd3ca5daa",
"userPrincipalName": "jdoe@contoso.com",
"userDisplayName": "Jane Doe",
"methodsRegistered": ["mobilePhone", "microsoftAuthenticatorPush"],
"isMfaRegistered": true,
"isSsprRegistered": true
}
]
}2. Scan sign-in logs for actual SMS challenges (last 30 days)
The authenticationDetails property is only available on the beta endpoint. You cannot filter on it server-side, so filter by date and process client-side.
GET https://graph.microsoft.com/beta/auditLogs/signIns
?$filter=createdDateTime ge 2025-10-01T00:00:00Z
&$top=999For each sign-in, inspect the authenticationDetails array:
{
"userPrincipalName": "jdoe@contoso.com",
"userDisplayName": "Jane Doe",
"createdDateTime": "2025-10-14T18:22:10Z",
"authenticationDetails": [
{
"authenticationMethod": "SMS",
"authenticationMethodDetail": "+1 XXX-XXX-1234",
"succeeded": true,
"authenticationStepRequirement": "Primary authentication"
}
]
}A sign-in counts as SMS when any element of authenticationDetails has authenticationMethod equal to SMS (case-insensitive) or authenticationMethodDetail containing "SMS" or "Text message". Ignore entries where the method is "Previously satisfied" โ those are cached MFA claims.
3. Aggregate
Group the matching events by userPrincipalName and record the latest createdDateTime and a count. This produces the "used SMS in the last 30 days" list that you join against the registration report.
Pagination note: follow @odata.nextLink until it is absent. For busy tenants, consider narrowing to 7-day windows and running multiple passes to stay under request timeouts.
Run the audit from PowerShell
The script uses the Microsoft.Graph SDK. Install it once with Install-Module Microsoft.Graph -Scope CurrentUser. The recipe pulls both the registration report and the sign-in log scan, joins them, and writes two CSVs to disk.
- Connect with the required scopes:
AuditLog.Read.All,UserAuthenticationMethod.Read.All,Reports.Read.All,Directory.Read.All. - Pull the registration report from
/beta/reports/authenticationMethods/userRegistrationDetailsand filter wheremethodsRegisteredcontainssmsormobilePhone. - Page the sign-in log for the last N days (default 30). For each event, inspect
authenticationDetailsand count it as SMS whenauthenticationMethod -match 'SMS'orauthenticationMethodDetail -match 'SMS|Text'. - Aggregate per user (last-seen date, count of SMS challenges).
- Export
sms-registered.csvandsms-used-last-Nd.csvfor review.
On a tenant of a few hundred users this runs in seconds. On larger tenants with heavy sign-in traffic, reduce -Days to 7 or 14, or run the sign-in scan during off-hours.
Next steps