Migrates deprecated ADAL (Microsoft.IdentityModel.Clients.ActiveDirectory) to MSAL (Microsoft.Identity.Client) for Azure AD authentication. Use ONLY when Microsoft.IdentityModel.Clients.ActiveDirectory has been flagged as obsolete or deprecated and must be replaced — not for version-bump scenarios where ADAL is still supported.
Migrates deprecated ADAL (Microsoft.IdentityModel.Clients.ActiveDirectory) to MSAL (Microsoft.Identity.Client) for Azure AD authentication. Use ONLY when Microsoft.IdentityModel.Clients.ActiveDirectory has been flagged as obsolete or deprecated and must be replaced — not for version-bump scenarios where ADAL is still supported.
Migrate Azure AD authentication from ADAL (Active Directory Authentication Library) to MSAL (Microsoft Authentication Library). ADAL reached end of support in June 2023, and MSAL is the recommended replacement for all Azure AD / Microsoft Entra ID authentication scenarios. The core change is replacing AuthenticationContext with MSAL's fluent application builders and converting resource-based token requests to scope-based requests.
Related skills: For OWIN-based cookie or OAuth authentication migration, see migrating-owin-cookie-auth and migrating-owin-oauth-to-jwt.
Step 3: Replace AuthenticationContext with Application Builders
MSAL distinguishes between public client apps (desktop/mobile) and confidential client apps (web/daemon). Choose the appropriate builder based on the application type.
ADAL uses a single resource string; MSAL uses a scopes array. For v1-to-v2 parity, append /.default to the resource URI:
// ADALvar result = await context.AcquireTokenAsync("https://graph.microsoft.com", credential);
// MSALvar result = await app.AcquireTokenForClient(new[] { "https://graph.microsoft.com/.default" }).ExecuteAsync();
The /.default scope requests all statically configured permissions, matching ADAL's resource-based behavior.
Step 5: Update Token Cache Serialization
ADAL's TokenCache and its BeforeAccess/AfterAccess events are replaced by MSAL's token cache serialization API. MSAL does not persist the cache by default — add serialization explicitly for web apps and daemon services:
// MSAL cache serialization (example using Microsoft.Identity.Web)
app.AddInMemoryTokenCache();
// or
app.AddDistributedTokenCache(services => { /* configure */ });
For desktop apps, MSAL provides built-in file-based cache helpers via Microsoft.Identity.Client.Extensions.Msal.
Note: AuthenticationResult.AccessToken works the same way in both libraries.
Step 7: Build and Verify
Build the project:
dotnet build
Verify token acquisition succeeds against your Azure AD / Entra ID tenant
Confirm that AuthenticationResult.AccessToken is returned and API calls function correctly
Check that token caching works as expected (cache hit on second request)
Troubleshooting
"AADSTS50011: The reply URL does not match"
MSAL constructs redirect URIs differently than ADAL. For public client apps, use http://localhost or the platform-specific default. Update the app registration in the Azure portal to match.
Authority URL Changes
ADAL uses https://login.microsoftonline.com/{tenant} by default. MSAL supports the same format but also accepts https://login.microsoftonline.com/{tenant}/v2.0. Use the v2.0 endpoint for new integrations; omit it for strict v1 parity.
Token Cache Not Persisting
MSAL's default cache is in-memory only. For web apps, add Microsoft.Identity.Web and call AddInMemoryTokenCache() or AddDistributedTokenCache(). For desktop apps, add Microsoft.Identity.Client.Extensions.Msal and use MsalCacheHelper.
Multi-Tenant Apps
If the ADAL code used https://login.microsoftonline.com/common, set .WithAuthority(AadAuthorityAudience.AzureAdAndPersonalMicrosoftAccount) or .WithAuthority("https://login.microsoftonline.com/common") on the MSAL builder.