Unignore mTLS PoP test for non-tenanted authority#5853
Conversation
There was a problem hiding this comment.
Pull request overview
This PR re-enables an mTLS PoP unit test that was previously ignored, aiming to start enforcing expected behavior for non-tenanted AAD authorities (e.g., /common, /organizations) in mTLS PoP scenarios.
Changes:
- Removed the
[Ignore]attribute fromMtlsPop_WithUnsupportedNonTenantedAuthorityAsync_ThrowsException.
Comments suppressed due to low confidence (1)
tests/Microsoft.Identity.Test.Unit/PublicApiTests/MtlsPopTests.cs:573
- Re-enabling this test will currently fail because the product code does not appear to throw
MsalError.MissingTenantedAuthority(or useMsalErrorMessage.MtlsNonTenantedAuthorityNotAllowedMessage) anywhere in the mTLS PoP path. A repo-wide search showsMissingTenantedAuthorityis only defined inMsalError.csand never thrown, and the non-tenanted mTLS message is only defined inMsalErrorMessage.csand never referenced.
Either (a) re-add the [Ignore] until the production validation is implemented, or (b) add validation for mTLS PoP requests against AAD authorities that target /common or /organizations (and likely other tenantless audiences) and throw MsalClientException(MsalError.MissingTenantedAuthority, MsalErrorMessage.MtlsNonTenantedAuthorityNotAllowedMessage) before any network calls.
[TestMethod]
[DataRow("https://login.microsoftonline.com", TestConstants.Common, "Public Cloud")]
[DataRow("https://login.microsoftonline.com", TestConstants.Organizations, "Public Cloud")]
[DataRow("https://login.microsoftonline.us", TestConstants.Common, "Azure Government")]
[DataRow("https://login.microsoftonline.us", TestConstants.Organizations, "Azure Government")]
You can also share your feedback on Copilot code review. Take the survey.
There was a problem hiding this comment.
Pull request overview
This PR restores/ensures correct behavior for explicit mTLS PoP requests against non-tenanted AAD authorities (/common, /organizations, /consumers) by failing early with MsalError.MissingTenantedAuthority, and re-enables the unit test validating that behavior.
Changes:
- Added early AAD-only validation in
MtlsPopParametersInitializerto throwMissingTenantedAuthorityfor non-tenanted authorities before region checks / HTTP. - Removed
[Ignore]fromMtlsPop_WithUnsupportedNonTenantedAuthorityAsync_ThrowsExceptionso the test runs again. - Updated the “without region” test setup to build the app with a tenanted authority.
Reviewed changes
Copilot reviewed 2 out of 2 changed files in this pull request and generated 1 comment.
| File | Description |
|---|---|
| tests/Microsoft.Identity.Test.Unit/PublicApiTests/MtlsPopTests.cs | Re-enables the non-tenanted authority mTLS PoP test and tweaks region-related tests to use a tenanted authority. |
| src/client/Microsoft.Identity.Client/ApiConfig/Parameters/MtlsPopParametersInitializer.cs | Adds early tenant validation for explicit mTLS PoP on AAD authorities and keeps region validation centralized. |
You can also share your feedback on Copilot code review. Take the survey.
tests/Microsoft.Identity.Test.Unit/PublicApiTests/MtlsPopTests.cs
Outdated
Show resolved
Hide resolved
809ce25 to
7ea136d
Compare
| MsalErrorMessage.MtlsNonTenantedAuthorityNotAllowedMessage); | ||
| } | ||
|
|
||
| if (serviceBundle.Config.AzureRegion == null) |
There was a problem hiding this comment.
I believe Entra does actually support this. There is a global mtls endpoint.
There was a problem hiding this comment.
To keep scope tight, this change is only validating that the authority is tenanted (and rejecting common/consumer authorities).
If we want to support the global mTLS endpoint by removing the regional checks, I can follow up with a separate work item/PR that includes the code changes and tests.
bgavrilMS
left a comment
There was a problem hiding this comment.
Entra supports global mtls endpoint as per discussion with them
Fixes - #5852
Follow up on comment from PR #5823 - #5823 (comment)
Why we are doing this
While investigating a test failure after the MSTest4 update, we found that the issue was not caused by MSTest4 itself.
Root Cause Analysis:
The issue happened because two MSTest test methods in the same class had the exact same name, with one being parameterless and the other parameterized. MSTest test discovery did not handle the overloaded test names correctly, so it picked up the wrong test during execution, which made it look like the parameterized test was passing when it was not actually being run as expected.
Fix:
Renamed the test methods so each test has a unique name and removed the naming collision, ensuring MSTest discovers and executes the correct test cases consistently.
The real problem was that the test expected MSAL to throw:
MsalError.MissingTenantedAuthorityfor explicit mTLS PoP requests using non-tenanted AAD authorities like:
/common/organizations/consumersBut there was no product code that actually performed that validation and threw that error. There is no product code implementing MissingTenantedAuthority for this mTLS PoP path. So even if the test appeared to pass before MSTest4, it was not validating the intended product behavior.
Because of that, the request continued deeper into execution and eventually failed in the test infrastructure (
MockHttpManager) instead of failing early with the intended MSAL exception.What we found
By searching through the codebase, we found:
MsalError.MissingTenantedAuthorityexists inMsalError.csSo there was a mismatch between:
What this change does
This change adds
MtlsPopParametersInitializerto centralize mTLS/PoP initialization and validation logic.It does a few important things:
MissingTenantedAuthoritybefore any HTTP call is madeWhy this is better
With this change:
Summary
This is a product correctness fix that was uncovered during the MSTest4 migration investigation.
MSTest4 only exposed the issue. The real gap was that MSAL had a public error and a unit test for this case, but no product code enforcing it.