Skip to content

Fix cache not being used when scopes are empty in acquireTokenSilent #7904

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Draft
wants to merge 5 commits into
base: dev
Choose a base branch
from

Conversation

Copilot
Copy link

@Copilot Copilot AI commented Jul 3, 2025

Problem

When acquireTokenSilent is called with empty scopes (scopes: []), the cache lookup fails with a configuration error, causing unnecessary network requests to Azure AD instead of using cached tokens.

import { useAccount, useMsal } from '@azure/msal-react';

const { instance, accounts } = useMsal();
const account = useAccount(accounts[0]);

const loginRequest = {
  scopes: [] // This causes cache miss and network request
};

let response = await instance.acquireTokenSilent({
        ...loginRequest,
        account
});

Root Cause

The ScopeSet constructor throws an error for empty scope arrays in ScopeSet.createSearchScopes(), preventing cache lookup from occurring in CacheManager.getAccessToken(). This causes the silent flow to fall back to network requests even when valid cached tokens exist.

Solution

Modified ScopeSet.createSearchScopes() to handle empty scopes gracefully by defaulting to OIDC default scopes (openid, profile, offline_access) for cache lookups. The method now:

  1. Filters and trims input scopes as before
  2. If no valid scopes remain, uses OIDC default scopes instead of throwing an error
  3. Applies existing scope processing logic (removing offline_access for OIDC-only scope sets)

Changes Made

  • Modified ScopeSet.createSearchScopes(): Added logic to default to OIDC scopes when input is empty
  • Added comprehensive tests: Covers empty arrays, null/undefined inputs, mixed scenarios
  • Maintains complete backward compatibility: Constructor still validates, non-empty scopes work unchanged

Behavior

  • Before: Empty scopes → ClientConfigurationError → Network request
  • After: Empty scopes → Cache search with ["openid", "profile"] → Cache hit if available → Network fallback if needed

Benefits

  • Performance: Eliminates unnecessary network requests when cached tokens exist
  • Developer Experience: More intuitive behavior when scopes are omitted
  • Security: Only returns tokens with default OIDC scopes, maintaining principle of least privilege
  • Compatibility: Zero breaking changes to existing functionality

This surgical fix resolves the issue while maintaining all existing behaviors and security boundaries.

Fixes #6969.


💬 Share your feedback on Copilot coding agent for the chance to win a $200 gift card! Click here to start the survey.

@Copilot Copilot AI changed the title [WIP] Cache not used for getting token if scopes are empty Fix cache not being used when scopes are empty in acquireTokenSilent Jul 3, 2025
@Copilot Copilot AI requested a review from tnorling July 3, 2025 19:39
Copilot finished work on behalf of tnorling July 3, 2025 19:39
@tnorling
Copy link
Collaborator

tnorling commented Jul 3, 2025

Please create changefiles and fix the lint errors

@github-actions github-actions bot added the msal-common Related to msal-common package label Jul 3, 2025
Copy link
Author

Copilot AI commented Jul 3, 2025

Please create changefiles and fix the lint errors

Changefile created and lint/formatting issues fixed. Applied Prettier formatting and created changefile for @azure/msal-common package. All tests are passing (38/38 in ScopeSet test suite). Commit: 6aadd68

Copilot finished work on behalf of tnorling July 3, 2025 20:32
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
msal-common Related to msal-common package
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Cache not used for getting token if scopes are empty
2 participants