From 2c180646661ce8f3de344856124b46aff2c30c6b Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 22 Oct 2024 16:01:08 -0700 Subject: [PATCH 001/137] initial commit --- .../Microsoft.Identity.Client.Broker.csproj | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/src/client/Microsoft.Identity.Client.Broker/Microsoft.Identity.Client.Broker.csproj b/src/client/Microsoft.Identity.Client.Broker/Microsoft.Identity.Client.Broker.csproj index 3d3eb81f18..f6dcbbf237 100644 --- a/src/client/Microsoft.Identity.Client.Broker/Microsoft.Identity.Client.Broker.csproj +++ b/src/client/Microsoft.Identity.Client.Broker/Microsoft.Identity.Client.Broker.csproj @@ -3,9 +3,11 @@ netstandard2.0 net462 + net6.0 AnyCPU - $(TargetFrameworkNetStandard) - $(TargetFrameworkNetStandard);$(TargetFrameworkNetDesktop) + + + $(TargetFrameworkNetCore) Debug;Release;Debug + MobileApps From 6a1f4317c0e72fe9e3ae6238e9d5b358c4c1028b Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Thu, 24 Oct 2024 12:53:22 -0700 Subject: [PATCH 002/137] add linux test app --- Directory.Packages.props | 2 +- NuGet.Config | 1 + tests/devapps/WAM/NetWSLWam/Class1.cs | 113 ++++++++++++++++++++++++ tests/devapps/WAM/NetWSLWam/test.csproj | 19 ++++ 4 files changed, 134 insertions(+), 1 deletion(-) create mode 100644 tests/devapps/WAM/NetWSLWam/Class1.cs create mode 100644 tests/devapps/WAM/NetWSLWam/test.csproj diff --git a/Directory.Packages.props b/Directory.Packages.props index 70acad5898..e3e38f8599 100644 --- a/Directory.Packages.props +++ b/Directory.Packages.props @@ -2,7 +2,7 @@ true - 0.16.2 + 0.17.1 4.61.0 diff --git a/NuGet.Config b/NuGet.Config index 7604d0051e..d9feace75a 100644 --- a/NuGet.Config +++ b/NuGet.Config @@ -3,5 +3,6 @@ + diff --git a/tests/devapps/WAM/NetWSLWam/Class1.cs b/tests/devapps/WAM/NetWSLWam/Class1.cs new file mode 100644 index 0000000000..ffc122c1e2 --- /dev/null +++ b/tests/devapps/WAM/NetWSLWam/Class1.cs @@ -0,0 +1,113 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT License. + +using System; +using System.Collections.Generic; +using System.Linq; +using System.Runtime.InteropServices; +using System.Text; +using System.Threading.Tasks; +using Microsoft.Identity.Client; +using Microsoft.Identity.Client.Broker; + +namespace WAMClassLibrary +{ + public class Authentication + { + /// + /// Get the handle of the console window for Linux + /// + [DllImport("libX11")] + private static extern IntPtr XOpenDisplay(string display); + + [DllImport("libX11")] + private static extern IntPtr XRootWindow(IntPtr display, int screen); + + [DllImport("libX11")] + private static extern IntPtr XDefaultRootWindow(IntPtr display); + + + public static async Task InvokeBrokerAsync() + { + IntPtr _parentHandle = XRootWindow(XOpenDisplay(null), 0);; + Func consoleWindowHandleProvider = () => _parentHandle; + + // 1. Configuration - read below about redirect URI + var pca = PublicClientApplicationBuilder.Create("04f0c124-f2bc-4f59-8241-bf6df9866bbd") + .WithAuthority(AzureCloudInstance.AzurePublic, "organizations") + .WithDefaultRedirectUri() + .WithBroker(new BrokerOptions(BrokerOptions.OperatingSystems.Windows)) + .WithParentActivityOrWindow(consoleWindowHandleProvider) + .Build(); + + // Add a token cache, see https://learn.microsoft.com/entra/msal/dotnet/how-to/token-cache-serialization?tabs=desktop + + // 2. GetAccounts + var accounts = await pca.GetAccountsAsync().ConfigureAwait(false); + var accountToLogin = accounts.FirstOrDefault(); + + try + { + var authResult = await pca.AcquireTokenSilent(new[] { "user.read" }, accountToLogin) + .ExecuteAsync().ConfigureAwait(false); + } + catch (MsalUiRequiredException ex) + { + Console.WriteLine(ex.Message); + Console.WriteLine(ex.ErrorCode); + } + + try + { + var authResult = await pca.AcquireTokenInteractive(new[] { "user.read" }) + .ExecuteAsync().ConfigureAwait(false); + + Console.WriteLine(authResult.Account); + + Console.WriteLine("Acquired Token Successfully!!!"); + + //logout + IEnumerable account = await pca.GetAccountsAsync().ConfigureAwait(false); + if (account.Any()) + { + try + { + await pca.RemoveAsync(account.FirstOrDefault()).ConfigureAwait(false); + Console.WriteLine("User has signed-out"); + } + catch (MsalClientException ex) + { + int errorCode = Marshal.GetHRForException(ex) & ((1 << 16) - 1); + Console.WriteLine("MsalClientException (ErrCode " + errorCode + "): " + ex.Message); + } + catch (MsalException ex) + { + Console.WriteLine($"MsalException Error signing-out user: {ex.Message}"); + } + catch (Exception ex) + { + int errorCode = Marshal.GetHRForException(ex) & ((1 << 16) - 1); + Console.WriteLine("Error Acquiring Token (ErrCode " + errorCode + "): " + ex); + } + } + + Console.Read(); + } + catch (MsalClientException ex) + { + int errorCode = Marshal.GetHRForException(ex) & ((1 << 16) - 1); + Console.WriteLine("MsalClientException (ErrCode " + errorCode + "): " + ex.Message); + } + catch (MsalException ex) + { + Console.WriteLine($"MsalException Error signing-out user: {ex.Message}"); + } + catch (Exception ex) + { + int errorCode = Marshal.GetHRForException(ex) & ((1 << 16) - 1); + Console.WriteLine("Error Acquiring Token (ErrCode " + errorCode + "): " + ex); + } + Console.Read(); + } + } +} diff --git a/tests/devapps/WAM/NetWSLWam/test.csproj b/tests/devapps/WAM/NetWSLWam/test.csproj new file mode 100644 index 0000000000..4b88f33997 --- /dev/null +++ b/tests/devapps/WAM/NetWSLWam/test.csproj @@ -0,0 +1,19 @@ + + + + net6.0 + Library + latest + false + + + + {6839f934-45f0-4026-8af3-c3aefb7d48a9} + Microsoft.Identity.Client.Broker + + + {60117a9b-4bb8-472e-bfff-52cbf67ca95a} + Microsoft.Identity.Client + + + \ No newline at end of file From 0eb40008b65f855275a04d92d6d678c37d8c5b98 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Sun, 27 Oct 2024 22:05:27 -0700 Subject: [PATCH 003/137] bypass check for linux platform --- Directory.Packages.props | 2 +- LibsAndSamples.sln | 2 +- .../BrokerExtension.cs | 9 +++++ .../RuntimeBroker.cs | 5 +++ .../ApiConfig/BrokerOptions.cs | 7 ++++ tests/devapps/WAM/NetWSLWam/Class1.cs | 34 +++++++++++-------- .../NetWSLWam/Properties/launchSettings.json | 11 ++++++ tests/devapps/WAM/NetWSLWam/test.csproj | 9 ++++- 8 files changed, 62 insertions(+), 17 deletions(-) create mode 100644 tests/devapps/WAM/NetWSLWam/Properties/launchSettings.json diff --git a/Directory.Packages.props b/Directory.Packages.props index e3e38f8599..bdd6d20561 100644 --- a/Directory.Packages.props +++ b/Directory.Packages.props @@ -2,7 +2,7 @@ true - 0.17.1 + 0.17.2 4.61.0 diff --git a/LibsAndSamples.sln b/LibsAndSamples.sln index 58a71b2043..4055286eb0 100644 --- a/LibsAndSamples.sln +++ b/LibsAndSamples.sln @@ -106,7 +106,7 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "NetDesktopWinFormsWAM", "te EndProject Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "NetCoreWinFormsWAM", "tests\devapps\WAM\NetCoreWinFormsWam\NetCoreWinFormsWAM.csproj", "{339E0B2B-4408-4947-B134-E8C5AAB11286}" EndProject -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "NetDesktopWpfWAM", "tests\devapps\WAM\NetDesktopWpf\NetDesktopWpfWAM.csproj", "{2AF48872-DD47-4DA1-A153-DF4DA13882C2}" +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "NetWSLWam", "tests\devapps\WAM\NetWSLWam\test.csproj", "{2AF48872-DD47-4DA1-A153-DF4DA13882C2}" EndProject Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Identity.Test.Integration.NetFx", "tests\Microsoft.Identity.Test.Integration.netfx\Microsoft.Identity.Test.Integration.NetFx.csproj", "{743BEA88-1903-4AF0-A791-705774F4B99D}" EndProject diff --git a/src/client/Microsoft.Identity.Client.Broker/BrokerExtension.cs b/src/client/Microsoft.Identity.Client.Broker/BrokerExtension.cs index 256d3427c8..e55d890258 100644 --- a/src/client/Microsoft.Identity.Client.Broker/BrokerExtension.cs +++ b/src/client/Microsoft.Identity.Client.Broker/BrokerExtension.cs @@ -47,6 +47,7 @@ public static PublicClientApplicationBuilder WithBrokerPreview(this PublicClient /// parameters, and to create a public client application instance public static PublicClientApplicationBuilder WithBroker(this PublicClientApplicationBuilder builder, BrokerOptions brokerOptions) { + Console.WriteLine("namespace Microsoft.Identity.Client.Broker "); AddRuntimeSupport(builder); builder.Config.BrokerOptions = brokerOptions; builder.Config.IsBrokerEnabled = brokerOptions.IsBrokerEnabledOnCurrentOs(); @@ -79,6 +80,14 @@ private static void AddRuntimeSupport(PublicClientApplicationBuilder builder) logger.Info("[Runtime] WAM supported OS."); return new RuntimeBroker(uiParent, appConfig, logger); }; + } else if (DesktopOsHelper.IsLinux()) { + Console.WriteLine("Support WAM in WSL"); + builder.Config.BrokerCreatorFunc = + (uiParent, appConfig, logger) => + { + logger.Info("[Runtime] WAM supported OS WSL."); + return new RuntimeBroker(uiParent, appConfig, logger); + }; } else { diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index ee9292f83b..9463f2d1bf 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -126,6 +126,7 @@ public async Task AcquireTokenInteractiveAsync( AuthenticationRequestParameters authenticationRequestParameters, AcquireTokenInteractiveParameters acquireTokenInteractiveParameters) { + Console.WriteLine("Runtime Broker AcquireTokenInteractiveAsync"); using LogEventWrapper logEventWrapper = new LogEventWrapper(this); Debug.Assert(s_lazyCore.Value != null, "Should not call this API if MSAL runtime init failed"); @@ -586,6 +587,10 @@ public void HandleInstallUrl(string appLink) public bool IsBrokerInstalledAndInvokable(AuthorityType authorityType) { + if (DesktopOsHelper.IsLinux()) { + _logger?.Info(() => "[RuntimeBroker] MsalRuntime running in WSL"); + return true; + } if (!DesktopOsHelper.IsWin10OrServerEquivalent()) { _logger?.Warning("[RuntimeBroker] Not a supported operating system. WAM broker is not available. "); diff --git a/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs b/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs index 871cacc8ad..baa4658c16 100644 --- a/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs +++ b/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs @@ -29,6 +29,10 @@ public enum OperatingSystems /// Use broker on Windows OS /// Windows = 0b_0000_0001, // 1 + /// + /// Use broker on Linux + /// + Linux = 0b_0000_0010, // 1 } /// @@ -81,6 +85,9 @@ internal bool IsBrokerEnabledOnCurrentOs() if (EnabledOn.HasFlag(OperatingSystems.Windows) && DesktopOsHelper.IsWindows()) { return true; + } else if (DesktopOsHelper.IsLinux()) { + Console.WriteLine("Broekr enabled on Linux"); + return true; } return false; diff --git a/tests/devapps/WAM/NetWSLWam/Class1.cs b/tests/devapps/WAM/NetWSLWam/Class1.cs index ffc122c1e2..d87cfbf9e1 100644 --- a/tests/devapps/WAM/NetWSLWam/Class1.cs +++ b/tests/devapps/WAM/NetWSLWam/Class1.cs @@ -34,28 +34,29 @@ public static async Task InvokeBrokerAsync() // 1. Configuration - read below about redirect URI var pca = PublicClientApplicationBuilder.Create("04f0c124-f2bc-4f59-8241-bf6df9866bbd") - .WithAuthority(AzureCloudInstance.AzurePublic, "organizations") + .WithAuthority("https://login.microsoftonline.com/common") .WithDefaultRedirectUri() - .WithBroker(new BrokerOptions(BrokerOptions.OperatingSystems.Windows)) + .WithBroker(new BrokerOptions(BrokerOptions.OperatingSystems.Linux)) .WithParentActivityOrWindow(consoleWindowHandleProvider) + .WithLogging((x, y, z) => Console.WriteLine($"{x} {y}"), LogLevel.Verbose, true) .Build(); // Add a token cache, see https://learn.microsoft.com/entra/msal/dotnet/how-to/token-cache-serialization?tabs=desktop // 2. GetAccounts - var accounts = await pca.GetAccountsAsync().ConfigureAwait(false); - var accountToLogin = accounts.FirstOrDefault(); + // var accounts = await pca.GetAccountsAsync().ConfigureAwait(false); + // var accountToLogin = accounts.FirstOrDefault(); - try - { - var authResult = await pca.AcquireTokenSilent(new[] { "user.read" }, accountToLogin) - .ExecuteAsync().ConfigureAwait(false); - } - catch (MsalUiRequiredException ex) - { - Console.WriteLine(ex.Message); - Console.WriteLine(ex.ErrorCode); - } + // try + // { + // var authResult = await pca.AcquireTokenSilent(new[] { "user.read" }, accountToLogin) + // .ExecuteAsync().ConfigureAwait(false); + // } + // catch (MsalUiRequiredException ex) + // { + // Console.WriteLine(ex.Message); + // Console.WriteLine(ex.ErrorCode); + // } try { @@ -109,5 +110,10 @@ public static async Task InvokeBrokerAsync() } Console.Read(); } + + public static void Main(string[] args) + { + InvokeBrokerAsync().Wait(); + } } } diff --git a/tests/devapps/WAM/NetWSLWam/Properties/launchSettings.json b/tests/devapps/WAM/NetWSLWam/Properties/launchSettings.json new file mode 100644 index 0000000000..0411ab6b8c --- /dev/null +++ b/tests/devapps/WAM/NetWSLWam/Properties/launchSettings.json @@ -0,0 +1,11 @@ +{ + "profiles": { + "test": { + "commandName": "Project" + }, + "WSL": { + "commandName": "WSL2", + "distributionName": "" + } + } +} \ No newline at end of file diff --git a/tests/devapps/WAM/NetWSLWam/test.csproj b/tests/devapps/WAM/NetWSLWam/test.csproj index 4b88f33997..376242f25d 100644 --- a/tests/devapps/WAM/NetWSLWam/test.csproj +++ b/tests/devapps/WAM/NetWSLWam/test.csproj @@ -2,7 +2,7 @@ net6.0 - Library + Exe latest false @@ -16,4 +16,11 @@ Microsoft.Identity.Client + + + + libmsalruntime.so + Always + + \ No newline at end of file From c7ff66a59ec15d6a9b8d25245c92523a2f87b4a4 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 5 Nov 2024 15:34:09 -0800 Subject: [PATCH 004/137] Add isRunningInWsl check --- .../Microsoft.Identity.Client.Broker/RuntimeBroker.cs | 6 +----- .../PlatformsCommon/Shared/DesktopOsHelper.cs | 10 ++++++++++ 2 files changed, 11 insertions(+), 5 deletions(-) diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index 9463f2d1bf..d17db73a3d 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -587,11 +587,7 @@ public void HandleInstallUrl(string appLink) public bool IsBrokerInstalledAndInvokable(AuthorityType authorityType) { - if (DesktopOsHelper.IsLinux()) { - _logger?.Info(() => "[RuntimeBroker] MsalRuntime running in WSL"); - return true; - } - if (!DesktopOsHelper.IsWin10OrServerEquivalent()) + if (!DesktopOsHelper.IsWin10OrServerEquivalent() && !DesktopOsHelper.IsRunningOnWsl()) { _logger?.Warning("[RuntimeBroker] Not a supported operating system. WAM broker is not available. "); return false; diff --git a/src/client/Microsoft.Identity.Client/PlatformsCommon/Shared/DesktopOsHelper.cs b/src/client/Microsoft.Identity.Client/PlatformsCommon/Shared/DesktopOsHelper.cs index a5fc805a46..f2f8a68ef0 100644 --- a/src/client/Microsoft.Identity.Client/PlatformsCommon/Shared/DesktopOsHelper.cs +++ b/src/client/Microsoft.Identity.Client/PlatformsCommon/Shared/DesktopOsHelper.cs @@ -2,6 +2,7 @@ // Licensed under the MIT License. using System; +using System.IO; using System.Linq; using System.Runtime.InteropServices; using Microsoft.Identity.Client.Utils; @@ -55,6 +56,15 @@ public static bool IsMac() #endif } + public static bool IsRunningOnWsl() + { + if (IsLinux()) { + var versionInfo = File.ReadAllText("/proc/version"); + return versionInfo.Contains("Microsoft") || versionInfo.Contains("WSL"); + } + return false; + } + /// /// Checks if the OS supports WAM (Web Account Manager) /// WAM Supported OS's are Windows 10 and above for Client, Windows 2019 and above for Server From 883e44d76d20a37636a9f5083cfa63c09fc974be Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 5 Nov 2024 15:35:33 -0800 Subject: [PATCH 005/137] Update RuntimeSupport OS check --- src/client/Microsoft.Identity.Client.Broker/BrokerExtension.cs | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/client/Microsoft.Identity.Client.Broker/BrokerExtension.cs b/src/client/Microsoft.Identity.Client.Broker/BrokerExtension.cs index e55d890258..d498b29574 100644 --- a/src/client/Microsoft.Identity.Client.Broker/BrokerExtension.cs +++ b/src/client/Microsoft.Identity.Client.Broker/BrokerExtension.cs @@ -80,8 +80,7 @@ private static void AddRuntimeSupport(PublicClientApplicationBuilder builder) logger.Info("[Runtime] WAM supported OS."); return new RuntimeBroker(uiParent, appConfig, logger); }; - } else if (DesktopOsHelper.IsLinux()) { - Console.WriteLine("Support WAM in WSL"); + } else if (DesktopOsHelper.IsRunningOnWsl()) { builder.Config.BrokerCreatorFunc = (uiParent, appConfig, logger) => { From 9b6cc0c841cb6d4f5a13c10361968c19d37083ef Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Fri, 15 Nov 2024 14:21:39 -0800 Subject: [PATCH 006/137] update --- LibsAndSamples.sln | 2 +- .../BrokerExtension.cs | 1 - .../Microsoft.Identity.Client.Broker.csproj | 4 +-- .../RuntimeBroker.cs | 2 +- .../ApiConfig/BrokerOptions.cs | 3 +- tests/devapps/WAM/NetWSLWam/Class1.cs | 32 ++----------------- tests/devapps/WAM/NetWSLWam/test.csproj | 7 ---- 7 files changed, 8 insertions(+), 43 deletions(-) diff --git a/LibsAndSamples.sln b/LibsAndSamples.sln index 4055286eb0..58a71b2043 100644 --- a/LibsAndSamples.sln +++ b/LibsAndSamples.sln @@ -106,7 +106,7 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "NetDesktopWinFormsWAM", "te EndProject Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "NetCoreWinFormsWAM", "tests\devapps\WAM\NetCoreWinFormsWam\NetCoreWinFormsWAM.csproj", "{339E0B2B-4408-4947-B134-E8C5AAB11286}" EndProject -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "NetWSLWam", "tests\devapps\WAM\NetWSLWam\test.csproj", "{2AF48872-DD47-4DA1-A153-DF4DA13882C2}" +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "NetDesktopWpfWAM", "tests\devapps\WAM\NetDesktopWpf\NetDesktopWpfWAM.csproj", "{2AF48872-DD47-4DA1-A153-DF4DA13882C2}" EndProject Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Identity.Test.Integration.NetFx", "tests\Microsoft.Identity.Test.Integration.netfx\Microsoft.Identity.Test.Integration.NetFx.csproj", "{743BEA88-1903-4AF0-A791-705774F4B99D}" EndProject diff --git a/src/client/Microsoft.Identity.Client.Broker/BrokerExtension.cs b/src/client/Microsoft.Identity.Client.Broker/BrokerExtension.cs index d498b29574..0c56c7d793 100644 --- a/src/client/Microsoft.Identity.Client.Broker/BrokerExtension.cs +++ b/src/client/Microsoft.Identity.Client.Broker/BrokerExtension.cs @@ -47,7 +47,6 @@ public static PublicClientApplicationBuilder WithBrokerPreview(this PublicClient /// parameters, and to create a public client application instance public static PublicClientApplicationBuilder WithBroker(this PublicClientApplicationBuilder builder, BrokerOptions brokerOptions) { - Console.WriteLine("namespace Microsoft.Identity.Client.Broker "); AddRuntimeSupport(builder); builder.Config.BrokerOptions = brokerOptions; builder.Config.IsBrokerEnabled = brokerOptions.IsBrokerEnabledOnCurrentOs(); diff --git a/src/client/Microsoft.Identity.Client.Broker/Microsoft.Identity.Client.Broker.csproj b/src/client/Microsoft.Identity.Client.Broker/Microsoft.Identity.Client.Broker.csproj index f6dcbbf237..de58c4e0ff 100644 --- a/src/client/Microsoft.Identity.Client.Broker/Microsoft.Identity.Client.Broker.csproj +++ b/src/client/Microsoft.Identity.Client.Broker/Microsoft.Identity.Client.Broker.csproj @@ -5,8 +5,8 @@ net462 net6.0 AnyCPU - - + $(TargetFrameworkNetStandard) + $(TargetFrameworkNetStandard);$(TargetFrameworkNetDesktop) $(TargetFrameworkNetCore) Debug;Release;Debug + MobileApps diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index d17db73a3d..2f4907cd41 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -478,7 +478,7 @@ public async Task> GetAccountsAsync( ICacheSessionManager cacheSessionManager, IInstanceDiscoveryManager instanceDiscoveryManager) { - if (!_wamOptions.ListOperatingSystemAccounts) + if (!DesktopOsHelper.IsRunningOnWsl() && !_wamOptions.ListOperatingSystemAccounts) { _logger.Info("[RuntimeBroker] ListWindowsWorkAndSchoolAccounts option was not enabled."); return Array.Empty(); diff --git a/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs b/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs index baa4658c16..ceecdeca4c 100644 --- a/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs +++ b/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs @@ -85,8 +85,7 @@ internal bool IsBrokerEnabledOnCurrentOs() if (EnabledOn.HasFlag(OperatingSystems.Windows) && DesktopOsHelper.IsWindows()) { return true; - } else if (DesktopOsHelper.IsLinux()) { - Console.WriteLine("Broekr enabled on Linux"); + } else if (DesktopOsHelper.IsRunningOnWsl()) { return true; } diff --git a/tests/devapps/WAM/NetWSLWam/Class1.cs b/tests/devapps/WAM/NetWSLWam/Class1.cs index d87cfbf9e1..e9dc40ea6c 100644 --- a/tests/devapps/WAM/NetWSLWam/Class1.cs +++ b/tests/devapps/WAM/NetWSLWam/Class1.cs @@ -44,8 +44,8 @@ public static async Task InvokeBrokerAsync() // Add a token cache, see https://learn.microsoft.com/entra/msal/dotnet/how-to/token-cache-serialization?tabs=desktop // 2. GetAccounts - // var accounts = await pca.GetAccountsAsync().ConfigureAwait(false); - // var accountToLogin = accounts.FirstOrDefault(); + var accounts = await pca.GetAccountsAsync().ConfigureAwait(false); + var accountToLogin = accounts.FirstOrDefault(); // try // { @@ -60,39 +60,13 @@ public static async Task InvokeBrokerAsync() try { - var authResult = await pca.AcquireTokenInteractive(new[] { "user.read" }) + var authResult = await pca.AcquireTokenInteractive(new[] { "user.read" }).WithLoginHint("idlab@msidlab4.onmicrosoft.com") .ExecuteAsync().ConfigureAwait(false); Console.WriteLine(authResult.Account); Console.WriteLine("Acquired Token Successfully!!!"); - //logout - IEnumerable account = await pca.GetAccountsAsync().ConfigureAwait(false); - if (account.Any()) - { - try - { - await pca.RemoveAsync(account.FirstOrDefault()).ConfigureAwait(false); - Console.WriteLine("User has signed-out"); - } - catch (MsalClientException ex) - { - int errorCode = Marshal.GetHRForException(ex) & ((1 << 16) - 1); - Console.WriteLine("MsalClientException (ErrCode " + errorCode + "): " + ex.Message); - } - catch (MsalException ex) - { - Console.WriteLine($"MsalException Error signing-out user: {ex.Message}"); - } - catch (Exception ex) - { - int errorCode = Marshal.GetHRForException(ex) & ((1 << 16) - 1); - Console.WriteLine("Error Acquiring Token (ErrCode " + errorCode + "): " + ex); - } - } - - Console.Read(); } catch (MsalClientException ex) { diff --git a/tests/devapps/WAM/NetWSLWam/test.csproj b/tests/devapps/WAM/NetWSLWam/test.csproj index 376242f25d..a28feb2c74 100644 --- a/tests/devapps/WAM/NetWSLWam/test.csproj +++ b/tests/devapps/WAM/NetWSLWam/test.csproj @@ -16,11 +16,4 @@ Microsoft.Identity.Client - - - - libmsalruntime.so - Always - - \ No newline at end of file From 67b0bbd8cef481f631cfa06513e2f21ed2d78b62 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 19 Nov 2024 15:48:19 -0800 Subject: [PATCH 007/137] Add linux --- .../Microsoft.Identity.Client.Broker/BrokerExtension.cs | 7 +++++++ .../Microsoft.Identity.Client.Broker/RuntimeBroker.cs | 4 ++-- .../Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs | 8 ++++++-- 3 files changed, 15 insertions(+), 4 deletions(-) diff --git a/src/client/Microsoft.Identity.Client.Broker/BrokerExtension.cs b/src/client/Microsoft.Identity.Client.Broker/BrokerExtension.cs index 0c56c7d793..36a11f7113 100644 --- a/src/client/Microsoft.Identity.Client.Broker/BrokerExtension.cs +++ b/src/client/Microsoft.Identity.Client.Broker/BrokerExtension.cs @@ -86,6 +86,13 @@ private static void AddRuntimeSupport(PublicClientApplicationBuilder builder) logger.Info("[Runtime] WAM supported OS WSL."); return new RuntimeBroker(uiParent, appConfig, logger); }; + } else if (DesktopOsHelper.IsLinux()) { + builder.Config.BrokerCreatorFunc = + (uiParent, appConfig, logger) => + { + logger.Info("[Runtime] Broker supported OS Linux."); + return new RuntimeBroker(uiParent, appConfig, logger); + }; } else { diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index 2f4907cd41..71054ddf44 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -478,7 +478,7 @@ public async Task> GetAccountsAsync( ICacheSessionManager cacheSessionManager, IInstanceDiscoveryManager instanceDiscoveryManager) { - if (!DesktopOsHelper.IsRunningOnWsl() && !_wamOptions.ListOperatingSystemAccounts) + if (!DesktopOsHelper.IsLinux() && !_wamOptions.ListOperatingSystemAccounts) { _logger.Info("[RuntimeBroker] ListWindowsWorkAndSchoolAccounts option was not enabled."); return Array.Empty(); @@ -587,7 +587,7 @@ public void HandleInstallUrl(string appLink) public bool IsBrokerInstalledAndInvokable(AuthorityType authorityType) { - if (!DesktopOsHelper.IsWin10OrServerEquivalent() && !DesktopOsHelper.IsRunningOnWsl()) + if (!DesktopOsHelper.IsWin10OrServerEquivalent() && !DesktopOsHelper.IsLinux()) { _logger?.Warning("[RuntimeBroker] Not a supported operating system. WAM broker is not available. "); return false; diff --git a/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs b/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs index ceecdeca4c..53ebf2ba92 100644 --- a/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs +++ b/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs @@ -32,7 +32,11 @@ public enum OperatingSystems /// /// Use broker on Linux /// - Linux = 0b_0000_0010, // 1 + Linux = 0b_0000_0010, // 2 + /// + /// Use broker on Linux + /// + WSL = 0b_0000_0011, // 3 } /// @@ -85,7 +89,7 @@ internal bool IsBrokerEnabledOnCurrentOs() if (EnabledOn.HasFlag(OperatingSystems.Windows) && DesktopOsHelper.IsWindows()) { return true; - } else if (DesktopOsHelper.IsRunningOnWsl()) { + } else if (DesktopOsHelper.IsLinux()) { return true; } From 12ae0211ec3e5cfb302c59d8bec37436ec13d7a1 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Wed, 15 Jan 2025 15:39:19 -0800 Subject: [PATCH 008/137] update --- Directory.Packages.props | 2 +- tests/devapps/WAM/NetWSLWam/Class1.cs | 20 ++++++++++---------- 2 files changed, 11 insertions(+), 11 deletions(-) diff --git a/Directory.Packages.props b/Directory.Packages.props index d330bb2d29..77ac7fafc2 100644 --- a/Directory.Packages.props +++ b/Directory.Packages.props @@ -2,7 +2,7 @@ true - 0.17.2 + 0.18.0 4.61.0 diff --git a/tests/devapps/WAM/NetWSLWam/Class1.cs b/tests/devapps/WAM/NetWSLWam/Class1.cs index e9dc40ea6c..23c00af45a 100644 --- a/tests/devapps/WAM/NetWSLWam/Class1.cs +++ b/tests/devapps/WAM/NetWSLWam/Class1.cs @@ -47,16 +47,16 @@ public static async Task InvokeBrokerAsync() var accounts = await pca.GetAccountsAsync().ConfigureAwait(false); var accountToLogin = accounts.FirstOrDefault(); - // try - // { - // var authResult = await pca.AcquireTokenSilent(new[] { "user.read" }, accountToLogin) - // .ExecuteAsync().ConfigureAwait(false); - // } - // catch (MsalUiRequiredException ex) - // { - // Console.WriteLine(ex.Message); - // Console.WriteLine(ex.ErrorCode); - // } + try + { + var authResult = await pca.AcquireTokenSilent(new[] { "user.read" }, accountToLogin) + .ExecuteAsync().ConfigureAwait(false); + } + catch (MsalUiRequiredException ex) + { + Console.WriteLine(ex.Message); + Console.WriteLine(ex.ErrorCode); + } try { From 0807920959cc7b845ab71beffad339df97dc1fee Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Wed, 15 Jan 2025 16:03:29 -0800 Subject: [PATCH 009/137] update to net8.0 --- .../Microsoft.Identity.Client.Broker.csproj | 4 +--- .../Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs | 2 +- tests/devapps/WAM/NetWSLWam/test.csproj | 2 +- 3 files changed, 3 insertions(+), 5 deletions(-) diff --git a/src/client/Microsoft.Identity.Client.Broker/Microsoft.Identity.Client.Broker.csproj b/src/client/Microsoft.Identity.Client.Broker/Microsoft.Identity.Client.Broker.csproj index 3e33d1eb3f..7ff968049f 100644 --- a/src/client/Microsoft.Identity.Client.Broker/Microsoft.Identity.Client.Broker.csproj +++ b/src/client/Microsoft.Identity.Client.Broker/Microsoft.Identity.Client.Broker.csproj @@ -3,11 +3,9 @@ netstandard2.0 net462 - net6.0 AnyCPU - $(TargetFrameworkNetStandard) + $(TargetFrameworkNetStandard) $(TargetFrameworkNetStandard);$(TargetFrameworkNetDesktop) - $(TargetFrameworkNetCore) Debug;Release;Debug + MobileApps diff --git a/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs b/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs index 53ebf2ba92..fc8599b9d3 100644 --- a/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs +++ b/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs @@ -34,7 +34,7 @@ public enum OperatingSystems /// Linux = 0b_0000_0010, // 2 /// - /// Use broker on Linux + /// Use broker on WSL /// WSL = 0b_0000_0011, // 3 } diff --git a/tests/devapps/WAM/NetWSLWam/test.csproj b/tests/devapps/WAM/NetWSLWam/test.csproj index a28feb2c74..ec3de2464c 100644 --- a/tests/devapps/WAM/NetWSLWam/test.csproj +++ b/tests/devapps/WAM/NetWSLWam/test.csproj @@ -1,7 +1,7 @@ - net6.0 + net8.0 Exe latest false From 9b277565f15dc54636f23af28b2fb4aaf8927402 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Wed, 15 Jan 2025 16:05:58 -0800 Subject: [PATCH 010/137] fix typo --- .../Microsoft.Identity.Client.Broker.csproj | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/client/Microsoft.Identity.Client.Broker/Microsoft.Identity.Client.Broker.csproj b/src/client/Microsoft.Identity.Client.Broker/Microsoft.Identity.Client.Broker.csproj index 7ff968049f..936518d212 100644 --- a/src/client/Microsoft.Identity.Client.Broker/Microsoft.Identity.Client.Broker.csproj +++ b/src/client/Microsoft.Identity.Client.Broker/Microsoft.Identity.Client.Broker.csproj @@ -4,7 +4,7 @@ netstandard2.0 net462 AnyCPU - $(TargetFrameworkNetStandard) + $(TargetFrameworkNetStandard) $(TargetFrameworkNetStandard);$(TargetFrameworkNetDesktop) Debug;Release;Debug + MobileApps From 0339fe5b0a1ce8d956e1b3909821a1073f0cd756 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Fri, 17 Jan 2025 15:52:54 -0800 Subject: [PATCH 011/137] Update msalruntime version to 0.7.0-alpha --- Directory.Packages.props | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Directory.Packages.props b/Directory.Packages.props index dfb0f023f4..e241f6e0bd 100644 --- a/Directory.Packages.props +++ b/Directory.Packages.props @@ -2,7 +2,7 @@ true - 0.16.2 + 0.7.0-alpha 4.61.0 From eadc942885b78e14149be60e024c2cb90fda17c7 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Wed, 22 Jan 2025 16:58:32 -0800 Subject: [PATCH 012/137] use lazy bool --- .../Microsoft.Identity.Client.Broker.csproj | 2 +- .../Microsoft.Identity.Client.Broker/RuntimeBroker.cs | 1 - .../PlatformsCommon/Shared/DesktopOsHelper.cs | 9 ++++++++- 3 files changed, 9 insertions(+), 3 deletions(-) diff --git a/src/client/Microsoft.Identity.Client.Broker/Microsoft.Identity.Client.Broker.csproj b/src/client/Microsoft.Identity.Client.Broker/Microsoft.Identity.Client.Broker.csproj index 936518d212..8786e8c800 100644 --- a/src/client/Microsoft.Identity.Client.Broker/Microsoft.Identity.Client.Broker.csproj +++ b/src/client/Microsoft.Identity.Client.Broker/Microsoft.Identity.Client.Broker.csproj @@ -4,7 +4,7 @@ netstandard2.0 net462 AnyCPU - $(TargetFrameworkNetStandard) + $(TargetFrameworkNetStandard) $(TargetFrameworkNetStandard);$(TargetFrameworkNetDesktop) Debug;Release;Debug + MobileApps diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index 71054ddf44..50cbf9ef53 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -126,7 +126,6 @@ public async Task AcquireTokenInteractiveAsync( AuthenticationRequestParameters authenticationRequestParameters, AcquireTokenInteractiveParameters acquireTokenInteractiveParameters) { - Console.WriteLine("Runtime Broker AcquireTokenInteractiveAsync"); using LogEventWrapper logEventWrapper = new LogEventWrapper(this); Debug.Assert(s_lazyCore.Value != null, "Should not call this API if MSAL runtime init failed"); diff --git a/src/client/Microsoft.Identity.Client/PlatformsCommon/Shared/DesktopOsHelper.cs b/src/client/Microsoft.Identity.Client/PlatformsCommon/Shared/DesktopOsHelper.cs index f2f8a68ef0..ecd0408eeb 100644 --- a/src/client/Microsoft.Identity.Client/PlatformsCommon/Shared/DesktopOsHelper.cs +++ b/src/client/Microsoft.Identity.Client/PlatformsCommon/Shared/DesktopOsHelper.cs @@ -20,6 +20,8 @@ internal static class DesktopOsHelper private static Lazy s_winVersionLazy = new Lazy( GetWindowsVersionStringInternal); + private static Lazy s_wslEnvLazy = new Lazy(IsWslEnv); + public static bool IsWindows() { @@ -56,7 +58,7 @@ public static bool IsMac() #endif } - public static bool IsRunningOnWsl() + public static bool IsWslEnv() { if (IsLinux()) { var versionInfo = File.ReadAllText("/proc/version"); @@ -105,6 +107,11 @@ private static string GetWindowsVersionStringInternal() #endif } + public static bool IsRunningOnWsl() + { + return s_wslEnvLazy.Value; + } + public static string GetWindowsVersionString() { return s_winVersionLazy.Value; From 9fde6ec166ca6bc66a8f12cac81da6540b86546f Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Fri, 24 Jan 2025 11:41:16 -0800 Subject: [PATCH 013/137] address comments --- NuGet.Config | 1 - .../Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs | 4 ---- 2 files changed, 5 deletions(-) diff --git a/NuGet.Config b/NuGet.Config index d9feace75a..7604d0051e 100644 --- a/NuGet.Config +++ b/NuGet.Config @@ -3,6 +3,5 @@ - diff --git a/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs b/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs index fc8599b9d3..4d11fd7451 100644 --- a/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs +++ b/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs @@ -33,10 +33,6 @@ public enum OperatingSystems /// Use broker on Linux /// Linux = 0b_0000_0010, // 2 - /// - /// Use broker on WSL - /// - WSL = 0b_0000_0011, // 3 } /// From f21e8f9aa17f56b3cf1ac9516c5925a3232deda9 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Fri, 24 Jan 2025 14:00:30 -0800 Subject: [PATCH 014/137] initial commit --- build/template-build-and-prep-automation.yaml | 3 ++- build/template-build-and-run-all-tests.yaml | 16 ++++++++++++ build/template-test-on-linux.yaml | 26 +++++++++++++++++++ 3 files changed, 44 insertions(+), 1 deletion(-) create mode 100644 build/template-test-on-linux.yaml diff --git a/build/template-build-and-prep-automation.yaml b/build/template-build-and-prep-automation.yaml index d942634bf3..c859a6dfe2 100644 --- a/build/template-build-and-prep-automation.yaml +++ b/build/template-build-and-prep-automation.yaml @@ -73,7 +73,8 @@ steps: #runtime path with file name $runtimes = @('runtimes\win-x64\native\msalruntime.dll', 'runtimes\win-x86\native\msalruntime_x86.dll', - 'runtimes\win-arm64\native\msalruntime_arm64.dll'); + 'runtimes\win-arm64\native\msalruntime_arm64.dll', + 'runtimes\linux-x64\native\libmsalruntime.so'); #dev apps to check $AppsToCheck = @('MSIX\WPF\bin\Release\', diff --git a/build/template-build-and-run-all-tests.yaml b/build/template-build-and-run-all-tests.yaml index 1f8d2f7184..055299d62b 100644 --- a/build/template-build-and-run-all-tests.yaml +++ b/build/template-build-and-run-all-tests.yaml @@ -82,3 +82,19 @@ jobs: #Build and stage projects fallbackOnPRTargetBranch: false baseDefinitionId: '905' #this is the PR build and it is used as a baseline baseBranchRef: 'main' + +- job: 'Run Unit Tests on Linux' + #strategy: + # parallel: 5 + dependsOn: + - 'BuildAndStageProjects' + pool: + vmImage: 'ubuntu-22.04' + demands: + - msbuild + variables: + runCodesignValidationInjection: false + Codeql.SkipTaskAutoInjection: true + + steps: + - template: template-test-on-linux.yaml \ No newline at end of file diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml new file mode 100644 index 0000000000..9560501008 --- /dev/null +++ b/build/template-test-on-linux.yaml @@ -0,0 +1,26 @@ +# template-test-on-linux.yaml +# Run all unit tests across the LibsAndSamples.sln project on Linux platform + +parameters: + BuildConfiguration: 'Release' + +steps: + +- task: UseDotNet@2 + displayName: 'Use the latest .NET 8' + inputs: + packageType: 'sdk' + version: '8.x' # Specify the .NET SDK version you need + installationPath: $(Agent.ToolsDirectory)/dotnet + +- task: VSTest@2 + displayName: 'Run unit tests .NET ' + inputs: + testSelector: 'testAssemblies' + testAssemblyVer2: '**\Microsoft.Identity.Test.Unit\bin\**\net8.0\Microsoft.Identity.Test.Unit.dll' + searchFolder: '$(System.DefaultWorkingDirectory)' + runInParallel: true + codeCoverageEnabled: true + failOnMinTestsNotRun: true + minimumExpectedTests: '1' + runSettingsFile: 'build\CodeCoverage.runsettings' From e9381a880567f8db3ec118cab23486c205cb4d9e Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Fri, 24 Jan 2025 14:03:42 -0800 Subject: [PATCH 015/137] fix name issue --- build/template-build-and-run-all-tests.yaml | 2 +- build/template-test-on-linux.yaml | 4 +--- 2 files changed, 2 insertions(+), 4 deletions(-) diff --git a/build/template-build-and-run-all-tests.yaml b/build/template-build-and-run-all-tests.yaml index 055299d62b..64b9c37214 100644 --- a/build/template-build-and-run-all-tests.yaml +++ b/build/template-build-and-run-all-tests.yaml @@ -83,7 +83,7 @@ jobs: #Build and stage projects baseDefinitionId: '905' #this is the PR build and it is used as a baseline baseBranchRef: 'main' -- job: 'Run Unit Tests on Linux' +- job: 'RunUnitTestsonLinux' #strategy: # parallel: 5 dependsOn: diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 9560501008..ba3579af2b 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -9,9 +9,7 @@ steps: - task: UseDotNet@2 displayName: 'Use the latest .NET 8' inputs: - packageType: 'sdk' - version: '8.x' # Specify the .NET SDK version you need - installationPath: $(Agent.ToolsDirectory)/dotnet + version: 8.x - task: VSTest@2 displayName: 'Run unit tests .NET ' From 5ee630b9ea177c4d762afc172488e8f10b09fe71 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Fri, 24 Jan 2025 14:17:51 -0800 Subject: [PATCH 016/137] remove for now --- build/template-build-and-prep-automation.yaml | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/build/template-build-and-prep-automation.yaml b/build/template-build-and-prep-automation.yaml index c859a6dfe2..d942634bf3 100644 --- a/build/template-build-and-prep-automation.yaml +++ b/build/template-build-and-prep-automation.yaml @@ -73,8 +73,7 @@ steps: #runtime path with file name $runtimes = @('runtimes\win-x64\native\msalruntime.dll', 'runtimes\win-x86\native\msalruntime_x86.dll', - 'runtimes\win-arm64\native\msalruntime_arm64.dll', - 'runtimes\linux-x64\native\libmsalruntime.so'); + 'runtimes\win-arm64\native\msalruntime_arm64.dll'); #dev apps to check $AppsToCheck = @('MSIX\WPF\bin\Release\', From 390ec376597c2ce3e9546a6841abfdf24ffa0fa1 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Fri, 24 Jan 2025 14:31:19 -0800 Subject: [PATCH 017/137] try use script --- build/template-test-on-linux.yaml | 14 +++----------- 1 file changed, 3 insertions(+), 11 deletions(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index ba3579af2b..5fcda689a2 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -11,14 +11,6 @@ steps: inputs: version: 8.x -- task: VSTest@2 - displayName: 'Run unit tests .NET ' - inputs: - testSelector: 'testAssemblies' - testAssemblyVer2: '**\Microsoft.Identity.Test.Unit\bin\**\net8.0\Microsoft.Identity.Test.Unit.dll' - searchFolder: '$(System.DefaultWorkingDirectory)' - runInParallel: true - codeCoverageEnabled: true - failOnMinTestsNotRun: true - minimumExpectedTests: '1' - runSettingsFile: 'build\CodeCoverage.runsettings' +# VSTest@2 is supported only on Windows +- script: dotnet test **/Microsoft.Identity.Test.Unit/bin/**/net8.0/Microsoft.Identity.Test.Unit.dll' --configuration Release --collect:"XPlat Code Coverage" --settings build/CodeCoverage.runsettings + displayName: 'Run unit tests .NET' From d8966be873c650f2c4e7607494ca76c151d70317 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Fri, 24 Jan 2025 14:49:39 -0800 Subject: [PATCH 018/137] fix syntax error --- build/template-test-on-linux.yaml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 5fcda689a2..bd5d466897 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -12,5 +12,6 @@ steps: version: 8.x # VSTest@2 is supported only on Windows -- script: dotnet test **/Microsoft.Identity.Test.Unit/bin/**/net8.0/Microsoft.Identity.Test.Unit.dll' --configuration Release --collect:"XPlat Code Coverage" --settings build/CodeCoverage.runsettings +- script: | + dotnet test **/Microsoft.Identity.Test.Unit/bin/**/net8.0/Microsoft.Identity.Test.Unit.dll --configuration Release --collect:"XPlat Code Coverage" --settings build/CodeCoverage.runsettings displayName: 'Run unit tests .NET' From d5afada73e1110ada678faa9bf1d25f67b0c6857 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Fri, 24 Jan 2025 15:36:02 -0800 Subject: [PATCH 019/137] temp change --- Directory.Packages.props | 2 +- .../PublicApi/net8.0/PublicAPI.Shipped.txt | 1 + .../PublicApi/netstandard2.0/PublicAPI.Shipped.txt | 1 + 3 files changed, 3 insertions(+), 1 deletion(-) diff --git a/Directory.Packages.props b/Directory.Packages.props index 77ac7fafc2..e241f6e0bd 100644 --- a/Directory.Packages.props +++ b/Directory.Packages.props @@ -2,7 +2,7 @@ true - 0.18.0 + 0.7.0-alpha 4.61.0 diff --git a/src/client/Microsoft.Identity.Client/PublicApi/net8.0/PublicAPI.Shipped.txt b/src/client/Microsoft.Identity.Client/PublicApi/net8.0/PublicAPI.Shipped.txt index 9703719173..91f5e26da1 100644 --- a/src/client/Microsoft.Identity.Client/PublicApi/net8.0/PublicAPI.Shipped.txt +++ b/src/client/Microsoft.Identity.Client/PublicApi/net8.0/PublicAPI.Shipped.txt @@ -414,6 +414,7 @@ Microsoft.Identity.Client.BrokerOptions.MsaPassthrough.set -> void Microsoft.Identity.Client.BrokerOptions.OperatingSystems Microsoft.Identity.Client.BrokerOptions.OperatingSystems.None = 0 -> Microsoft.Identity.Client.BrokerOptions.OperatingSystems Microsoft.Identity.Client.BrokerOptions.OperatingSystems.Windows = 1 -> Microsoft.Identity.Client.BrokerOptions.OperatingSystems +Microsoft.Identity.Client.BrokerOptions.OperatingSystems.Linux = 2 -> Microsoft.Identity.Client.BrokerOptions.OperatingSystems Microsoft.Identity.Client.BrokerOptions.Title.get -> string Microsoft.Identity.Client.BrokerOptions.Title.set -> void Microsoft.Identity.Client.Cache.CacheData diff --git a/src/client/Microsoft.Identity.Client/PublicApi/netstandard2.0/PublicAPI.Shipped.txt b/src/client/Microsoft.Identity.Client/PublicApi/netstandard2.0/PublicAPI.Shipped.txt index b259daa973..05edb60382 100644 --- a/src/client/Microsoft.Identity.Client/PublicApi/netstandard2.0/PublicAPI.Shipped.txt +++ b/src/client/Microsoft.Identity.Client/PublicApi/netstandard2.0/PublicAPI.Shipped.txt @@ -414,6 +414,7 @@ Microsoft.Identity.Client.BrokerOptions.MsaPassthrough.set -> void Microsoft.Identity.Client.BrokerOptions.OperatingSystems Microsoft.Identity.Client.BrokerOptions.OperatingSystems.None = 0 -> Microsoft.Identity.Client.BrokerOptions.OperatingSystems Microsoft.Identity.Client.BrokerOptions.OperatingSystems.Windows = 1 -> Microsoft.Identity.Client.BrokerOptions.OperatingSystems +Microsoft.Identity.Client.BrokerOptions.OperatingSystems.Linux = 2 -> Microsoft.Identity.Client.BrokerOptions.OperatingSystems Microsoft.Identity.Client.BrokerOptions.Title.get -> string Microsoft.Identity.Client.BrokerOptions.Title.set -> void Microsoft.Identity.Client.Cache.CacheData From 78f8cc8b755975d4b7721663c15b0a543b79aee0 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Fri, 24 Jan 2025 16:20:29 -0800 Subject: [PATCH 020/137] Add download artifacts --- build/template-test-on-linux.yaml | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index bd5d466897..a923f79b59 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -11,6 +11,13 @@ steps: inputs: version: 8.x +- task: DownloadBuildArtifacts@0 + displayName: Download Build Artifacts + inputs: + artifactName: drop + itemPattern: 'drop/**' + downloadPath: $(Build.artifactstagingdirectory) + # VSTest@2 is supported only on Windows - script: | dotnet test **/Microsoft.Identity.Test.Unit/bin/**/net8.0/Microsoft.Identity.Test.Unit.dll --configuration Release --collect:"XPlat Code Coverage" --settings build/CodeCoverage.runsettings From f0034f2e87b4c378dd96fa8a24e7b4d1dca53c71 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Fri, 24 Jan 2025 17:01:55 -0800 Subject: [PATCH 021/137] update download path --- build/template-test-on-linux.yaml | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index a923f79b59..9f08bc11c3 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -12,13 +12,15 @@ steps: version: 8.x - task: DownloadBuildArtifacts@0 - displayName: Download Build Artifacts + displayName: Download Artifacts from Windows Build inputs: artifactName: drop itemPattern: 'drop/**' - downloadPath: $(Build.artifactstagingdirectory) + downloadPath: $(System.DefaultWorkingDirectory) # VSTest@2 is supported only on Windows - script: | + ls '$(System.DefaultWorkingDirectory)' + ls '$(System.DefaultWorkingDirectory)/drop/' dotnet test **/Microsoft.Identity.Test.Unit/bin/**/net8.0/Microsoft.Identity.Test.Unit.dll --configuration Release --collect:"XPlat Code Coverage" --settings build/CodeCoverage.runsettings displayName: 'Run unit tests .NET' From 7d67fa3f0eb97b97c82bc287921b0afa0669cd24 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Fri, 24 Jan 2025 17:22:30 -0800 Subject: [PATCH 022/137] use DownloadPipelineArtifact --- build/template-test-on-linux.yaml | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 9f08bc11c3..651933fa7e 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -11,12 +11,11 @@ steps: inputs: version: 8.x -- task: DownloadBuildArtifacts@0 +- task: DownloadPipelineArtifact@0 displayName: Download Artifacts from Windows Build inputs: artifactName: drop - itemPattern: 'drop/**' - downloadPath: $(System.DefaultWorkingDirectory) + downloadPath: $(System.DefaultWorkingDirectory)/drop # VSTest@2 is supported only on Windows - script: | From 9bf80bec6eca0048ba1df56c218abe67d32ae5fc Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 11:35:58 -0800 Subject: [PATCH 023/137] use MSBuild to restore sln on Linux --- build/template-test-on-linux.yaml | 35 +++++++++++++++++++++++++++---- 1 file changed, 31 insertions(+), 4 deletions(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 651933fa7e..5408b4efae 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -11,11 +11,38 @@ steps: inputs: version: 8.x -- task: DownloadPipelineArtifact@0 - displayName: Download Artifacts from Windows Build +- task: CmdLine@2 + displayName: 'Clear local NuGet cache' inputs: - artifactName: drop - downloadPath: $(System.DefaultWorkingDirectory)/drop + script: 'nuget locals all -clear' + +#Restore workload with the .NET Core CLI task +- task: DotNetCoreCLI@2 + displayName: 'dotnet workload restore for Desktop project' + inputs: + command: 'custom' + custom: 'workload' + arguments: 'restore .\src\client\Microsoft.Identity.Client.Desktop\Microsoft.Identity.Client.Desktop.csproj' + +- task: DotNetCoreCLI@2 + displayName: 'dotnet workload restore' + inputs: + command: 'custom' + custom: 'workload' + arguments: 'restore .\src\client\Microsoft.Identity.Client\Microsoft.Identity.Client.csproj' + +- task: MSBuild@1 + displayName: 'NuGet restore LibsAndSamples.sln' + inputs: + solution: 'LibsAndSamples.sln' + msbuildArguments: '/t:restore' + configuration: ${{ parameters.BuildConfiguration }}' + +# - task: DownloadPipelineArtifact@0 +# displayName: Download Artifacts from Windows Build +# inputs: +# artifactName: drop +# downloadPath: $(System.DefaultWorkingDirectory)/drop # VSTest@2 is supported only on Windows - script: | From cd281c409d2d081bbe520b09ef26a94c40df3509 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 11:41:58 -0800 Subject: [PATCH 024/137] try restore unit test first --- build/template-test-on-linux.yaml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 5408b4efae..225b75a768 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -32,9 +32,9 @@ steps: arguments: 'restore .\src\client\Microsoft.Identity.Client\Microsoft.Identity.Client.csproj' - task: MSBuild@1 - displayName: 'NuGet restore LibsAndSamples.sln' + displayName: 'NuGet restore Unit Test' inputs: - solution: 'LibsAndSamples.sln' + solution: 'tests/Microsoft.Identity.Test.Unit/Microsoft.Identity.Test.Unit.csproj' msbuildArguments: '/t:restore' configuration: ${{ parameters.BuildConfiguration }}' From ad07cde25b46fc1174536dab94a70fb79c23abae Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 11:47:35 -0800 Subject: [PATCH 025/137] Add new broker option to PublicAPI.Unshipped --- .../PublicApi/net462/PublicAPI.Unshipped.txt | 1 + .../PublicApi/net472/PublicAPI.Unshipped.txt | 1 + .../PublicApi/net8.0/PublicAPI.Shipped.txt | 1 - .../PublicApi/net8.0/PublicAPI.Unshipped.txt | 1 + .../PublicApi/netstandard2.0/PublicAPI.Shipped.txt | 1 - .../PublicApi/netstandard2.0/PublicAPI.Unshipped.txt | 1 + 6 files changed, 4 insertions(+), 2 deletions(-) diff --git a/src/client/Microsoft.Identity.Client/PublicApi/net462/PublicAPI.Unshipped.txt b/src/client/Microsoft.Identity.Client/PublicApi/net462/PublicAPI.Unshipped.txt index e69de29bb2..4ad03b5be9 100644 --- a/src/client/Microsoft.Identity.Client/PublicApi/net462/PublicAPI.Unshipped.txt +++ b/src/client/Microsoft.Identity.Client/PublicApi/net462/PublicAPI.Unshipped.txt @@ -0,0 +1 @@ +Microsoft.Identity.Client.BrokerOptions.OperatingSystems.Linux = 2 -> Microsoft.Identity.Client.BrokerOptions.OperatingSystems \ No newline at end of file diff --git a/src/client/Microsoft.Identity.Client/PublicApi/net472/PublicAPI.Unshipped.txt b/src/client/Microsoft.Identity.Client/PublicApi/net472/PublicAPI.Unshipped.txt index e69de29bb2..4ad03b5be9 100644 --- a/src/client/Microsoft.Identity.Client/PublicApi/net472/PublicAPI.Unshipped.txt +++ b/src/client/Microsoft.Identity.Client/PublicApi/net472/PublicAPI.Unshipped.txt @@ -0,0 +1 @@ +Microsoft.Identity.Client.BrokerOptions.OperatingSystems.Linux = 2 -> Microsoft.Identity.Client.BrokerOptions.OperatingSystems \ No newline at end of file diff --git a/src/client/Microsoft.Identity.Client/PublicApi/net8.0/PublicAPI.Shipped.txt b/src/client/Microsoft.Identity.Client/PublicApi/net8.0/PublicAPI.Shipped.txt index 91f5e26da1..9703719173 100644 --- a/src/client/Microsoft.Identity.Client/PublicApi/net8.0/PublicAPI.Shipped.txt +++ b/src/client/Microsoft.Identity.Client/PublicApi/net8.0/PublicAPI.Shipped.txt @@ -414,7 +414,6 @@ Microsoft.Identity.Client.BrokerOptions.MsaPassthrough.set -> void Microsoft.Identity.Client.BrokerOptions.OperatingSystems Microsoft.Identity.Client.BrokerOptions.OperatingSystems.None = 0 -> Microsoft.Identity.Client.BrokerOptions.OperatingSystems Microsoft.Identity.Client.BrokerOptions.OperatingSystems.Windows = 1 -> Microsoft.Identity.Client.BrokerOptions.OperatingSystems -Microsoft.Identity.Client.BrokerOptions.OperatingSystems.Linux = 2 -> Microsoft.Identity.Client.BrokerOptions.OperatingSystems Microsoft.Identity.Client.BrokerOptions.Title.get -> string Microsoft.Identity.Client.BrokerOptions.Title.set -> void Microsoft.Identity.Client.Cache.CacheData diff --git a/src/client/Microsoft.Identity.Client/PublicApi/net8.0/PublicAPI.Unshipped.txt b/src/client/Microsoft.Identity.Client/PublicApi/net8.0/PublicAPI.Unshipped.txt index e69de29bb2..94545ea595 100644 --- a/src/client/Microsoft.Identity.Client/PublicApi/net8.0/PublicAPI.Unshipped.txt +++ b/src/client/Microsoft.Identity.Client/PublicApi/net8.0/PublicAPI.Unshipped.txt @@ -0,0 +1 @@ +tests\Microsoft.Identity.Test.Unit\Microsoft.Identity.Test.Unit.csproj \ No newline at end of file diff --git a/src/client/Microsoft.Identity.Client/PublicApi/netstandard2.0/PublicAPI.Shipped.txt b/src/client/Microsoft.Identity.Client/PublicApi/netstandard2.0/PublicAPI.Shipped.txt index 05edb60382..b259daa973 100644 --- a/src/client/Microsoft.Identity.Client/PublicApi/netstandard2.0/PublicAPI.Shipped.txt +++ b/src/client/Microsoft.Identity.Client/PublicApi/netstandard2.0/PublicAPI.Shipped.txt @@ -414,7 +414,6 @@ Microsoft.Identity.Client.BrokerOptions.MsaPassthrough.set -> void Microsoft.Identity.Client.BrokerOptions.OperatingSystems Microsoft.Identity.Client.BrokerOptions.OperatingSystems.None = 0 -> Microsoft.Identity.Client.BrokerOptions.OperatingSystems Microsoft.Identity.Client.BrokerOptions.OperatingSystems.Windows = 1 -> Microsoft.Identity.Client.BrokerOptions.OperatingSystems -Microsoft.Identity.Client.BrokerOptions.OperatingSystems.Linux = 2 -> Microsoft.Identity.Client.BrokerOptions.OperatingSystems Microsoft.Identity.Client.BrokerOptions.Title.get -> string Microsoft.Identity.Client.BrokerOptions.Title.set -> void Microsoft.Identity.Client.Cache.CacheData diff --git a/src/client/Microsoft.Identity.Client/PublicApi/netstandard2.0/PublicAPI.Unshipped.txt b/src/client/Microsoft.Identity.Client/PublicApi/netstandard2.0/PublicAPI.Unshipped.txt index e69de29bb2..4ad03b5be9 100644 --- a/src/client/Microsoft.Identity.Client/PublicApi/netstandard2.0/PublicAPI.Unshipped.txt +++ b/src/client/Microsoft.Identity.Client/PublicApi/netstandard2.0/PublicAPI.Unshipped.txt @@ -0,0 +1 @@ +Microsoft.Identity.Client.BrokerOptions.OperatingSystems.Linux = 2 -> Microsoft.Identity.Client.BrokerOptions.OperatingSystems \ No newline at end of file From 3bb06a759a96dba1840351fdcf266a4e5b4cfb03 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 11:55:12 -0800 Subject: [PATCH 026/137] remove dependency --- build/template-build-and-run-all-tests.yaml | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/build/template-build-and-run-all-tests.yaml b/build/template-build-and-run-all-tests.yaml index 64b9c37214..b190917fa1 100644 --- a/build/template-build-and-run-all-tests.yaml +++ b/build/template-build-and-run-all-tests.yaml @@ -83,11 +83,7 @@ jobs: #Build and stage projects baseDefinitionId: '905' #this is the PR build and it is used as a baseline baseBranchRef: 'main' -- job: 'RunUnitTestsonLinux' - #strategy: - # parallel: 5 - dependsOn: - - 'BuildAndStageProjects' +- job: 'BuildandRunUnitTestsonLinux' pool: vmImage: 'ubuntu-22.04' demands: From f9aff19700a880edfb8c2c011dd95a3ab83dd44b Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 12:01:36 -0800 Subject: [PATCH 027/137] specify the msBuildVersion --- build/template-test-on-linux.yaml | 1 + 1 file changed, 1 insertion(+) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 225b75a768..0a867b9233 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -37,6 +37,7 @@ steps: solution: 'tests/Microsoft.Identity.Test.Unit/Microsoft.Identity.Test.Unit.csproj' msbuildArguments: '/t:restore' configuration: ${{ parameters.BuildConfiguration }}' + msBuildVersion: '17.0' # - task: DownloadPipelineArtifact@0 # displayName: Download Artifacts from Windows Build From cbed763a7e68a2da79365075b53b82a6ac5cccfc Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 12:21:01 -0800 Subject: [PATCH 028/137] use dotnet task --- build/template-test-on-linux.yaml | 18 ++++++++++++------ 1 file changed, 12 insertions(+), 6 deletions(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 0a867b9233..cacaf5040e 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -31,13 +31,19 @@ steps: custom: 'workload' arguments: 'restore .\src\client\Microsoft.Identity.Client\Microsoft.Identity.Client.csproj' -- task: MSBuild@1 - displayName: 'NuGet restore Unit Test' +- task: DotNetCoreCLI@2 + displayName: 'Build Unit Test' inputs: - solution: 'tests/Microsoft.Identity.Test.Unit/Microsoft.Identity.Test.Unit.csproj' - msbuildArguments: '/t:restore' - configuration: ${{ parameters.BuildConfiguration }}' - msBuildVersion: '17.0' + command: 'build' + projects: './tests/Microsoft.Identity.Test.Unit/Microsoft.Identity.Test.Unit.csproj' + +# - task: MSBuild@1 +# displayName: 'NuGet restore Unit Test' +# inputs: +# solution: 'tests/Microsoft.Identity.Test.Unit/Microsoft.Identity.Test.Unit.csproj' +# msbuildArguments: '/t:restore' +# configuration: ${{ parameters.BuildConfiguration }}' +# msBuildVersion: '17.0' # - task: DownloadPipelineArtifact@0 # displayName: Download Artifacts from Windows Build From a221a528f8b8b65f15952e7ec69dc4a4c18dde55 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 13:19:32 -0800 Subject: [PATCH 029/137] set enableWindowsTargeting --- .../Microsoft.Identity.Test.Unit.csproj | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/Microsoft.Identity.Test.Unit/Microsoft.Identity.Test.Unit.csproj b/tests/Microsoft.Identity.Test.Unit/Microsoft.Identity.Test.Unit.csproj index 275d5e892e..e12485ef97 100644 --- a/tests/Microsoft.Identity.Test.Unit/Microsoft.Identity.Test.Unit.csproj +++ b/tests/Microsoft.Identity.Test.Unit/Microsoft.Identity.Test.Unit.csproj @@ -10,7 +10,7 @@ Debug;Release;Debug + MobileApps AnyCPU;x64 - + true From 362aeaa755be389a35c40a0dab2af557a65cb4ae Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 13:43:33 -0800 Subject: [PATCH 030/137] build and run common test --- build/template-test-on-linux.yaml | 12 ++---------- .../Microsoft.Identity.Test.Unit.csproj | 1 - 2 files changed, 2 insertions(+), 11 deletions(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index cacaf5040e..5d9b5a9fba 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -16,14 +16,6 @@ steps: inputs: script: 'nuget locals all -clear' -#Restore workload with the .NET Core CLI task -- task: DotNetCoreCLI@2 - displayName: 'dotnet workload restore for Desktop project' - inputs: - command: 'custom' - custom: 'workload' - arguments: 'restore .\src\client\Microsoft.Identity.Client.Desktop\Microsoft.Identity.Client.Desktop.csproj' - - task: DotNetCoreCLI@2 displayName: 'dotnet workload restore' inputs: @@ -35,7 +27,7 @@ steps: displayName: 'Build Unit Test' inputs: command: 'build' - projects: './tests/Microsoft.Identity.Test.Unit/Microsoft.Identity.Test.Unit.csproj' + projects: './tests/Microsoft.Identity.Test.Common/Microsoft.Identity.Test.Common.csproj' # - task: MSBuild@1 # displayName: 'NuGet restore Unit Test' @@ -55,5 +47,5 @@ steps: - script: | ls '$(System.DefaultWorkingDirectory)' ls '$(System.DefaultWorkingDirectory)/drop/' - dotnet test **/Microsoft.Identity.Test.Unit/bin/**/net8.0/Microsoft.Identity.Test.Unit.dll --configuration Release --collect:"XPlat Code Coverage" --settings build/CodeCoverage.runsettings + dotnet test **/Microsoft.Identity.Test.Common/bin/**/net8.0/Microsoft.Identity.Test.Common.dll --configuration Release --collect:"XPlat Code Coverage" --settings build/CodeCoverage.runsettings displayName: 'Run unit tests .NET' diff --git a/tests/Microsoft.Identity.Test.Unit/Microsoft.Identity.Test.Unit.csproj b/tests/Microsoft.Identity.Test.Unit/Microsoft.Identity.Test.Unit.csproj index e12485ef97..eb6a842e0f 100644 --- a/tests/Microsoft.Identity.Test.Unit/Microsoft.Identity.Test.Unit.csproj +++ b/tests/Microsoft.Identity.Test.Unit/Microsoft.Identity.Test.Unit.csproj @@ -10,7 +10,6 @@ Debug;Release;Debug + MobileApps AnyCPU;x64 - true From ccbf9ce8e73d2de9c6c10076ea2b1b4208d4bb97 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 13:58:19 -0800 Subject: [PATCH 031/137] integration tests --- build/template-test-on-linux.yaml | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 5d9b5a9fba..42d6528038 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -27,7 +27,9 @@ steps: displayName: 'Build Unit Test' inputs: command: 'build' - projects: './tests/Microsoft.Identity.Test.Common/Microsoft.Identity.Test.Common.csproj' + projects: | + ./tests/Microsoft.Identity.Test.Common/Microsoft.Identity.Test.Common.csproj + ./tests/Microsoft.Identity.Test.Integration.NetCore/Microsoft.Identity.Test.Integration.NetCore.csproj # - task: MSBuild@1 # displayName: 'NuGet restore Unit Test' @@ -47,5 +49,5 @@ steps: - script: | ls '$(System.DefaultWorkingDirectory)' ls '$(System.DefaultWorkingDirectory)/drop/' - dotnet test **/Microsoft.Identity.Test.Common/bin/**/net8.0/Microsoft.Identity.Test.Common.dll --configuration Release --collect:"XPlat Code Coverage" --settings build/CodeCoverage.runsettings + dotnet test **/Microsoft.Identity.Test.Integration.NetCore/bin/**/net8.0/Microsoft.Identity.Test.Integration.NetCore.dll --configuration Release --collect:"XPlat Code Coverage" --settings build/CodeCoverage.runsettings displayName: 'Run unit tests .NET' From af8fb87577ea9c6db31dee6ab1ad2da9660dd295 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 14:02:00 -0800 Subject: [PATCH 032/137] build Integration --- build/template-test-on-linux.yaml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 42d6528038..5b54043de4 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -28,7 +28,7 @@ steps: inputs: command: 'build' projects: | - ./tests/Microsoft.Identity.Test.Common/Microsoft.Identity.Test.Common.csproj + # ./tests/Microsoft.Identity.Test.Common/Microsoft.Identity.Test.Common.csproj ./tests/Microsoft.Identity.Test.Integration.NetCore/Microsoft.Identity.Test.Integration.NetCore.csproj # - task: MSBuild@1 @@ -48,6 +48,6 @@ steps: # VSTest@2 is supported only on Windows - script: | ls '$(System.DefaultWorkingDirectory)' - ls '$(System.DefaultWorkingDirectory)/drop/' + # ls '$(System.DefaultWorkingDirectory)/drop/' dotnet test **/Microsoft.Identity.Test.Integration.NetCore/bin/**/net8.0/Microsoft.Identity.Test.Integration.NetCore.dll --configuration Release --collect:"XPlat Code Coverage" --settings build/CodeCoverage.runsettings displayName: 'Run unit tests .NET' From fb2190f175d60cd084b7e45dd4bc1600b0230a0f Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 14:10:02 -0800 Subject: [PATCH 033/137] fix typo --- build/template-test-on-linux.yaml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 5b54043de4..b245a47530 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -29,7 +29,7 @@ steps: command: 'build' projects: | # ./tests/Microsoft.Identity.Test.Common/Microsoft.Identity.Test.Common.csproj - ./tests/Microsoft.Identity.Test.Integration.NetCore/Microsoft.Identity.Test.Integration.NetCore.csproj + ./tests/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj # - task: MSBuild@1 # displayName: 'NuGet restore Unit Test' @@ -49,5 +49,5 @@ steps: - script: | ls '$(System.DefaultWorkingDirectory)' # ls '$(System.DefaultWorkingDirectory)/drop/' - dotnet test **/Microsoft.Identity.Test.Integration.NetCore/bin/**/net8.0/Microsoft.Identity.Test.Integration.NetCore.dll --configuration Release --collect:"XPlat Code Coverage" --settings build/CodeCoverage.runsettings + dotnet test **/Microsoft.Identity.Test.Integration.netcore/bin/**/net8.0/Microsoft.Identity.Test.Integration.NetCore.dll --configuration Release --collect:"XPlat Code Coverage" --settings build/CodeCoverage.runsettings displayName: 'Run unit tests .NET' From 65f444fa0dfb89d0084873e357e708d3099afcb0 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 14:13:46 -0800 Subject: [PATCH 034/137] update --- build/template-test-on-linux.yaml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index b245a47530..802f80674c 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -24,7 +24,7 @@ steps: arguments: 'restore .\src\client\Microsoft.Identity.Client\Microsoft.Identity.Client.csproj' - task: DotNetCoreCLI@2 - displayName: 'Build Unit Test' + displayName: 'Build Integration Test' inputs: command: 'build' projects: | @@ -49,5 +49,5 @@ steps: - script: | ls '$(System.DefaultWorkingDirectory)' # ls '$(System.DefaultWorkingDirectory)/drop/' - dotnet test **/Microsoft.Identity.Test.Integration.netcore/bin/**/net8.0/Microsoft.Identity.Test.Integration.NetCore.dll --configuration Release --collect:"XPlat Code Coverage" --settings build/CodeCoverage.runsettings + dotnet test **/Microsoft.Identity.Test.Integration.netcore/bin/**/net8*/Microsoft.Identity.Test.Integration.NetCore.dll --configuration Debug --collect:"XPlat Code Coverage" --settings build/CodeCoverage.runsettings displayName: 'Run unit tests .NET' From 4496fcb22d65f59c0fa267259690882d0c860e0c Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 14:20:42 -0800 Subject: [PATCH 035/137] add install keyvault --- build/template-test-on-linux.yaml | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 802f80674c..7d7bb9862b 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -6,6 +6,8 @@ parameters: steps: +- template: template-install-keyvault-secrets.yaml + - task: UseDotNet@2 displayName: 'Use the latest .NET 8' inputs: @@ -50,4 +52,4 @@ steps: ls '$(System.DefaultWorkingDirectory)' # ls '$(System.DefaultWorkingDirectory)/drop/' dotnet test **/Microsoft.Identity.Test.Integration.netcore/bin/**/net8*/Microsoft.Identity.Test.Integration.NetCore.dll --configuration Debug --collect:"XPlat Code Coverage" --settings build/CodeCoverage.runsettings - displayName: 'Run unit tests .NET' + displayName: 'Run Integration tests .NET' From 4f03c3cf8631df93688d0625fd80c46106371313 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 15:13:39 -0800 Subject: [PATCH 036/137] get cert pass --- build/template-install-keyvault-secrets.yaml | 15 +++++++++++---- build/template-test-on-linux.yaml | 2 ++ 2 files changed, 13 insertions(+), 4 deletions(-) diff --git a/build/template-install-keyvault-secrets.yaml b/build/template-install-keyvault-secrets.yaml index 0e9b83ddb8..d9128be0dd 100644 --- a/build/template-install-keyvault-secrets.yaml +++ b/build/template-install-keyvault-secrets.yaml @@ -16,11 +16,18 @@ steps: $kvSecretBytes = [System.Convert]::FromBase64String('$(LabAuth)') $certCollection = New-Object System.Security.Cryptography.X509Certificates.X509Certificate2Collection $certCollection.Import($kvSecretBytes, $null, [System.Security.Cryptography.X509Certificates.X509KeyStorageFlags]::Exportable) - - $protectedCertificateBytes = $certCollection.Export([System.Security.Cryptography.X509Certificates.X509ContentType]::Pkcs12) + $CertPass = '' + $protectedCertificateBytes = $certCollection.Export([System.Security.Cryptography.X509Certificates.X509ContentType]::Pkcs12, $CertPass) $pfxPath = '$(Build.SourcesDirectory)' + "\TestCert.pfx" [System.IO.File]::WriteAllBytes($pfxPath, $protectedCertificateBytes) - Import-PfxCertificate -FilePath $pfxPath -CertStoreLocation Cert:\LocalMachine\My - + if ($PSVersionTable.PSPlatform -eq 'Win32NT') { + # This block will only execute on Windows + Import-PfxCertificate -FilePath $pfxPath -CertStoreLocation "Cert:\LocalMachine\My" + } else { + Write-Output "This script is running on a non-Windows platform. Skipping Import-PfxCertificate." + } + Write-Host "Write $((Get-Item -Path $pfxPath).Length) PFX bytes to: $pfxPath" + Write-Host "##vso[task.setvariable variable=certPass;isSecret=true;isOutput=true]$CertPass" + name: generateLabCert displayName: 'Install Keyvault Secrets' diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 7d7bb9862b..89bb208859 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -53,3 +53,5 @@ steps: # ls '$(System.DefaultWorkingDirectory)/drop/' dotnet test **/Microsoft.Identity.Test.Integration.netcore/bin/**/net8*/Microsoft.Identity.Test.Integration.NetCore.dll --configuration Debug --collect:"XPlat Code Coverage" --settings build/CodeCoverage.runsettings displayName: 'Run Integration tests .NET' + env: + CERTIFICATE_PASSWORD: $(generateLabCert.certPass) \ No newline at end of file From 1ace40eca9caa81650ec1aaad400d1cd89598946 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 15:23:17 -0800 Subject: [PATCH 037/137] retry --- build/template-install-keyvault-secrets.yaml | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/build/template-install-keyvault-secrets.yaml b/build/template-install-keyvault-secrets.yaml index d9128be0dd..94554d0bdf 100644 --- a/build/template-install-keyvault-secrets.yaml +++ b/build/template-install-keyvault-secrets.yaml @@ -18,11 +18,10 @@ steps: $certCollection.Import($kvSecretBytes, $null, [System.Security.Cryptography.X509Certificates.X509KeyStorageFlags]::Exportable) $CertPass = '' $protectedCertificateBytes = $certCollection.Export([System.Security.Cryptography.X509Certificates.X509ContentType]::Pkcs12, $CertPass) - $pfxPath = '$(Build.SourcesDirectory)' + "\TestCert.pfx" + $pfxPath = '$(Build.SourcesDirectory)' + "/TestCert.pfx" [System.IO.File]::WriteAllBytes($pfxPath, $protectedCertificateBytes) if ($PSVersionTable.PSPlatform -eq 'Win32NT') { - # This block will only execute on Windows Import-PfxCertificate -FilePath $pfxPath -CertStoreLocation "Cert:\LocalMachine\My" } else { Write-Output "This script is running on a non-Windows platform. Skipping Import-PfxCertificate." From 53c13088c09d0cfc058d8b4664c974d95af4c2fe Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 15:54:29 -0800 Subject: [PATCH 038/137] directly read cert on Linux --- .../CertificateHelper.cs | 38 +++++++++++++------ 1 file changed, 26 insertions(+), 12 deletions(-) diff --git a/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs b/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs index 1c4519e621..b93e0fca6d 100644 --- a/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs +++ b/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs @@ -4,6 +4,8 @@ using System; using System.Security.Cryptography.X509Certificates; +using Microsoft.Identity.Client.PlatformsCommon.Shared; + namespace Microsoft.Identity.Test.LabInfrastructure { public static class CertificateHelper @@ -39,24 +41,36 @@ public static X509Certificate2 FindCertificateByName(string certName, StoreLocat { // Don't validate certs, since the test root isn't installed. const bool validateCerts = false; - using (var store = new X509Store(name, location)) { - store.Open(OpenFlags.ReadOnly); - X509Certificate2Collection collection = store.Certificates.Find(X509FindType.FindBySubjectName, certName, validateCerts); - - X509Certificate2 certToUse = null; - - // select the "freshest" certificate - foreach (X509Certificate2 cert in collection) + // Unix LocalMachine X509Store is limited to the Root and CertificateAuthority stores + if (DesktopOsHelper.IsWindows()) { - if (certToUse == null || cert.NotBefore > certToUse.NotBefore) + store.Open(OpenFlags.ReadOnly); + X509Certificate2Collection collection = store.Certificates.Find(X509FindType.FindBySubjectName, certName, validateCerts); + + X509Certificate2 certToUse = null; + + // select the "freshest" certificate + foreach (X509Certificate2 cert in collection) { - certToUse = cert; + if (certToUse == null || cert.NotBefore > certToUse.NotBefore) + { + certToUse = cert; + } } - } - return certToUse; + return certToUse; + } else if (DesktopOsHelper.IsLinux()) + { + var certPasswrod = Environment.GetEnvironmentVariable("CERTIFICATE_PASSWORD"); + var cert = new X509Certificate2(location, certPasswrod); + return cert; + } + else + { + throw new PlatformNotSupportedException("This platform is not supported"); + } } } From c1db7a154d700ab0dd8d78c971b793a623bc3482 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 16:04:31 -0800 Subject: [PATCH 039/137] use env --- .../CertificateHelper.cs | 46 ++++++++----------- 1 file changed, 20 insertions(+), 26 deletions(-) diff --git a/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs b/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs index b93e0fca6d..a375a2ceac 100644 --- a/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs +++ b/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs @@ -2,10 +2,9 @@ // Licensed under the MIT License. using System; +using System.Runtime.InteropServices; using System.Security.Cryptography.X509Certificates; -using Microsoft.Identity.Client.PlatformsCommon.Shared; - namespace Microsoft.Identity.Test.LabInfrastructure { public static class CertificateHelper @@ -39,39 +38,34 @@ public static X509Certificate2 FindCertificateByName(string subjectName) /// with , or null if no matching certificate was found public static X509Certificate2 FindCertificateByName(string certName, StoreLocation location, StoreName name) { + // Unix LocalMachine X509Store is limited to the Root and CertificateAuthority stores + if (Environment.OSVersion.Platform == PlatformID.Unix) + { + var certPasswrod = Environment.GetEnvironmentVariable("CERTIFICATE_PASSWORD"); + var cert = new X509Certificate2(location, certPasswrod); + return cert; + } // Don't validate certs, since the test root isn't installed. const bool validateCerts = false; using (var store = new X509Store(name, location)) { - // Unix LocalMachine X509Store is limited to the Root and CertificateAuthority stores - if (DesktopOsHelper.IsWindows()) - { - store.Open(OpenFlags.ReadOnly); - X509Certificate2Collection collection = store.Certificates.Find(X509FindType.FindBySubjectName, certName, validateCerts); + store.Open(OpenFlags.ReadOnly); + X509Certificate2Collection collection = store.Certificates.Find(X509FindType.FindBySubjectName, certName, validateCerts); - X509Certificate2 certToUse = null; - - // select the "freshest" certificate - foreach (X509Certificate2 cert in collection) + X509Certificate2 certToUse = null; + + // select the "freshest" certificate + foreach (X509Certificate2 cert in collection) + { + if (certToUse == null || cert.NotBefore > certToUse.NotBefore) { - if (certToUse == null || cert.NotBefore > certToUse.NotBefore) - { - certToUse = cert; - } + certToUse = cert; } - - return certToUse; - } else if (DesktopOsHelper.IsLinux()) - { - var certPasswrod = Environment.GetEnvironmentVariable("CERTIFICATE_PASSWORD"); - var cert = new X509Certificate2(location, certPasswrod); - return cert; - } - else - { - throw new PlatformNotSupportedException("This platform is not supported"); } + return certToUse; + + } } } From 390115c6af2b07bb71a5ae338d561361a2817cfa Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 16:11:27 -0800 Subject: [PATCH 040/137] fix cert location --- build/template-install-keyvault-secrets.yaml | 1 + build/template-test-on-linux.yaml | 1 + .../CertificateHelper.cs | 3 ++- 3 files changed, 4 insertions(+), 1 deletion(-) diff --git a/build/template-install-keyvault-secrets.yaml b/build/template-install-keyvault-secrets.yaml index 94554d0bdf..1cb74483b8 100644 --- a/build/template-install-keyvault-secrets.yaml +++ b/build/template-install-keyvault-secrets.yaml @@ -27,6 +27,7 @@ steps: Write-Output "This script is running on a non-Windows platform. Skipping Import-PfxCertificate." } Write-Host "Write $((Get-Item -Path $pfxPath).Length) PFX bytes to: $pfxPath" + Write-Host "##vso[task.setvariable variable=certDir;isOutput=true]$pfxPath" Write-Host "##vso[task.setvariable variable=certPass;isSecret=true;isOutput=true]$CertPass" name: generateLabCert displayName: 'Install Keyvault Secrets' diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 89bb208859..ed8f01c577 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -54,4 +54,5 @@ steps: dotnet test **/Microsoft.Identity.Test.Integration.netcore/bin/**/net8*/Microsoft.Identity.Test.Integration.NetCore.dll --configuration Debug --collect:"XPlat Code Coverage" --settings build/CodeCoverage.runsettings displayName: 'Run Integration tests .NET' env: + CERTIFICATE_LOCATION: $(generateLabCert.certDir) CERTIFICATE_PASSWORD: $(generateLabCert.certPass) \ No newline at end of file diff --git a/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs b/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs index a375a2ceac..6a90e93a66 100644 --- a/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs +++ b/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs @@ -42,7 +42,8 @@ public static X509Certificate2 FindCertificateByName(string certName, StoreLocat if (Environment.OSVersion.Platform == PlatformID.Unix) { var certPasswrod = Environment.GetEnvironmentVariable("CERTIFICATE_PASSWORD"); - var cert = new X509Certificate2(location, certPasswrod); + var certLocation = Environment.GetEnvironmentVariable("CERTIFICATE_LOCATION"); + var cert = new X509Certificate2(certLocation, certPasswrod); return cert; } // Don't validate certs, since the test root isn't installed. From c19a643557fbc6d95e69faef2525e3301d4dcc9a Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 16:57:03 -0800 Subject: [PATCH 041/137] add utils to import dlls on Linux --- build/template-install-keyvault-secrets.yaml | 2 +- build/template-test-on-linux.yaml | 2 +- .../HeadlessTests/RuntimeBrokerTests.cs | 20 ++++--- .../Utils/TestUtils.cs | 54 +++++++++++++++++++ .../CertificateHelper.cs | 4 +- 5 files changed, 67 insertions(+), 15 deletions(-) create mode 100644 tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs diff --git a/build/template-install-keyvault-secrets.yaml b/build/template-install-keyvault-secrets.yaml index 1cb74483b8..297b4be99b 100644 --- a/build/template-install-keyvault-secrets.yaml +++ b/build/template-install-keyvault-secrets.yaml @@ -21,7 +21,7 @@ steps: $pfxPath = '$(Build.SourcesDirectory)' + "/TestCert.pfx" [System.IO.File]::WriteAllBytes($pfxPath, $protectedCertificateBytes) - if ($PSVersionTable.PSPlatform -eq 'Win32NT') { + if ([System.Environment]::OSVersion.Platform -eq 'Win32NT') { Import-PfxCertificate -FilePath $pfxPath -CertStoreLocation "Cert:\LocalMachine\My" } else { Write-Output "This script is running on a non-Windows platform. Skipping Import-PfxCertificate." diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index ed8f01c577..756c740810 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -51,7 +51,7 @@ steps: - script: | ls '$(System.DefaultWorkingDirectory)' # ls '$(System.DefaultWorkingDirectory)/drop/' - dotnet test **/Microsoft.Identity.Test.Integration.netcore/bin/**/net8*/Microsoft.Identity.Test.Integration.NetCore.dll --configuration Debug --collect:"XPlat Code Coverage" --settings build/CodeCoverage.runsettings + dotnet test **/Microsoft.Identity.Test.Integration.netcore/bin/**/net8*/Microsoft.Identity.Test.Integration.NetCore.dll --configuration Debug --settings build/CodeCoverage.runsettings displayName: 'Run Integration tests .NET' env: CERTIFICATE_LOCATION: $(generateLabCert.certDir) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs index 7ddb03bc42..2eb4b05fd5 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs @@ -26,6 +26,7 @@ using Microsoft.Identity.Test.Common.Core.Helpers; using Microsoft.Identity.Test.Common.Core.Mocks; using Microsoft.Identity.Test.Integration.Infrastructure; +using Microsoft.Identity.Test.Integration.Utils; using Microsoft.Identity.Test.LabInfrastructure; using Microsoft.VisualStudio.TestTools.UnitTesting; using NSubstitute; @@ -35,9 +36,6 @@ namespace Microsoft.Identity.Test.Integration.Broker [TestClass] public class RuntimeBrokerTests { - [DllImport("user32.dll")] - static extern IntPtr GetForegroundWindow(); - //This client id is for Azure CLI which is one of the only 2 clients that have PreAuth to use ssh cert feature string _SSH_ClientId = "04b07795-8ddb-461a-bbee-02f9e1bf7b46"; //SSH User impersonation scope required for this test @@ -200,7 +198,7 @@ public async Task WamUsernamePasswordRequestAsync() string[] scopes = { "User.Read" }; string[] expectedScopes = { "email", "offline_access", "openid", "profile", "User.Read" }; - IntPtr intPtr = GetForegroundWindow(); + IntPtr intPtr = TestUtils.GetWindowHandle(); Func windowHandleProvider = () => intPtr; @@ -247,7 +245,7 @@ await AssertException.TaskThrowsAsync( [TestMethod] public async Task WamWithSSHCertificateAuthenticationSchemeAsync() { - IntPtr intPtr = GetForegroundWindow(); + IntPtr intPtr = TestUtils.GetWindowHandle(); Func windowHandleProvider = () => intPtr; var labResponse = await LabUserHelper.GetDefaultUserAsync().ConfigureAwait(false); @@ -290,7 +288,7 @@ public async Task WamUsernamePasswordWithForceRefreshAsync() string[] scopes = { "User.Read" }; string[] expectedScopes = { "email", "offline_access", "openid", "profile", "User.Read" }; - IntPtr intPtr = GetForegroundWindow(); + IntPtr intPtr = TestUtils.GetWindowHandle(); Func windowHandleProvider = () => intPtr; IPublicClientApplication pca = PublicClientApplicationBuilder @@ -341,7 +339,7 @@ public async Task WamUsernamePasswordRequestAsync_WithPiiAsync() string[] scopes = { "User.Read" }; string[] expectedScopes = { "email", "offline_access", "openid", "profile", "User.Read" }; - IntPtr intPtr = GetForegroundWindow(); + IntPtr intPtr = TestUtils.GetWindowHandle(); Func windowHandleProvider = () => intPtr; @@ -394,7 +392,7 @@ public async Task WamListWindowsWorkAndSchoolAccountsAsync() string[] scopes = { "User.Read" }; string[] expectedScopes = { "email", "offline_access", "openid", "profile", "User.Read" }; - IntPtr intPtr = GetForegroundWindow(); + IntPtr intPtr = TestUtils.GetWindowHandle(); Func windowHandleProvider = () => intPtr; @@ -430,7 +428,7 @@ public async Task WamListWindowsWorkAndSchoolAccountsAsync() [TestMethod] public async Task WamAddDefaultScopesWhenNoScopesArePassedAsync(string scopes) { - IntPtr intPtr = GetForegroundWindow(); + IntPtr intPtr = TestUtils.GetWindowHandle(); Func windowHandleProvider = () => intPtr; @@ -461,7 +459,7 @@ public async Task WamUsernamePasswordPopTokenEnforcedWithCaOnValidResourceAsync( string[] scopes = { "https://msidlab4.sharepoint.com/user.read" }; - IntPtr intPtr = GetForegroundWindow(); + IntPtr intPtr = TestUtils.GetWindowHandle(); Func windowHandleProvider = () => intPtr; @@ -496,7 +494,7 @@ public async Task WamUsernamePasswordPopTokenEnforcedWithCaOnInValidResourceAsyn string[] scopes = { "user.read" }; - IntPtr intPtr = GetForegroundWindow(); + IntPtr intPtr = TestUtils.GetWindowHandle(); Func windowHandleProvider = () => intPtr; diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs new file mode 100644 index 0000000000..32f7dfaa8c --- /dev/null +++ b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs @@ -0,0 +1,54 @@ +using System; +using Microsoft.Identity.Client.Extensions.Msal; + +namespace Microsoft.Identity.Test.Integration.Utils +{ + public static class TestUtils + { + /// + /// Get the handle of the foreground window for Windows + /// + [DllImport("user32.dll")] + static extern IntPtr GetForegroundWindow(); + + // + /// Get the handle of the console window for Linux + /// + [DllImport("libX11")] + private static extern IntPtr XOpenDisplay(string display); + + [DllImport("libX11")] + private static extern IntPtr XRootWindow(IntPtr display, int screen); + + [DllImport("libX11")] + private static extern IntPtr XDefaultRootWindow(IntPtr display); + + /// + /// Get window handle on xplat + /// + public static IntPtr GetWindowHandle() + { + if (SharedUtilities.IsWindowsPlatform()) + { + return GetForegroundWindow(); + } + else if (SharedUtilities.IsLinuxPlatform()) + { + try { + return XRootWindow(XOpenDisplay(null), 0); + } catch (System.Exception ex) + { + Console.ForegroundColor = ConsoleColor.Red; + Console.WriteLine(ex.ToString()); + Console.ResetColor(); + } + return IntPtr.Zero; + } + else + { + throw new PlatformNotSupportedException("Cannot get window handle on this platform."); + } + } + + } +} \ No newline at end of file diff --git a/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs b/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs index 6a90e93a66..5ccd5de60a 100644 --- a/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs +++ b/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs @@ -2,8 +2,8 @@ // Licensed under the MIT License. using System; -using System.Runtime.InteropServices; using System.Security.Cryptography.X509Certificates; +using Microsoft.Identity.Client.Extensions.Msal; namespace Microsoft.Identity.Test.LabInfrastructure { @@ -39,7 +39,7 @@ public static X509Certificate2 FindCertificateByName(string subjectName) public static X509Certificate2 FindCertificateByName(string certName, StoreLocation location, StoreName name) { // Unix LocalMachine X509Store is limited to the Root and CertificateAuthority stores - if (Environment.OSVersion.Platform == PlatformID.Unix) + if (SharedUtilities.IsLinuxPlatform()) { var certPasswrod = Environment.GetEnvironmentVariable("CERTIFICATE_PASSWORD"); var certLocation = Environment.GetEnvironmentVariable("CERTIFICATE_LOCATION"); From f81e5e7e0a74260ee8400ffe90b4e3b165df1dc6 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 17:05:10 -0800 Subject: [PATCH 042/137] include extension project for testing --- .../Microsoft.Identity.Test.LabInfrastructure.csproj | 1 + 1 file changed, 1 insertion(+) diff --git a/tests/Microsoft.Identity.Test.LabInfrastructure/Microsoft.Identity.Test.LabInfrastructure.csproj b/tests/Microsoft.Identity.Test.LabInfrastructure/Microsoft.Identity.Test.LabInfrastructure.csproj index 7c8ed47cba..cb491f52d7 100644 --- a/tests/Microsoft.Identity.Test.LabInfrastructure/Microsoft.Identity.Test.LabInfrastructure.csproj +++ b/tests/Microsoft.Identity.Test.LabInfrastructure/Microsoft.Identity.Test.LabInfrastructure.csproj @@ -17,6 +17,7 @@ Microsoft.Identity.Client + From 6eae017c47d51e55927cef141a5a8c4f30d1083a Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 19:23:25 -0800 Subject: [PATCH 043/137] conditional build --- .../Utils/TestUtils.cs | 29 +++++++++---------- 1 file changed, 14 insertions(+), 15 deletions(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs index 32f7dfaa8c..cf6ca684ce 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs @@ -8,12 +8,14 @@ public static class TestUtils /// /// Get the handle of the foreground window for Windows /// +#if WINDOWS [DllImport("user32.dll")] static extern IntPtr GetForegroundWindow(); - - // +#endif + /// /// Get the handle of the console window for Linux /// +#if LINUX [DllImport("libX11")] private static extern IntPtr XOpenDisplay(string display); @@ -22,32 +24,29 @@ public static class TestUtils [DllImport("libX11")] private static extern IntPtr XDefaultRootWindow(IntPtr display); - +#endif /// /// Get window handle on xplat /// public static IntPtr GetWindowHandle() { - if (SharedUtilities.IsWindowsPlatform()) - { + #if WINDOWS return GetForegroundWindow(); - } - else if (SharedUtilities.IsLinuxPlatform()) - { - try { + #elif LINUX + try + { return XRootWindow(XOpenDisplay(null), 0); - } catch (System.Exception ex) + } + catch (System.Exception ex) { Console.ForegroundColor = ConsoleColor.Red; Console.WriteLine(ex.ToString()); Console.ResetColor(); + return IntPtr.Zero; } - return IntPtr.Zero; - } - else - { + #else throw new PlatformNotSupportedException("Cannot get window handle on this platform."); - } + #endif } } From 2b2f8271e3d7492a5dd557cc9d43f6db11333df8 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 21:44:15 -0800 Subject: [PATCH 044/137] install deps --- build/linux-install-deps.sh | 52 +++++++++++++++++++ build/template-test-on-linux.yaml | 7 +++ .../PublicApi/net8.0/PublicAPI.Unshipped.txt | 2 +- 3 files changed, 60 insertions(+), 1 deletion(-) create mode 100644 build/linux-install-deps.sh diff --git a/build/linux-install-deps.sh b/build/linux-install-deps.sh new file mode 100644 index 0000000000..9d409e16d7 --- /dev/null +++ b/build/linux-install-deps.sh @@ -0,0 +1,52 @@ +#!/bin/bash + +# Copyright (c) Microsoft Corporation. +# Licensed under the MIT License. + +# This script must be run elevated. Adding a sudo wrapper if needed. +if [ "$UID" -ne 0 ]; then + exec sudo "$0" "$@" +fi + +set -o errexit # Exit the script if any command returns a non-true return value + +if [ -f '/usr/bin/apt' ]; then + DEBIAN_FRONTEND=noninteractive + # Install quietly, accepting all packages and not overriding user configurations + PKGINSTALL_CMD='apt-get install -q -y -o Dpkg::Options::=--force-confold' + PACKAGE_MANAGER=apt + PKGEXISTS_CMD='dpkg -s' +elif [ -f '/usr/bin/yum' ]; then + PACKAGE_MANAGER=yum + PKGINSTALL_CMD='yum -y install' + PKGEXISTS_CMD='yum list installed' +else + echo 'Package system currently not supported.' + exit 2 +fi + +if [ $PACKAGE_MANAGER == 'apt' ]; then + apt-get update || true # If apt update fails, see if we can continue anyway + $PKGINSTALL_CMD \ + libx11-dev \ + dbus-x11 \ + x11-xserver-utils \ + libp11-kit-dev +fi + +echo "Installing JavaBroker" +LINUX_VERSION=$(sed -r -n -e 's/^VERSION_ID="?([^"]+)"?/\1/p' /etc/os-release) +LINUX_VERSION_MAIN=$(echo $LINUX_VERSION | sed 's/\([0-9]*\)\..*/\1/') + +if [ -f '/usr/bin/apt' ]; then + curl https://packages.microsoft.com/config/ubuntu/$LINUX_VERSION/prod.list | sudo sudo tee /etc/apt/trusted.gpg.d/microsoft.asc +else + $PKGINSTALL_CMD yum-utils + yum-config-manager --add-repo=https://packages.microsoft.com/config/rhel/$LINUX_VERSION_MAIN/prod.repo + rpm --import http://packages.microsoft.com/keys/microsoft.asc +fi +echo "Installing latest published JavaBroker package" +$PKGINSTALL_CMD $BROKER_PACKAGE_NAME + +xhost +SI:localuser:microsoft-identity-broker +exit 0 \ No newline at end of file diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 756c740810..1dfcd06a65 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -8,6 +8,13 @@ steps: - template: template-install-keyvault-secrets.yaml +- task: Bash@3 + displayName: Install broker and depenencies + inputs: + targetType: filePath + filePath: build/linux-install-deps.sh + condition: succeededOrFailed() + - task: UseDotNet@2 displayName: 'Use the latest .NET 8' inputs: diff --git a/src/client/Microsoft.Identity.Client/PublicApi/net8.0/PublicAPI.Unshipped.txt b/src/client/Microsoft.Identity.Client/PublicApi/net8.0/PublicAPI.Unshipped.txt index 94545ea595..4ad03b5be9 100644 --- a/src/client/Microsoft.Identity.Client/PublicApi/net8.0/PublicAPI.Unshipped.txt +++ b/src/client/Microsoft.Identity.Client/PublicApi/net8.0/PublicAPI.Unshipped.txt @@ -1 +1 @@ -tests\Microsoft.Identity.Test.Unit\Microsoft.Identity.Test.Unit.csproj \ No newline at end of file +Microsoft.Identity.Client.BrokerOptions.OperatingSystems.Linux = 2 -> Microsoft.Identity.Client.BrokerOptions.OperatingSystems \ No newline at end of file From 80b02dd5e70cd2f474807fae36c771e87f6f8468 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 21:49:43 -0800 Subject: [PATCH 045/137] install sudo --- build/linux-install-deps.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build/linux-install-deps.sh b/build/linux-install-deps.sh index 9d409e16d7..9e8b318f3f 100644 --- a/build/linux-install-deps.sh +++ b/build/linux-install-deps.sh @@ -2,7 +2,7 @@ # Copyright (c) Microsoft Corporation. # Licensed under the MIT License. - +apt install sudo # This script must be run elevated. Adding a sudo wrapper if needed. if [ "$UID" -ne 0 ]; then exec sudo "$0" "$@" From 44e221ac696cc25b5d6c572c774f630cca798dec Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 22:09:43 -0800 Subject: [PATCH 046/137] install --- build/template-test-on-linux.yaml | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 1dfcd06a65..436c0e2af1 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -11,9 +11,10 @@ steps: - task: Bash@3 displayName: Install broker and depenencies inputs: - targetType: filePath - filePath: build/linux-install-deps.sh - condition: succeededOrFailed() + targetType: 'inline' + script: | + chmod +x ./build/linux-install-deps.sh + ./build/linux-install-deps.sh - task: UseDotNet@2 displayName: 'Use the latest .NET 8' From 97b92dbd8ffbd66969bfee9cfed27f609cbcc32b Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 23:42:44 -0800 Subject: [PATCH 047/137] start xvfb --- build/template-test-on-linux.yaml | 120 ++++++++++++++++++++++++++++++ 1 file changed, 120 insertions(+) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 436c0e2af1..b998a1736e 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -16,6 +16,126 @@ steps: chmod +x ./build/linux-install-deps.sh ./build/linux-install-deps.sh +- task: Bash@3 + name: SetDbusSession + displayName: Set DBUS_SESSION_BUS_ADDRESS + inputs: + targetType: inline + script: | + echo "Setting DBUS_SESSION_BUS_ADDRESS" + # ensure that /var/lib/dbus/machine-id exists and has the uuid in it + sudo dbus-uuidgen --ensure + # Java broker end to end test needs the Dbus session to be user session address + if [ ${{ parameters.testType }} == 'end2end-broker' ]; then + # sudo usermod -aG dbus -u ${UID} + DBUS_SESSION_BUS_ADDRESS="unix:path=/run/user/${UID}/bus" + # enable session lingering for the user + sudo loginctl enable-linger ${USER} + # enable and start dbus service + sudo systemctl enable dbus.service + sudo systemctl start dbus.service + # make sure per-user instance of systemd is running + /usr/bin/dbus-daemon --session --address=systemd: --nofork --print-address --nopidfile --systemd-activation --syslog-only + else + eval `dbus-launch --sh-syntax` + fi + echo "dbus-launch finished" + + echo "##vso[task.setvariable variable=dbusSessionAddress;isOutput=true]$DBUS_SESSION_BUS_ADDRESS" + echo "Set dbusSessionAddress successfully" + echo "set DBUS_SESSION_BUS_ADDRESS=${DBUS_SESSION_BUS_ADDRESS}" + +- task: Bash@3 + name: SetTestKeyring + displayName: Set test key ring + timeoutInMinutes: 2 + inputs: + targetType: inline + script: | + echo "Setting DBUS_SESSION_BUS_ADDRESS" + echo "Set to DBUS_SESSION_BUS_ADDRESS=${DBUS_SESSION_BUS_ADDRESS}" + + killall -q -u "$(whoami)" gnome-keyring-daemon + echo "gnome-keyring-daemon was terminated" + + rm -f ~/.local/share/keyrings/login.keyring + echo "Login keyring deleted" + + _UNLOCK_KEYRING_DATA=`cat /dev/urandom | tr -dc 'a-zA-Z0-9' | fold -w 10 | head -n 1` + echo "_UNLOCK_KEYRING_DATA is set" + + eval $(echo -n "${_UNLOCK_KEYRING_DATA}" \ + | gnome-keyring-daemon --daemonize --login \ + | sed -e 's/^/export /') + echo "keyring daemon was set" + + unset _UNLOCK_KEYRING_DATA + /usr/bin/gnome-keyring-daemon --start --components=secrets + echo "keyring daemon started" + + secret-tool search --all version 1.0 + echo "secret-tool executed" + + echo "##vso[task.setvariable variable=keyRingControl;isOutput=true]$GNOME_KEYRING_CONTROL" + echo "GNOME_KEYRING_CONTROL was set." + env: + DBUS_SESSION_BUS_ADDRESS: $(SetDbusSession.dbusSessionAddress) + +# - task: Bash@3 +# displayName: Copy named semaphores +# inputs: +# targetType: inline +# script: | +# echo "Copying shm" +# mkdir -p $(Build.Repository.LocalPath)/_systemLogs/shm_start 2>/dev/null +# sudo cp -r /dev/shm/* $(Build.Repository.LocalPath)/_systemLogs/shm_start 2>/dev/null +# sudo rm -r /dev/shm/* 2>/dev/null +# exit 0 + +- task: Bash@3 + displayName: Start Xvfb server and launch GUI + inputs: + targetType: inline + script: | + if [ -f '/usr/bin/apt' ]; then + sudo chmod 777 /etc/systemd/system/ + sudo rm -f /etc/systemd/system/xvfb.service + sudo touch /etc/systemd/system/xvfb.service + sudo chmod 777 /etc/systemd/system/xvfb.service + echo '[unit]' | sudo tee -a /etc/systemd/system/xvfb.service + echo 'Description=X Virtual Frame Buffer Service' | sudo tee -a /etc/systemd/system/xvfb.service + echo 'After=network.target' | sudo tee -a /etc/systemd/system/xvfb.service + echo '[Service]' | sudo tee -a /etc/systemd/system/xvfb.service + echo 'ExecStart=/usr/bin/Xvfb :99 -screen 0 1024x768x24' | sudo tee -a /etc/systemd/system/xvfb.service + echo 'Restart=always' | sudo tee -a /etc/systemd/system/xvfb.service + echo '[Install]' | sudo tee -a /etc/systemd/system/xvfb.service + echo 'WantedBy=multi-user.target' | sudo tee -a /etc/systemd/system/xvfb.service + + sudo systemctl enable /etc/systemd/system/xvfb.service + sudo service xvfb start + + wget -qO- https://packages.microsoft.com/keys/microsoft.asc | gpg --dearmor > packages.microsoft.gpg + sudo install -D -o root -g root -m 644 packages.microsoft.gpg /etc/apt/keyrings/packages.microsoft.gpg + sudo sh -c 'echo "deb [arch=amd64,arm64,armhf signed-by=/etc/apt/keyrings/packages.microsoft.gpg] https://packages.microsoft.com/repos/code stable main" > /etc/apt/sources.list.d/vscode.list' + rm -f packages.microsoft.gpg + sudo apt update + sudo apt install code + export DISPLAY=:99 + elif [ -f '/usr/bin/yum' ]; then + # install packages for GUI test + sudo yum -y install xorg-x11-server-Xvfb mesa-libEGL-devel glx-utils mesa-dri-drivers xorg-x11-server-utils + Xvfb -ac ${DISPLAY} 2>/dev/null & + sudo rpm --import https://packages.microsoft.com/keys/microsoft.asc + sudo sh -c 'echo -e "[code]\nname=Visual Studio Code\nbaseurl=https://packages.microsoft.com/yumrepos/vscode\nenabled=1\ngpgcheck=1\ngpgkey=https://packages.microsoft.com/keys/microsoft.asc" > /etc/yum.repos.d/vscode.repo' + dnf check-update + sudo dnf -y install code + fi + + code . + dbus-update-activation-environment --systemd DISPLAY XAUTHORITY + env: + DBUS_SESSION_BUS_ADDRESS: $(SetDbusSession.dbusSessionAddress) + - task: UseDotNet@2 displayName: 'Use the latest .NET 8' inputs: From f6a5ff91840890afa232762f7ec807ba60d1ad3a Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 27 Jan 2025 23:59:39 -0800 Subject: [PATCH 048/137] update --- build/linux-install-deps.sh | 1 - build/template-test-on-linux.yaml | 1 + 2 files changed, 1 insertion(+), 1 deletion(-) diff --git a/build/linux-install-deps.sh b/build/linux-install-deps.sh index 9e8b318f3f..a24221975b 100644 --- a/build/linux-install-deps.sh +++ b/build/linux-install-deps.sh @@ -48,5 +48,4 @@ fi echo "Installing latest published JavaBroker package" $PKGINSTALL_CMD $BROKER_PACKAGE_NAME -xhost +SI:localuser:microsoft-identity-broker exit 0 \ No newline at end of file diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index b998a1736e..0b9af81c46 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -133,6 +133,7 @@ steps: code . dbus-update-activation-environment --systemd DISPLAY XAUTHORITY + xhost +SI:localuser:microsoft-identity-broker env: DBUS_SESSION_BUS_ADDRESS: $(SetDbusSession.dbusSessionAddress) From f43c5474c732102cd6fe37e7ed6d80d0cc408a8b Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 10:14:48 -0800 Subject: [PATCH 049/137] install libwebkit2gtk-4.0 --- Directory.Packages.props | 2 +- build/linux-install-deps.sh | 3 ++- .../PublicApi/net8.0-android/PublicAPI.Unshipped.txt | 1 + .../PublicApi/net8.0-ios/PublicAPI.Unshipped.txt | 1 + 4 files changed, 5 insertions(+), 2 deletions(-) diff --git a/Directory.Packages.props b/Directory.Packages.props index e241f6e0bd..77ac7fafc2 100644 --- a/Directory.Packages.props +++ b/Directory.Packages.props @@ -2,7 +2,7 @@ true - 0.7.0-alpha + 0.18.0 4.61.0 diff --git a/build/linux-install-deps.sh b/build/linux-install-deps.sh index a24221975b..859918f061 100644 --- a/build/linux-install-deps.sh +++ b/build/linux-install-deps.sh @@ -31,7 +31,8 @@ if [ $PACKAGE_MANAGER == 'apt' ]; then libx11-dev \ dbus-x11 \ x11-xserver-utils \ - libp11-kit-dev + libp11-kit-dev \ + libwebkit2gtk-4.0-dev fi echo "Installing JavaBroker" diff --git a/src/client/Microsoft.Identity.Client/PublicApi/net8.0-android/PublicAPI.Unshipped.txt b/src/client/Microsoft.Identity.Client/PublicApi/net8.0-android/PublicAPI.Unshipped.txt index e69de29bb2..4ad03b5be9 100644 --- a/src/client/Microsoft.Identity.Client/PublicApi/net8.0-android/PublicAPI.Unshipped.txt +++ b/src/client/Microsoft.Identity.Client/PublicApi/net8.0-android/PublicAPI.Unshipped.txt @@ -0,0 +1 @@ +Microsoft.Identity.Client.BrokerOptions.OperatingSystems.Linux = 2 -> Microsoft.Identity.Client.BrokerOptions.OperatingSystems \ No newline at end of file diff --git a/src/client/Microsoft.Identity.Client/PublicApi/net8.0-ios/PublicAPI.Unshipped.txt b/src/client/Microsoft.Identity.Client/PublicApi/net8.0-ios/PublicAPI.Unshipped.txt index e69de29bb2..4ad03b5be9 100644 --- a/src/client/Microsoft.Identity.Client/PublicApi/net8.0-ios/PublicAPI.Unshipped.txt +++ b/src/client/Microsoft.Identity.Client/PublicApi/net8.0-ios/PublicAPI.Unshipped.txt @@ -0,0 +1 @@ +Microsoft.Identity.Client.BrokerOptions.OperatingSystems.Linux = 2 -> Microsoft.Identity.Client.BrokerOptions.OperatingSystems \ No newline at end of file From 1106d991ab9749fb5c5353873f122cc899de4718 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 11:08:02 -0800 Subject: [PATCH 050/137] get window --- .../Utils/TestUtils.cs | 36 +++++++++---------- 1 file changed, 17 insertions(+), 19 deletions(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs index cf6ca684ce..298f2c8a35 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs @@ -1,5 +1,5 @@ using System; -using Microsoft.Identity.Client.Extensions.Msal; +using System.Runtime.InteropServices; namespace Microsoft.Identity.Test.Integration.Utils { @@ -8,14 +8,12 @@ public static class TestUtils /// /// Get the handle of the foreground window for Windows /// -#if WINDOWS [DllImport("user32.dll")] static extern IntPtr GetForegroundWindow(); -#endif + /// /// Get the handle of the console window for Linux /// -#if LINUX [DllImport("libX11")] private static extern IntPtr XOpenDisplay(string display); @@ -24,29 +22,29 @@ public static class TestUtils [DllImport("libX11")] private static extern IntPtr XDefaultRootWindow(IntPtr display); -#endif + /// /// Get window handle on xplat /// public static IntPtr GetWindowHandle() { - #if WINDOWS + if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows)) + { return GetForegroundWindow(); - #elif LINUX - try - { - return XRootWindow(XOpenDisplay(null), 0); - } - catch (System.Exception ex) + } + else if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux)) + { + IntPtr display = XOpenDisplay(null); + if (display == IntPtr.Zero) { - Console.ForegroundColor = ConsoleColor.Red; - Console.WriteLine(ex.ToString()); - Console.ResetColor(); - return IntPtr.Zero; + throw new Exception("Unable to open X display"); } - #else - throw new PlatformNotSupportedException("Cannot get window handle on this platform."); - #endif + return XDefaultRootWindow(display); + } + else + { + throw new PlatformNotSupportedException("This platform is not supported."); + } } } From 2dd7fe211a0cdfc90b5dc3fb480ac1e708cd73e8 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 11:43:06 -0800 Subject: [PATCH 051/137] install xvfb --- build/linux-install-deps.sh | 3 ++- build/template-test-on-linux.yaml | 2 +- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/build/linux-install-deps.sh b/build/linux-install-deps.sh index 859918f061..601f0b34dd 100644 --- a/build/linux-install-deps.sh +++ b/build/linux-install-deps.sh @@ -32,7 +32,8 @@ if [ $PACKAGE_MANAGER == 'apt' ]; then dbus-x11 \ x11-xserver-utils \ libp11-kit-dev \ - libwebkit2gtk-4.0-dev + libwebkit2gtk-4.0-dev \ + xvfb fi echo "Installing JavaBroker" diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 0b9af81c46..2bb156e356 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -120,7 +120,7 @@ steps: rm -f packages.microsoft.gpg sudo apt update sudo apt install code - export DISPLAY=:99 + export DISPLAY=:0 elif [ -f '/usr/bin/yum' ]; then # install packages for GUI test sudo yum -y install xorg-x11-server-Xvfb mesa-libEGL-devel glx-utils mesa-dri-drivers xorg-x11-server-utils From af35cf4eb030197d1433fb6cfbe8c4e11582b917 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 11:54:06 -0800 Subject: [PATCH 052/137] install systemd --- build/linux-install-deps.sh | 4 ++-- build/template-test-on-linux.yaml | 19 +++---------------- .../Utils/TestUtils.cs | 7 +------ 3 files changed, 6 insertions(+), 24 deletions(-) diff --git a/build/linux-install-deps.sh b/build/linux-install-deps.sh index 601f0b34dd..464e3db7c8 100644 --- a/build/linux-install-deps.sh +++ b/build/linux-install-deps.sh @@ -30,10 +30,10 @@ if [ $PACKAGE_MANAGER == 'apt' ]; then $PKGINSTALL_CMD \ libx11-dev \ dbus-x11 \ + libsystemd0 \ x11-xserver-utils \ libp11-kit-dev \ - libwebkit2gtk-4.0-dev \ - xvfb + libwebkit2gtk-4.0-dev fi echo "Installing JavaBroker" diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 2bb156e356..812a0f3e40 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -25,20 +25,7 @@ steps: echo "Setting DBUS_SESSION_BUS_ADDRESS" # ensure that /var/lib/dbus/machine-id exists and has the uuid in it sudo dbus-uuidgen --ensure - # Java broker end to end test needs the Dbus session to be user session address - if [ ${{ parameters.testType }} == 'end2end-broker' ]; then - # sudo usermod -aG dbus -u ${UID} - DBUS_SESSION_BUS_ADDRESS="unix:path=/run/user/${UID}/bus" - # enable session lingering for the user - sudo loginctl enable-linger ${USER} - # enable and start dbus service - sudo systemctl enable dbus.service - sudo systemctl start dbus.service - # make sure per-user instance of systemd is running - /usr/bin/dbus-daemon --session --address=systemd: --nofork --print-address --nopidfile --systemd-activation --syslog-only - else - eval `dbus-launch --sh-syntax` - fi + eval `dbus-launch --sh-syntax` echo "dbus-launch finished" echo "##vso[task.setvariable variable=dbusSessionAddress;isOutput=true]$DBUS_SESSION_BUS_ADDRESS" @@ -120,7 +107,7 @@ steps: rm -f packages.microsoft.gpg sudo apt update sudo apt install code - export DISPLAY=:0 + export DISPLAY=:99 elif [ -f '/usr/bin/yum' ]; then # install packages for GUI test sudo yum -y install xorg-x11-server-Xvfb mesa-libEGL-devel glx-utils mesa-dri-drivers xorg-x11-server-utils @@ -133,7 +120,7 @@ steps: code . dbus-update-activation-environment --systemd DISPLAY XAUTHORITY - xhost +SI:localuser:microsoft-identity-broker + xhost +SI:localuser env: DBUS_SESSION_BUS_ADDRESS: $(SetDbusSession.dbusSessionAddress) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs index 298f2c8a35..d81506d683 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs @@ -34,12 +34,7 @@ public static IntPtr GetWindowHandle() } else if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux)) { - IntPtr display = XOpenDisplay(null); - if (display == IntPtr.Zero) - { - throw new Exception("Unable to open X display"); - } - return XDefaultRootWindow(display); + return return XRootWindow(XOpenDisplay(null), 0); } else { From 2c6677619f85e3414ca1ddad680ab3be1c243717 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 12:02:06 -0800 Subject: [PATCH 053/137] comment some code --- build/linux-install-deps.sh | 24 ++++++++++++------------ build/template-test-on-linux.yaml | 2 +- 2 files changed, 13 insertions(+), 13 deletions(-) diff --git a/build/linux-install-deps.sh b/build/linux-install-deps.sh index 464e3db7c8..d329ab2b70 100644 --- a/build/linux-install-deps.sh +++ b/build/linux-install-deps.sh @@ -36,18 +36,18 @@ if [ $PACKAGE_MANAGER == 'apt' ]; then libwebkit2gtk-4.0-dev fi -echo "Installing JavaBroker" -LINUX_VERSION=$(sed -r -n -e 's/^VERSION_ID="?([^"]+)"?/\1/p' /etc/os-release) -LINUX_VERSION_MAIN=$(echo $LINUX_VERSION | sed 's/\([0-9]*\)\..*/\1/') +# echo "Installing JavaBroker" +# LINUX_VERSION=$(sed -r -n -e 's/^VERSION_ID="?([^"]+)"?/\1/p' /etc/os-release) +# LINUX_VERSION_MAIN=$(echo $LINUX_VERSION | sed 's/\([0-9]*\)\..*/\1/') -if [ -f '/usr/bin/apt' ]; then - curl https://packages.microsoft.com/config/ubuntu/$LINUX_VERSION/prod.list | sudo sudo tee /etc/apt/trusted.gpg.d/microsoft.asc -else - $PKGINSTALL_CMD yum-utils - yum-config-manager --add-repo=https://packages.microsoft.com/config/rhel/$LINUX_VERSION_MAIN/prod.repo - rpm --import http://packages.microsoft.com/keys/microsoft.asc -fi -echo "Installing latest published JavaBroker package" -$PKGINSTALL_CMD $BROKER_PACKAGE_NAME +# if [ -f '/usr/bin/apt' ]; then +# curl https://packages.microsoft.com/config/ubuntu/$LINUX_VERSION/prod.list | sudo sudo tee /etc/apt/trusted.gpg.d/microsoft.asc +# else +# $PKGINSTALL_CMD yum-utils +# yum-config-manager --add-repo=https://packages.microsoft.com/config/rhel/$LINUX_VERSION_MAIN/prod.repo +# rpm --import http://packages.microsoft.com/keys/microsoft.asc +# fi +# echo "Installing latest published JavaBroker package" +# $PKGINSTALL_CMD $BROKER_PACKAGE_NAME exit 0 \ No newline at end of file diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 812a0f3e40..b71768a5fb 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -120,7 +120,7 @@ steps: code . dbus-update-activation-environment --systemd DISPLAY XAUTHORITY - xhost +SI:localuser + # xhost +SI:localuser env: DBUS_SESSION_BUS_ADDRESS: $(SetDbusSession.dbusSessionAddress) From 3bb45fc6d5cbddada080722825d41352a8e2735a Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 12:38:59 -0800 Subject: [PATCH 054/137] fix typo --- .../Utils/TestUtils.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs index d81506d683..d6fbd4b1ad 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs @@ -34,7 +34,7 @@ public static IntPtr GetWindowHandle() } else if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux)) { - return return XRootWindow(XOpenDisplay(null), 0); + return XRootWindow(XOpenDisplay(null), 0); } else { From e438ce3288f26b0c0b1dbaaea7e5d2994897e2e6 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 13:53:53 -0800 Subject: [PATCH 055/137] add log --- build/template-test-on-linux.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index b71768a5fb..c754afbe1f 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -167,7 +167,7 @@ steps: - script: | ls '$(System.DefaultWorkingDirectory)' # ls '$(System.DefaultWorkingDirectory)/drop/' - dotnet test **/Microsoft.Identity.Test.Integration.netcore/bin/**/net8*/Microsoft.Identity.Test.Integration.NetCore.dll --configuration Debug --settings build/CodeCoverage.runsettings + dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --settings build/CodeCoverage.runsettings -l "console;verbosity=detailed" --blame-crash displayName: 'Run Integration tests .NET' env: CERTIFICATE_LOCATION: $(generateLabCert.certDir) From bacf045fb7a18dd0de03925f5c298530608eb91d Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 14:28:07 -0800 Subject: [PATCH 056/137] broker options for different platforms --- .../HeadlessTests/RuntimeBrokerTests.cs | 24 ++++++++++--------- .../Utils/TestUtils.cs | 16 +++++++++++++ 2 files changed, 29 insertions(+), 11 deletions(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs index 2eb4b05fd5..012f2bf78f 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs @@ -41,6 +41,8 @@ public class RuntimeBrokerTests //SSH User impersonation scope required for this test private string[] _SSH_scopes = new[] { "https://pas.windows.net/CheckMyAccess/Linux/user_impersonation" }; + private BrokerOptions _brokerOption = TestUtils.GetPlatformBroker(); + private string CreateJwk() { RSACryptoServiceProvider rsa = new RSACryptoServiceProvider(2048); @@ -68,7 +70,7 @@ public async Task WamSilentAuthUserInteractionRequiredAsync() .WithAuthority("https://login.microsoftonline.com/organizations"); IPublicClientApplication pca = pcaBuilder - .WithBroker(new BrokerOptions(BrokerOptions.OperatingSystems.Windows)) + .WithBroker(_brokerOption) .Build(); // Act @@ -103,7 +105,7 @@ public async Task ExtractNonceWithAuthParserAndValidateShrAsync() IPublicClientApplication pca = PublicClientApplicationBuilder .Create(labResponse.App.AppId) .WithAuthority(labResponse.Lab.Authority, "organizations") - .WithBroker(new BrokerOptions(BrokerOptions.OperatingSystems.Windows)) + .WithBroker(_brokerOption) .Build(); Assert.IsTrue(pca.IsProofOfPossessionSupportedByClient(), "Either the broker is not configured or it does not support POP."); @@ -142,7 +144,7 @@ public async Task WamInvalidROPC_ThrowsException_TestAsync() .Create(labResponse.App.AppId) .WithAuthority(labResponse.Lab.Authority, "organizations") .WithLogging(wastestLogger, enablePiiLogging: true) // it's important that the PII is turned on, otherwise context is 'pii' - .WithBroker(new BrokerOptions(BrokerOptions.OperatingSystems.Windows)) + .WithBroker(_brokerOption) .Build(); MsalServiceException ex = await AssertException.TaskThrowsAsync(() => @@ -174,7 +176,7 @@ public async Task WamSilentAuthLoginHintNoAccontInCacheAsync() .WithAuthority("https://login.microsoftonline.com/organizations"); IPublicClientApplication pca = pcaBuilder - .WithBroker(new BrokerOptions(BrokerOptions.OperatingSystems.Windows)) + .WithBroker(_brokerOption) .Build(); // Act @@ -206,7 +208,7 @@ public async Task WamUsernamePasswordRequestAsync() .Create(labResponse.App.AppId) .WithParentActivityOrWindow(windowHandleProvider) .WithAuthority(labResponse.Lab.Authority, "organizations") - .WithBroker(new BrokerOptions(BrokerOptions.OperatingSystems.Windows)) + .WithBroker(_brokerOption) .Build(); // Acquire token using username password @@ -254,7 +256,7 @@ public async Task WamWithSSHCertificateAuthenticationSchemeAsync() .WithTestLogging() .WithAuthority(labResponse.Lab.Authority, "organizations") .WithParentActivityOrWindow(windowHandleProvider) - .WithBroker(new BrokerOptions(BrokerOptions.OperatingSystems.Windows)) + .WithBroker(_brokerOption) .Build(); string jwk = CreateJwk(); @@ -295,7 +297,7 @@ public async Task WamUsernamePasswordWithForceRefreshAsync() .Create(labResponse.App.AppId) .WithParentActivityOrWindow(windowHandleProvider) .WithAuthority(labResponse.Lab.Authority, "organizations") - .WithBroker(new BrokerOptions(BrokerOptions.OperatingSystems.Windows)) + .WithBroker(_brokerOption) .Build(); // Acquire token using username password @@ -350,7 +352,7 @@ public async Task WamUsernamePasswordRequestAsync_WithPiiAsync() .WithParentActivityOrWindow(windowHandleProvider) .WithAuthority(labResponse.Lab.Authority, "organizations") .WithLogging(testLogger, enablePiiLogging: true) - .WithBroker(new BrokerOptions(BrokerOptions.OperatingSystems.Windows)) + .WithBroker(_brokerOption) .Build(); // Acquire token using username password @@ -436,7 +438,7 @@ public async Task WamAddDefaultScopesWhenNoScopesArePassedAsync(string scopes) .Create("43dfbb29-3683-4673-a66f-baba91798bd2") .WithAuthority("https://login.microsoftonline.com/organizations") .WithParentActivityOrWindow(windowHandleProvider) - .WithBroker(new BrokerOptions(BrokerOptions.OperatingSystems.Windows)) + .WithBroker(_brokerOption) .Build(); // Act @@ -467,7 +469,7 @@ public async Task WamUsernamePasswordPopTokenEnforcedWithCaOnValidResourceAsync( .Create(labResponse.App.AppId) .WithParentActivityOrWindow(windowHandleProvider) .WithAuthority(labResponse.Lab.Authority, "organizations") - .WithBroker(new BrokerOptions(BrokerOptions.OperatingSystems.Windows)) + .WithBroker(_brokerOption) .Build(); // Acquire token using username password with POP on a valid resource @@ -502,7 +504,7 @@ public async Task WamUsernamePasswordPopTokenEnforcedWithCaOnInValidResourceAsyn .Create(labResponse.App.AppId) .WithParentActivityOrWindow(windowHandleProvider) .WithAuthority(labResponse.Lab.Authority, "organizations") - .WithBroker(new BrokerOptions(BrokerOptions.OperatingSystems.Windows)) + .WithBroker(_brokerOption) .Build(); // Acquire token using username password with POP on a resource not in the CA policy diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs index d6fbd4b1ad..ffa8ffba80 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs @@ -1,5 +1,6 @@ using System; using System.Runtime.InteropServices; +using Microsoft.Identity.Client; namespace Microsoft.Identity.Test.Integration.Utils { @@ -42,5 +43,20 @@ public static IntPtr GetWindowHandle() } } + public static BrokerOptions GetPlatformBroker() { + if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows)) + { + return new BrokerOptions(BrokerOptions.OperatingSystems.Windows); + } + else if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux)) + { + return new BrokerOptions(BrokerOptions.OperatingSystems.Linux); + } + else + { + throw new PlatformNotSupportedException("This platform is not supported."); + } + } + } } \ No newline at end of file From fad45001f449a11c7738566726935a339173ab5b Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 15:55:46 -0800 Subject: [PATCH 057/137] try another logger --- .../Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs | 2 +- .../HeadlessTests/RuntimeBrokerTests.cs | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs b/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs index 4d11fd7451..1a947556dd 100644 --- a/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs +++ b/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs @@ -85,7 +85,7 @@ internal bool IsBrokerEnabledOnCurrentOs() if (EnabledOn.HasFlag(OperatingSystems.Windows) && DesktopOsHelper.IsWindows()) { return true; - } else if (DesktopOsHelper.IsLinux()) { + } else if (EnabledOn.HasFlag(OperatingSystems.Linux) && DesktopOsHelper.IsLinux()) { return true; } diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs index 012f2bf78f..4928c1f7e8 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs @@ -138,12 +138,12 @@ public async Task WamInvalidROPC_ThrowsException_TestAsync() { var labResponse = await LabUserHelper.GetDefaultUserAsync().ConfigureAwait(false); string[] scopes = { "User.Read" }; - WamLoggerValidator wastestLogger = new WamLoggerValidator(); + // WamLoggerValidator wastestLogger = new WamLoggerValidator(); IPublicClientApplication pca = PublicClientApplicationBuilder .Create(labResponse.App.AppId) .WithAuthority(labResponse.Lab.Authority, "organizations") - .WithLogging(wastestLogger, enablePiiLogging: true) // it's important that the PII is turned on, otherwise context is 'pii' + .WithLogging((x, y, z) => Console.WriteLine($"{x} {y}"), LogLevel.Verbose, true) // it's important that the PII is turned on, otherwise context is 'pii' .WithBroker(_brokerOption) .Build(); From 165d6c054b8340abd8e961aa7d9df27174fa6b9b Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 17:09:23 -0800 Subject: [PATCH 058/137] update --- .../RuntimeBroker.cs | 15 +++++++++++++-- .../HeadlessTests/RuntimeBrokerTests.cs | 5 +++-- 2 files changed, 16 insertions(+), 4 deletions(-) diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index 50cbf9ef53..6932107c88 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -39,7 +39,10 @@ internal class RuntimeBroker : IBroker { NativeInterop.LogLevel.Fatal, LogLevel.Error }, }; - public bool IsPopSupported => true; + /// + /// Pop is supported on Windows only + /// + public bool IsPopSupported => DesktopOsHelper.IsWindows(); /// /// Being a C API, MSAL runtime uses a "global init" and "global shutdown" approach. @@ -93,8 +96,16 @@ public RuntimeBroker( ApplicationConfiguration appConfig, ILoggerAdapter logger) { - _logger = logger ?? throw new ArgumentNullException(nameof(logger)); + _logger = logger ?? throw new ArgumentNullException("123212312321"); + if (s_lazyCore.Value == null) + { + throw new MsalClientException( + "wam_runtime_init_failed", + "MSAL runtime initialization failed. See https://aka.ms/msal-net-wam#troubleshooting", + s_initException); + } + if (_logger.PiiLoggingEnabled) { s_lazyCore.Value.EnablePii(_logger.PiiLoggingEnabled); diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs index 4928c1f7e8..92094f439e 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs @@ -138,12 +138,12 @@ public async Task WamInvalidROPC_ThrowsException_TestAsync() { var labResponse = await LabUserHelper.GetDefaultUserAsync().ConfigureAwait(false); string[] scopes = { "User.Read" }; - // WamLoggerValidator wastestLogger = new WamLoggerValidator(); + WamLoggerValidator wastestLogger = new WamLoggerValidator(); IPublicClientApplication pca = PublicClientApplicationBuilder .Create(labResponse.App.AppId) .WithAuthority(labResponse.Lab.Authority, "organizations") - .WithLogging((x, y, z) => Console.WriteLine($"{x} {y}"), LogLevel.Verbose, true) // it's important that the PII is turned on, otherwise context is 'pii' + .WithLogging(wastestLogger, enablePiiLogging: true) // it's important that the PII is turned on, otherwise context is 'pii' .WithBroker(_brokerOption) .Build(); @@ -201,6 +201,7 @@ public async Task WamUsernamePasswordRequestAsync() string[] expectedScopes = { "email", "offline_access", "openid", "profile", "User.Read" }; IntPtr intPtr = TestUtils.GetWindowHandle(); + Assert.IsNotNull(intPtr); Func windowHandleProvider = () => intPtr; From 7e3887f0bf0d744cb0a60c87fd87aa7817f5b963 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 17:35:09 -0800 Subject: [PATCH 059/137] add installation --- build/linux-install-deps.sh | 24 +++++++++---------- .../DeviceCodeFlowIntegrationTest.cs | 3 ++- 2 files changed, 14 insertions(+), 13 deletions(-) diff --git a/build/linux-install-deps.sh b/build/linux-install-deps.sh index d329ab2b70..464e3db7c8 100644 --- a/build/linux-install-deps.sh +++ b/build/linux-install-deps.sh @@ -36,18 +36,18 @@ if [ $PACKAGE_MANAGER == 'apt' ]; then libwebkit2gtk-4.0-dev fi -# echo "Installing JavaBroker" -# LINUX_VERSION=$(sed -r -n -e 's/^VERSION_ID="?([^"]+)"?/\1/p' /etc/os-release) -# LINUX_VERSION_MAIN=$(echo $LINUX_VERSION | sed 's/\([0-9]*\)\..*/\1/') +echo "Installing JavaBroker" +LINUX_VERSION=$(sed -r -n -e 's/^VERSION_ID="?([^"]+)"?/\1/p' /etc/os-release) +LINUX_VERSION_MAIN=$(echo $LINUX_VERSION | sed 's/\([0-9]*\)\..*/\1/') -# if [ -f '/usr/bin/apt' ]; then -# curl https://packages.microsoft.com/config/ubuntu/$LINUX_VERSION/prod.list | sudo sudo tee /etc/apt/trusted.gpg.d/microsoft.asc -# else -# $PKGINSTALL_CMD yum-utils -# yum-config-manager --add-repo=https://packages.microsoft.com/config/rhel/$LINUX_VERSION_MAIN/prod.repo -# rpm --import http://packages.microsoft.com/keys/microsoft.asc -# fi -# echo "Installing latest published JavaBroker package" -# $PKGINSTALL_CMD $BROKER_PACKAGE_NAME +if [ -f '/usr/bin/apt' ]; then + curl https://packages.microsoft.com/config/ubuntu/$LINUX_VERSION/prod.list | sudo sudo tee /etc/apt/trusted.gpg.d/microsoft.asc +else + $PKGINSTALL_CMD yum-utils + yum-config-manager --add-repo=https://packages.microsoft.com/config/rhel/$LINUX_VERSION_MAIN/prod.repo + rpm --import http://packages.microsoft.com/keys/microsoft.asc +fi +echo "Installing latest published JavaBroker package" +$PKGINSTALL_CMD $BROKER_PACKAGE_NAME exit 0 \ No newline at end of file diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/SeleniumTests/DeviceCodeFlowIntegrationTest.cs b/tests/Microsoft.Identity.Test.Integration.netcore/SeleniumTests/DeviceCodeFlowIntegrationTest.cs index cd341b3a9e..5bb6aaa179 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/SeleniumTests/DeviceCodeFlowIntegrationTest.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/SeleniumTests/DeviceCodeFlowIntegrationTest.cs @@ -9,6 +9,7 @@ using Microsoft.Identity.Test.Common; using Microsoft.Identity.Test.Common.Core.Helpers; using Microsoft.Identity.Test.Integration.Infrastructure; +using Microsoft.Identity.Test.Integration.Utils; using Microsoft.Identity.Test.LabInfrastructure; using Microsoft.Identity.Test.Unit; using Microsoft.VisualStudio.TestTools.UnitTesting; @@ -126,7 +127,7 @@ private async Task AcquireTokenWithDeviceCodeFlowAsync(LabResponse labResponse, private async Task AcquireTokenSilentAfterDeviceCodeFlowWithBrokerAsync(LabResponse labResponse, string userType) { Trace.WriteLine($"Calling AcquireTokenSilentAfterDeviceCodeFlowWithBrokerAsync with {0}", userType); - BrokerOptions options = new BrokerOptions(BrokerOptions.OperatingSystems.Windows); + BrokerOptions options = TestUtils.GetPlatformBroker(); var builder = PublicClientApplicationBuilder.Create(labResponse.App.AppId).WithTestLogging().WithBroker(options); switch (labResponse.User.AzureEnvironment) From f0a078535ee30e11d26342241d9e8ef4920b4c60 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 17:42:43 -0800 Subject: [PATCH 060/137] fix install broker bug --- build/linux-install-deps.sh | 1 + 1 file changed, 1 insertion(+) diff --git a/build/linux-install-deps.sh b/build/linux-install-deps.sh index 464e3db7c8..8752c2af0c 100644 --- a/build/linux-install-deps.sh +++ b/build/linux-install-deps.sh @@ -40,6 +40,7 @@ echo "Installing JavaBroker" LINUX_VERSION=$(sed -r -n -e 's/^VERSION_ID="?([^"]+)"?/\1/p' /etc/os-release) LINUX_VERSION_MAIN=$(echo $LINUX_VERSION | sed 's/\([0-9]*\)\..*/\1/') +BROKER_PACKAGE_NAME='microsoft-identity-broker' if [ -f '/usr/bin/apt' ]; then curl https://packages.microsoft.com/config/ubuntu/$LINUX_VERSION/prod.list | sudo sudo tee /etc/apt/trusted.gpg.d/microsoft.asc else From 2e334750909eb8ca3206e3b8283d72426609deac Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 20:02:59 -0800 Subject: [PATCH 061/137] add broker xhost --- build/linux-install-deps.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build/linux-install-deps.sh b/build/linux-install-deps.sh index 8752c2af0c..974c5487f3 100644 --- a/build/linux-install-deps.sh +++ b/build/linux-install-deps.sh @@ -50,5 +50,5 @@ else fi echo "Installing latest published JavaBroker package" $PKGINSTALL_CMD $BROKER_PACKAGE_NAME - +xhost +SI:localuser:microsoft-identity-broker exit 0 \ No newline at end of file From 80285f399b2f47c5d237d6069a9f6a3162eee95f Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 20:06:06 -0800 Subject: [PATCH 062/137] set DBUS_SESSION_BUS_ADDRESS --- build/template-test-on-linux.yaml | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index c754afbe1f..f4430c799b 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -25,7 +25,14 @@ steps: echo "Setting DBUS_SESSION_BUS_ADDRESS" # ensure that /var/lib/dbus/machine-id exists and has the uuid in it sudo dbus-uuidgen --ensure - eval `dbus-launch --sh-syntax` + DBUS_SESSION_BUS_ADDRESS="unix:path=/run/user/${UID}/bus" + # enable session lingering for the user + sudo loginctl enable-linger ${USER} + # enable and start dbus service + sudo systemctl enable dbus.service + sudo systemctl start dbus.service + # make sure per-user instance of systemd is running + /usr/bin/dbus-daemon --session --address=systemd: --nofork --print-address --nopidfile --systemd-activation --syslog-only echo "dbus-launch finished" echo "##vso[task.setvariable variable=dbusSessionAddress;isOutput=true]$DBUS_SESSION_BUS_ADDRESS" From 1c3f76b53d760e15710d9e33974b674ba03377b5 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 20:07:18 -0800 Subject: [PATCH 063/137] test --- build/linux-install-deps.sh | 2 +- build/template-test-on-linux.yaml | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/build/linux-install-deps.sh b/build/linux-install-deps.sh index 974c5487f3..8752c2af0c 100644 --- a/build/linux-install-deps.sh +++ b/build/linux-install-deps.sh @@ -50,5 +50,5 @@ else fi echo "Installing latest published JavaBroker package" $PKGINSTALL_CMD $BROKER_PACKAGE_NAME -xhost +SI:localuser:microsoft-identity-broker + exit 0 \ No newline at end of file diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index f4430c799b..8213106103 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -127,7 +127,7 @@ steps: code . dbus-update-activation-environment --systemd DISPLAY XAUTHORITY - # xhost +SI:localuser + xhost +SI:localuser:microsoft-identity-broker env: DBUS_SESSION_BUS_ADDRESS: $(SetDbusSession.dbusSessionAddress) From 37b9a6c88149cc7a0327a7576a6e66d3a6663b26 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 21:18:18 -0800 Subject: [PATCH 064/137] try fix crash --- .../HeadlessTests/RuntimeBrokerTests.cs | 15 ++++++++++----- .../Utils/TestUtils.cs | 10 +++++++++- 2 files changed, 19 insertions(+), 6 deletions(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs index 92094f439e..064b957f7e 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs @@ -18,6 +18,7 @@ using Microsoft.Identity.Client.ApiConfig; using Microsoft.Identity.Client.Broker; using Microsoft.Identity.Client.Core; +using Microsoft.Identity.Client.Extensions.Msal; using Microsoft.Identity.Client.OAuth2; using Microsoft.Identity.Client.SSHCertificates; using Microsoft.Identity.Client.UI; @@ -155,11 +156,15 @@ public async Task WamInvalidROPC_ThrowsException_TestAsync() .ExecuteAsync()) .ConfigureAwait(false); - Assert.AreEqual("0x2142008A", ex.AdditionalExceptionData[MsalException.BrokerErrorTag]); - Assert.AreEqual("User name is malformed.", ex.AdditionalExceptionData[MsalException.BrokerErrorContext]); // message might change. not a big deal - Assert.AreEqual("ApiContractViolation", ex.AdditionalExceptionData[MsalException.BrokerErrorStatus]); - Assert.AreEqual("3399811229", ex.AdditionalExceptionData[MsalException.BrokerErrorCode]); - Assert.IsNotNull(ex.AdditionalExceptionData[MsalException.BrokerTelemetry]); + if (SharedUtilities.IsLinuxPlatform()) { + Assert.Contains("illegal_argument_exception", ex.AdditionalExceptionData[MsalException.BrokerErrorContext]); + } else { + Assert.AreEqual("0x2142008A", ex.AdditionalExceptionData[MsalException.BrokerErrorTag]); + Assert.AreEqual("User name is malformed.", ex.AdditionalExceptionData[MsalException.BrokerErrorContext]); // message might change. not a big deal + Assert.AreEqual("ApiContractViolation", ex.AdditionalExceptionData[MsalException.BrokerErrorStatus]); + Assert.AreEqual("3399811229", ex.AdditionalExceptionData[MsalException.BrokerErrorCode]); + Assert.IsNotNull(ex.AdditionalExceptionData[MsalException.BrokerTelemetry]); + } } [IgnoreOnOneBranch] diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs index ffa8ffba80..34f82b29da 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs @@ -35,7 +35,15 @@ public static IntPtr GetWindowHandle() } else if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux)) { - return XRootWindow(XOpenDisplay(null), 0); + try { + return XRootWindow(XOpenDisplay(null), 0); + } catch (System.Exception ex) + { + Console.ForegroundColor = ConsoleColor.Red; + Console.WriteLine(ex.ToString()); + Console.ResetColor(); + } + return IntPtr.Zero; } else { From af22c02ed88d5cfa550d8833237c49796f497342 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 21:18:36 -0800 Subject: [PATCH 065/137] add test filter --- build/template-test-on-linux.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 8213106103..68fc91d56f 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -174,7 +174,7 @@ steps: - script: | ls '$(System.DefaultWorkingDirectory)' # ls '$(System.DefaultWorkingDirectory)/drop/' - dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --settings build/CodeCoverage.runsettings -l "console;verbosity=detailed" --blame-crash + dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --settings build/CodeCoverage.runsettings --filter FullyQualifiedName~Microsoft.Identity.Test.Integration.Broker -l "console;verbosity=detailed" --blame-crash displayName: 'Run Integration tests .NET' env: CERTIFICATE_LOCATION: $(generateLabCert.certDir) From c8b9745b8787d85cc9d4cb8b481c34c86f28e1b4 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 21:24:20 -0800 Subject: [PATCH 066/137] fix assert --- .../HeadlessTests/RuntimeBrokerTests.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs index 064b957f7e..cecafe74bd 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs @@ -157,7 +157,7 @@ public async Task WamInvalidROPC_ThrowsException_TestAsync() .ConfigureAwait(false); if (SharedUtilities.IsLinuxPlatform()) { - Assert.Contains("illegal_argument_exception", ex.AdditionalExceptionData[MsalException.BrokerErrorContext]); + StringAssert.Contains("illegal_argument_exception", ex.AdditionalExceptionData[MsalException.BrokerErrorContext]); } else { Assert.AreEqual("0x2142008A", ex.AdditionalExceptionData[MsalException.BrokerErrorTag]); Assert.AreEqual("User name is malformed.", ex.AdditionalExceptionData[MsalException.BrokerErrorContext]); // message might change. not a big deal From 295e33ec72bf213559577eaf17a9eb5ab18d8545 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 21:39:41 -0800 Subject: [PATCH 067/137] add more filter --- build/template-test-on-linux.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 68fc91d56f..c3bffbc80a 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -174,7 +174,7 @@ steps: - script: | ls '$(System.DefaultWorkingDirectory)' # ls '$(System.DefaultWorkingDirectory)/drop/' - dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --settings build/CodeCoverage.runsettings --filter FullyQualifiedName~Microsoft.Identity.Test.Integration.Broker -l "console;verbosity=detailed" --blame-crash + dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --settings build/CodeCoverage.runsettings --filter FullyQualifiedName~Microsoft.Identity.Test.Integration.Broker.WamUsernamePasswordRequestAsync -l "console;verbosity=detailed" --blame-crash displayName: 'Run Integration tests .NET' env: CERTIFICATE_LOCATION: $(generateLabCert.certDir) From ea5b9c470c67e5779012ea0825bd5e1b6cdcee93 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 21:44:45 -0800 Subject: [PATCH 068/137] runtime broker test --- build/template-test-on-linux.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index c3bffbc80a..3a33ab0f61 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -174,7 +174,7 @@ steps: - script: | ls '$(System.DefaultWorkingDirectory)' # ls '$(System.DefaultWorkingDirectory)/drop/' - dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --settings build/CodeCoverage.runsettings --filter FullyQualifiedName~Microsoft.Identity.Test.Integration.Broker.WamUsernamePasswordRequestAsync -l "console;verbosity=detailed" --blame-crash + dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --settings build/CodeCoverage.runsettings --filter FullyQualifiedName~Microsoft.Identity.Test.Integration.Broker.RuntimeBrokerTests.WamUsernamePasswordRequestAsync -l "console;verbosity=detailed" --blame-crash displayName: 'Run Integration tests .NET' env: CERTIFICATE_LOCATION: $(generateLabCert.certDir) From 732f1404624f4121221873fef5ec2f61662aa18f Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 21:59:07 -0800 Subject: [PATCH 069/137] get display --- .../Utils/TestUtils.cs | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs index 34f82b29da..fbbe60611d 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs @@ -36,7 +36,16 @@ public static IntPtr GetWindowHandle() else if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux)) { try { - return XRootWindow(XOpenDisplay(null), 0); + IntPtr display = XOpenDisplay(null); + if (display == IntPtr.Zero) + { + Console.WriteLine("No X display available. Running in headless mode."); + } + else + { + Console.WriteLine("X display is available."); + } + return display; } catch (System.Exception ex) { Console.ForegroundColor = ConsoleColor.Red; From 0f1f6fdf27fa732cc0fa0592b6d01838214175a8 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 22:15:11 -0800 Subject: [PATCH 070/137] test --- build/template-test-on-linux.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 3a33ab0f61..c99246020d 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -174,7 +174,7 @@ steps: - script: | ls '$(System.DefaultWorkingDirectory)' # ls '$(System.DefaultWorkingDirectory)/drop/' - dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --settings build/CodeCoverage.runsettings --filter FullyQualifiedName~Microsoft.Identity.Test.Integration.Broker.RuntimeBrokerTests.WamUsernamePasswordRequestAsync -l "console;verbosity=detailed" --blame-crash + dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --settings build/CodeCoverage.runsettings --filter FullyQualifiedName~Microsoft.Identity.Test.Integration.Broker.RuntimeBrokerTests.WamUsernamePasswordRequestAsync_WithPiiAsync -l "console;verbosity=detailed" --blame-crash displayName: 'Run Integration tests .NET' env: CERTIFICATE_LOCATION: $(generateLabCert.certDir) From ac50e1afc6afbdd465f3af47c6a5eb668ccc4085 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 22:24:52 -0800 Subject: [PATCH 071/137] remove filter --- build/template-test-on-linux.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index c99246020d..8213106103 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -174,7 +174,7 @@ steps: - script: | ls '$(System.DefaultWorkingDirectory)' # ls '$(System.DefaultWorkingDirectory)/drop/' - dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --settings build/CodeCoverage.runsettings --filter FullyQualifiedName~Microsoft.Identity.Test.Integration.Broker.RuntimeBrokerTests.WamUsernamePasswordRequestAsync_WithPiiAsync -l "console;verbosity=detailed" --blame-crash + dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --settings build/CodeCoverage.runsettings -l "console;verbosity=detailed" --blame-crash displayName: 'Run Integration tests .NET' env: CERTIFICATE_LOCATION: $(generateLabCert.certDir) From 4dd38de751a6f72f02ce17825e10cd736b64a283 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 23:23:54 -0800 Subject: [PATCH 072/137] disable some tests --- .../ClientCredentialsMtlsPopTests.cs | 1 + .../HeadlessTests/RuntimeBrokerTests.cs | 18 ++++++++++++---- .../Infrastructure/IgnoreOnOneBranch.cs | 21 +++++++++++++++++++ 3 files changed, 36 insertions(+), 4 deletions(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/ClientCredentialsMtlsPopTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/ClientCredentialsMtlsPopTests.cs index 55c924df51..a7398b5e53 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/ClientCredentialsMtlsPopTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/ClientCredentialsMtlsPopTests.cs @@ -24,6 +24,7 @@ public void TestInitialize() TestCommon.ResetInternalStaticCaches(); } + [IgnoreOnLinux] // POP is not supported on Linux [TestMethod] public async Task Sni_Gets_Pop_Token_Successfully_TestAsync() { diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs index cecafe74bd..4245b821d5 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs @@ -249,6 +249,7 @@ await AssertException.TaskThrowsAsync( .ConfigureAwait(false); } + [IgnoreOnLinux] // SSH Certs are not supported on Linux [IgnoreOnOneBranch] [TestMethod] public async Task WamWithSSHCertificateAuthenticationSchemeAsync() @@ -392,6 +393,7 @@ public async Task WamUsernamePasswordRequestAsync_WithPiiAsync() result = await pca.AcquireTokenSilent(scopes, account).ExecuteAsync().ConfigureAwait(false); } + [IgnoreOnLinux] // List Windows Work and School accounts is not supported on Linux [IgnoreOnOneBranch] [TestMethod] public async Task WamListWindowsWorkAndSchoolAccountsAsync() @@ -446,16 +448,23 @@ public async Task WamAddDefaultScopesWhenNoScopesArePassedAsync(string scopes) .WithParentActivityOrWindow(windowHandleProvider) .WithBroker(_brokerOption) .Build(); - // Act - var ex = await AssertException.TaskThrowsAsync( + if (SharedUtilities.IsLinuxPlatform()) { + var exLinux = await AssertException.TaskThrowsAsync( () => pca.AcquireTokenSilent(new string[] { scopes }, PublicClientApplication.OperatingSystemAccount) .ExecuteAsync()) .ConfigureAwait(false); - - Assert.IsTrue(!string.IsNullOrEmpty(ex.ErrorCode)); + StringAssert.Contains("requestedScopes is NULL or EMPTY", exLinux.AdditionalExceptionData[MsalException.BrokerErrorContext]); + } else { + var ex = await AssertException.TaskThrowsAsync( + () => pca.AcquireTokenSilent(new string[] { scopes }, PublicClientApplication.OperatingSystemAccount) + .ExecuteAsync()) + .ConfigureAwait(false); + Assert.IsTrue(!string.IsNullOrEmpty(ex.ErrorCode)); + } } + [IgnoreOnLinux] // POP is not supported on Linux [IgnoreOnOneBranch] [TestMethod] public async Task WamUsernamePasswordPopTokenEnforcedWithCaOnValidResourceAsync() @@ -490,6 +499,7 @@ public async Task WamUsernamePasswordPopTokenEnforcedWithCaOnValidResourceAsync( Assert.AreEqual(popUser, result.Account.Username); } + [IgnoreOnLinux] // POP are not supported on Linux [IgnoreOnOneBranch] [TestMethod] [ExpectedException(typeof(MsalUiRequiredException))] diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/Infrastructure/IgnoreOnOneBranch.cs b/tests/Microsoft.Identity.Test.Integration.netcore/Infrastructure/IgnoreOnOneBranch.cs index 16910bf777..93058d9613 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/Infrastructure/IgnoreOnOneBranch.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/Infrastructure/IgnoreOnOneBranch.cs @@ -6,6 +6,7 @@ using System.Linq; using System.Text; using System.Threading.Tasks; +using Microsoft.Identity.Client.Extensions.Msal; using Microsoft.VisualStudio.TestTools.UnitTesting; namespace Microsoft.Identity.Test.Integration.Infrastructure @@ -29,4 +30,24 @@ public override TestResult[] Execute(ITestMethod testMethod) #endif } } + + internal class IgnoreOnLinuxAttribute : TestMethodAttribute + { + public override TestResult[] Execute(ITestMethod testMethod) + { + if (SharedUtilities.IsLinuxPlatform()) { + return new[] + { + new TestResult + { + Outcome = UnitTestOutcome.Inconclusive, + TestFailureException = new AssertInconclusiveException( + $"Skipped on Linux") + } + }; + } else { + return base.Execute(testMethod); + } + } + } } From e88b1a451afe0f669575ca1a9ffa4cc0d4316e62 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 23:36:07 -0800 Subject: [PATCH 073/137] clean up some code --- .../BrokerExtension.cs | 20 +++---------------- .../RuntimeBroker.cs | 9 +-------- 2 files changed, 4 insertions(+), 25 deletions(-) diff --git a/src/client/Microsoft.Identity.Client.Broker/BrokerExtension.cs b/src/client/Microsoft.Identity.Client.Broker/BrokerExtension.cs index 36a11f7113..462f231cf6 100644 --- a/src/client/Microsoft.Identity.Client.Broker/BrokerExtension.cs +++ b/src/client/Microsoft.Identity.Client.Broker/BrokerExtension.cs @@ -71,29 +71,15 @@ public static PublicClientApplicationBuilder WithSsoPolicy(this PublicClientAppl private static void AddRuntimeSupport(PublicClientApplicationBuilder builder) { - if (DesktopOsHelper.IsWin10OrServerEquivalent()) + if (DesktopOsHelper.IsWin10OrServerEquivalent() || DesktopOsHelper.IsLinux()) { builder.Config.BrokerCreatorFunc = (uiParent, appConfig, logger) => { - logger.Info("[Runtime] WAM supported OS."); + logger.Info("[Runtime] Broker supported OS."); return new RuntimeBroker(uiParent, appConfig, logger); }; - } else if (DesktopOsHelper.IsRunningOnWsl()) { - builder.Config.BrokerCreatorFunc = - (uiParent, appConfig, logger) => - { - logger.Info("[Runtime] WAM supported OS WSL."); - return new RuntimeBroker(uiParent, appConfig, logger); - }; - } else if (DesktopOsHelper.IsLinux()) { - builder.Config.BrokerCreatorFunc = - (uiParent, appConfig, logger) => - { - logger.Info("[Runtime] Broker supported OS Linux."); - return new RuntimeBroker(uiParent, appConfig, logger); - }; - } + } else { builder.Config.BrokerCreatorFunc = diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index 6932107c88..317a404047 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -97,14 +97,7 @@ public RuntimeBroker( ILoggerAdapter logger) { - _logger = logger ?? throw new ArgumentNullException("123212312321"); - if (s_lazyCore.Value == null) - { - throw new MsalClientException( - "wam_runtime_init_failed", - "MSAL runtime initialization failed. See https://aka.ms/msal-net-wam#troubleshooting", - s_initException); - } + _logger = logger ?? throw new ArgumentNullException(nameof(logger)); if (_logger.PiiLoggingEnabled) { From a97ca2730062105d5c8fc9bd433f522a156dd37d Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 23:45:54 -0800 Subject: [PATCH 074/137] clean up unused code --- build/template-test-on-linux.yaml | 26 ------------------- .../RuntimeBroker.cs | 1 - 2 files changed, 27 deletions(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 8213106103..e6bcba8b06 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -75,17 +75,6 @@ steps: env: DBUS_SESSION_BUS_ADDRESS: $(SetDbusSession.dbusSessionAddress) -# - task: Bash@3 -# displayName: Copy named semaphores -# inputs: -# targetType: inline -# script: | -# echo "Copying shm" -# mkdir -p $(Build.Repository.LocalPath)/_systemLogs/shm_start 2>/dev/null -# sudo cp -r /dev/shm/* $(Build.Repository.LocalPath)/_systemLogs/shm_start 2>/dev/null -# sudo rm -r /dev/shm/* 2>/dev/null -# exit 0 - - task: Bash@3 displayName: Start Xvfb server and launch GUI inputs: @@ -156,21 +145,6 @@ steps: # ./tests/Microsoft.Identity.Test.Common/Microsoft.Identity.Test.Common.csproj ./tests/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj -# - task: MSBuild@1 -# displayName: 'NuGet restore Unit Test' -# inputs: -# solution: 'tests/Microsoft.Identity.Test.Unit/Microsoft.Identity.Test.Unit.csproj' -# msbuildArguments: '/t:restore' -# configuration: ${{ parameters.BuildConfiguration }}' -# msBuildVersion: '17.0' - -# - task: DownloadPipelineArtifact@0 -# displayName: Download Artifacts from Windows Build -# inputs: -# artifactName: drop -# downloadPath: $(System.DefaultWorkingDirectory)/drop - -# VSTest@2 is supported only on Windows - script: | ls '$(System.DefaultWorkingDirectory)' # ls '$(System.DefaultWorkingDirectory)/drop/' diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index 317a404047..eb8cca66fa 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -96,7 +96,6 @@ public RuntimeBroker( ApplicationConfiguration appConfig, ILoggerAdapter logger) { - _logger = logger ?? throw new ArgumentNullException(nameof(logger)); if (_logger.PiiLoggingEnabled) From 70b210785e4ec39931ef703da27706671cfa8a2e Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 28 Jan 2025 23:50:41 -0800 Subject: [PATCH 075/137] fix string assert --- .../HeadlessTests/RuntimeBrokerTests.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs index 4245b821d5..afb613f6a4 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs @@ -454,7 +454,7 @@ public async Task WamAddDefaultScopesWhenNoScopesArePassedAsync(string scopes) () => pca.AcquireTokenSilent(new string[] { scopes }, PublicClientApplication.OperatingSystemAccount) .ExecuteAsync()) .ConfigureAwait(false); - StringAssert.Contains("requestedScopes is NULL or EMPTY", exLinux.AdditionalExceptionData[MsalException.BrokerErrorContext]); + StringAssert.Contains(exLinux.AdditionalExceptionData[MsalException.BrokerErrorContext], "requestedScopes is NULL or EMPTY"); } else { var ex = await AssertException.TaskThrowsAsync( () => pca.AcquireTokenSilent(new string[] { scopes }, PublicClientApplication.OperatingSystemAccount) From c51f5fbfe37acdf4bd1769738ef172e470242ab2 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Wed, 29 Jan 2025 16:48:08 -0800 Subject: [PATCH 076/137] disable POP test on Linux --- .../ClientCredentialsMtlsPopTests.cs | 3 ++- .../HeadlessTests/PoPTests.NetFwk.cs | 24 ++++++++++++++++++- .../HeadlessTests/RuntimeBrokerTests.cs | 9 +++---- .../Infrastructure/IgnoreOnOneBranch.cs | 20 ---------------- 4 files changed, 30 insertions(+), 26 deletions(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/ClientCredentialsMtlsPopTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/ClientCredentialsMtlsPopTests.cs index a7398b5e53..0810388ff7 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/ClientCredentialsMtlsPopTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/ClientCredentialsMtlsPopTests.cs @@ -6,6 +6,7 @@ using Microsoft.Identity.Client; using Microsoft.Identity.Client.Internal; using Microsoft.Identity.Test.Common; +using Microsoft.Identity.Test.Common.Core.Helpers; using Microsoft.Identity.Test.Integration.Infrastructure; using Microsoft.Identity.Test.Integration.NetFx.Infrastructure; using Microsoft.VisualStudio.TestTools.UnitTesting; @@ -24,7 +25,7 @@ public void TestInitialize() TestCommon.ResetInternalStaticCaches(); } - [IgnoreOnLinux] // POP is not supported on Linux + [DoNotRunOnLinux] // POP is not supported on Linux [TestMethod] public async Task Sni_Gets_Pop_Token_Successfully_TestAsync() { diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs index bfe661bfca..5ec7d40f0f 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs @@ -55,12 +55,14 @@ public void TestInitialize() TestCommon.ResetInternalStaticCaches(); } + [DoNotRunOnLinux] // POP is not supported on Linux [RunOn(TargetFrameworks.NetCore)] public async Task PoP_MultipleKeys_Async() { await MultipleKeys_Async().ConfigureAwait(false); } + [DoNotRunOnLinux] // POP is not supported on Linux [RunOn(TargetFrameworks.NetCore)] public async Task PoP_BearerAndPoP_CanCoexist_Async() { @@ -68,6 +70,7 @@ public async Task PoP_BearerAndPoP_CanCoexist_Async() await BearerAndPoP_CanCoexist_Async().ConfigureAwait(false); } + [DoNotRunOnLinux] // POP is not supported on Linux [TestMethod] public async Task HappyPath_Async() { @@ -217,6 +220,7 @@ private async Task MultipleKeys_Async() result); } + [DoNotRunOnLinux] // POP is not supported on Linux [RunOn(TargetFrameworks.NetCore)] public async Task PopTestWithConfigObjectAsync() { @@ -254,6 +258,7 @@ public async Task PopTestWithConfigObjectAsync() Assert.AreEqual("RS256", alg, "The algorithm in the token header should be RS256"); } + [DoNotRunOnLinux] // POP is not supported on Linux [TestMethod] public async Task PopTestWithRSAAsync() { @@ -291,6 +296,7 @@ public async Task PopTestWithRSAAsync() Assert.AreEqual("RS256", alg, "The algorithm in the token header should be RS256"); } + [DoNotRunOnLinux] // POP is not supported on Linux [RunOn(TargetFrameworks.NetCore)] public async Task ROPC_PopTestWithRSAAsync() { @@ -323,6 +329,7 @@ public async Task ROPC_PopTestWithRSAAsync() } + [DoNotRunOnLinux] // POP is not supported on Linux [TestMethod] public async Task PopTest_ExternalWilsonSigning_Async() { @@ -388,7 +395,8 @@ public async Task PopTest_ExternalWilsonSigning_Async() TokenSource.Cache, result2.AuthenticationResultMetadata.TokenSource); } - + + [DoNotRunOnLinux] // POP is not supported on Linux [TestMethod] public async Task PopTestWithECDAsync() { @@ -427,6 +435,7 @@ public async Task PopTestWithECDAsync() result); } + [DoNotRunOnLinux] // POP is not supported on Linux [TestMethod] public async Task NewPOP_WithKeyIdOnly_Async() { @@ -520,6 +529,7 @@ public async Task NewPOP_WithKeyIdOnly_Async() result2.AuthenticationResultMetadata.TokenSource); } + [DoNotRunOnLinux] // POP is not supported on Linux [TestMethod] public async Task InMemoryCryptoProvider_AlgIsPS256() { @@ -662,6 +672,7 @@ public async Task InMemoryCryptoProvider_WithGraph() Assert.IsTrue(responseWithPopToken.IsSuccessStatusCode, "The response should be successful with the PoP token"); } + [DoNotRunOnLinux] // POP is not supported on Linux [TestMethod] public async Task PoPToken_ShouldHaveCorrectAlgorithm_PS256_Async() { @@ -700,6 +711,7 @@ public async Task PoPToken_ShouldHaveCorrectAlgorithm_PS256_Async() } #if NET_CORE + [DoNotRunOnLinux] // POP is not supported on Linux [IgnoreOnOneBranch] public async Task WamUsernamePasswordRequestWithPOPAsync() { @@ -760,6 +772,16 @@ public void CheckPopRuntimeBrokerSupportTest() Assert.IsFalse(app.IsProofOfPossessionSupportedByClient()); + // POP is not supported on Linux + pcaBuilder = PublicClientApplicationBuilder + .Create(TestConstants.ClientId); + + pcaBuilder.WithBroker(new BrokerOptions(BrokerOptions.OperatingSystems.Linux)); + + app = pcaBuilder.Build(); + + Assert.IsFalse(app.IsProofOfPossessionSupportedByClient()); + //Broker not configured app = PublicClientApplicationBuilder .Create(TestConstants.ClientId) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs index afb613f6a4..9138e98c1a 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs @@ -91,6 +91,7 @@ public async Task WamSilentAuthUserInteractionRequiredAsync() } } + [DoNotRunOnLinux] // POP is not supported on Linux [IgnoreOnOneBranch] [TestMethod] public async Task ExtractNonceWithAuthParserAndValidateShrAsync() @@ -249,7 +250,7 @@ await AssertException.TaskThrowsAsync( .ConfigureAwait(false); } - [IgnoreOnLinux] // SSH Certs are not supported on Linux + [DoNotRunOnLinux] // SSH Certs are not supported on Linux [IgnoreOnOneBranch] [TestMethod] public async Task WamWithSSHCertificateAuthenticationSchemeAsync() @@ -393,7 +394,7 @@ public async Task WamUsernamePasswordRequestAsync_WithPiiAsync() result = await pca.AcquireTokenSilent(scopes, account).ExecuteAsync().ConfigureAwait(false); } - [IgnoreOnLinux] // List Windows Work and School accounts is not supported on Linux + [DoNotRunOnLinux] // List Windows Work and School accounts is not supported on Linux [IgnoreOnOneBranch] [TestMethod] public async Task WamListWindowsWorkAndSchoolAccountsAsync() @@ -464,7 +465,7 @@ public async Task WamAddDefaultScopesWhenNoScopesArePassedAsync(string scopes) } } - [IgnoreOnLinux] // POP is not supported on Linux + [DoNotRunOnLinux] // POP is not supported on Linux [IgnoreOnOneBranch] [TestMethod] public async Task WamUsernamePasswordPopTokenEnforcedWithCaOnValidResourceAsync() @@ -499,7 +500,7 @@ public async Task WamUsernamePasswordPopTokenEnforcedWithCaOnValidResourceAsync( Assert.AreEqual(popUser, result.Account.Username); } - [IgnoreOnLinux] // POP are not supported on Linux + [DoNotRunOnLinux] // POP are not supported on Linux [IgnoreOnOneBranch] [TestMethod] [ExpectedException(typeof(MsalUiRequiredException))] diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/Infrastructure/IgnoreOnOneBranch.cs b/tests/Microsoft.Identity.Test.Integration.netcore/Infrastructure/IgnoreOnOneBranch.cs index 93058d9613..3c223b8717 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/Infrastructure/IgnoreOnOneBranch.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/Infrastructure/IgnoreOnOneBranch.cs @@ -30,24 +30,4 @@ public override TestResult[] Execute(ITestMethod testMethod) #endif } } - - internal class IgnoreOnLinuxAttribute : TestMethodAttribute - { - public override TestResult[] Execute(ITestMethod testMethod) - { - if (SharedUtilities.IsLinuxPlatform()) { - return new[] - { - new TestResult - { - Outcome = UnitTestOutcome.Inconclusive, - TestFailureException = new AssertInconclusiveException( - $"Skipped on Linux") - } - }; - } else { - return base.Execute(testMethod); - } - } - } } From ca8aca85a2ca7a986b2ad8527869b469b48bc3b1 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Wed, 29 Jan 2025 17:20:50 -0800 Subject: [PATCH 077/137] fix some tests --- .../MsalCacheStorageIntegrationTests.cs | 12 ++++-------- .../Infrastructure/IgnoreOnOneBranch.cs | 1 - .../CertificateHelper.cs | 3 +-- 3 files changed, 5 insertions(+), 11 deletions(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/MsalCacheStorageIntegrationTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/MsalCacheStorageIntegrationTests.cs index c309dbe284..3f2f7b9b8c 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/MsalCacheStorageIntegrationTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/MsalCacheStorageIntegrationTests.cs @@ -125,15 +125,12 @@ public void CacheStorageFactory_WithFallback_Linux() attribute2: new KeyValuePair("MsalClientVersion", "1.0.0.0")) .Build(); - // Tests run on machines without Libsecret Storage store = Storage.Create(storageWithKeyRing, logger: _logger); Assert.IsTrue(store.CacheAccessor is LinuxKeyringAccessor); - // ADO Linux test agents do not have libsecret installed by default - // If you run this test on a Linux box with UI / LibSecret, then this test will fail - // because the statement below will not throw. - AssertException.Throws( - () => store.VerifyPersistence()); + // Installed libsecret on ADO Linux test agents, please see build/linux-install-deps.sh + // and setup keyring on the agent, please see build/template-test-on-linux.yml + store.VerifyPersistence(); Storage unprotectedStore = Storage.Create(s_storageCreationProperties, _logger); Assert.IsTrue(unprotectedStore.CacheAccessor is FileAccessor); @@ -147,8 +144,7 @@ public void CacheStorageFactory_WithFallback_Linux() // Mimic another sdk client to check libsecret availability by calling // MsalCacheStorage.VerifyPeristence() -> LinuxKeyringAccessor.CreateForPersistenceValidation() - AssertException.Throws( - () => store.VerifyPersistence()); + store.VerifyPersistence(); // Verify above call doesn't delete existing cache file Assert.IsTrue(File.Exists(s_storageCreationProperties.CacheFilePath)); diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/Infrastructure/IgnoreOnOneBranch.cs b/tests/Microsoft.Identity.Test.Integration.netcore/Infrastructure/IgnoreOnOneBranch.cs index 3c223b8717..16910bf777 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/Infrastructure/IgnoreOnOneBranch.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/Infrastructure/IgnoreOnOneBranch.cs @@ -6,7 +6,6 @@ using System.Linq; using System.Text; using System.Threading.Tasks; -using Microsoft.Identity.Client.Extensions.Msal; using Microsoft.VisualStudio.TestTools.UnitTesting; namespace Microsoft.Identity.Test.Integration.Infrastructure diff --git a/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs b/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs index 5ccd5de60a..0a4f1892a0 100644 --- a/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs +++ b/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs @@ -65,8 +65,7 @@ public static X509Certificate2 FindCertificateByName(string certName, StoreLocat } return certToUse; - - + } } } From 0c008948d283f14f1bb3c29268dd6bdd249baf87 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Wed, 29 Jan 2025 19:22:47 -0800 Subject: [PATCH 078/137] test interactive sign in --- .../HeadlessTests/RuntimeBrokerTests.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs index 9138e98c1a..63af65e862 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs @@ -219,7 +219,7 @@ public async Task WamUsernamePasswordRequestAsync() .Build(); // Acquire token using username password - var result = await pca.AcquireTokenByUsernamePassword(scopes, labResponse.User.Upn, labResponse.User.GetOrFetchPassword()).ExecuteAsync().ConfigureAwait(false); + var result = await pca.AcquireTokenInteractive(scopes).WithLoginHint(labResponse.User.Upn).ExecuteAsync().ConfigureAwait(false); MsalAssert.AssertAuthResult(result, TokenSource.Broker, labResponse.Lab.TenantId, expectedScopes); Assert.IsNotNull(result.AuthenticationResultMetadata.Telemetry); From 1d41aaa0a7d15fee8d50d40bcd290b75c7154638 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Wed, 29 Jan 2025 20:02:42 -0800 Subject: [PATCH 079/137] try --- .../RuntimeBroker.cs | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index eb8cca66fa..1c893b25f0 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -133,12 +133,12 @@ public async Task AcquireTokenInteractiveAsync( Debug.Assert(s_lazyCore.Value != null, "Should not call this API if MSAL runtime init failed"); //need to provide a handle - if (_parentHandle == IntPtr.Zero) - { - throw new MsalClientException( - "window_handle_required", - "A window handle must be configured. See https://aka.ms/msal-net-wam#parent-window-handles"); - } + // if (_parentHandle == IntPtr.Zero) + // { + // throw new MsalClientException( + // "window_handle_required", + // "A window handle must be configured. See https://aka.ms/msal-net-wam#parent-window-handles"); + // } //if OperatingSystemAccount is passed then we use the user signed-in on the machine if (PublicClientApplication.IsOperatingSystemAccount(authenticationRequestParameters.Account)) From 04379d10b3cfcaa44ab72f3c5a78873290b6f8a2 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Wed, 29 Jan 2025 20:31:09 -0800 Subject: [PATCH 080/137] start xvfb --- build/template-test-on-linux.yaml | 1 + .../RuntimeBroker.cs | 12 ++++++------ 2 files changed, 7 insertions(+), 6 deletions(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index e6bcba8b06..e788683a44 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -103,6 +103,7 @@ steps: rm -f packages.microsoft.gpg sudo apt update sudo apt install code + Xvfb :99 -screen 0 1920x1080x24 & export DISPLAY=:99 elif [ -f '/usr/bin/yum' ]; then # install packages for GUI test diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index 1c893b25f0..eb8cca66fa 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -133,12 +133,12 @@ public async Task AcquireTokenInteractiveAsync( Debug.Assert(s_lazyCore.Value != null, "Should not call this API if MSAL runtime init failed"); //need to provide a handle - // if (_parentHandle == IntPtr.Zero) - // { - // throw new MsalClientException( - // "window_handle_required", - // "A window handle must be configured. See https://aka.ms/msal-net-wam#parent-window-handles"); - // } + if (_parentHandle == IntPtr.Zero) + { + throw new MsalClientException( + "window_handle_required", + "A window handle must be configured. See https://aka.ms/msal-net-wam#parent-window-handles"); + } //if OperatingSystemAccount is passed then we use the user signed-in on the machine if (PublicClientApplication.IsOperatingSystemAccount(authenticationRequestParameters.Account)) From 7a733c6a15c94ccf4558c19fb92ad311c74cb9fe Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Wed, 29 Jan 2025 20:41:19 -0800 Subject: [PATCH 081/137] add the current user to host --- build/template-test-on-linux.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index e788683a44..cd64e44dbf 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -103,7 +103,6 @@ steps: rm -f packages.microsoft.gpg sudo apt update sudo apt install code - Xvfb :99 -screen 0 1920x1080x24 & export DISPLAY=:99 elif [ -f '/usr/bin/yum' ]; then # install packages for GUI test @@ -117,6 +116,7 @@ steps: code . dbus-update-activation-environment --systemd DISPLAY XAUTHORITY + xhost +SI:localuser:$(whoami) xhost +SI:localuser:microsoft-identity-broker env: DBUS_SESSION_BUS_ADDRESS: $(SetDbusSession.dbusSessionAddress) From 266d27094d6c8bbead38e804cb2fe19c4eeba022 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Wed, 29 Jan 2025 21:15:15 -0800 Subject: [PATCH 082/137] update --- build/linux-install-deps.sh | 5 +++++ .../Utils/TestUtils.cs | 6 +++--- 2 files changed, 8 insertions(+), 3 deletions(-) diff --git a/build/linux-install-deps.sh b/build/linux-install-deps.sh index 8752c2af0c..63b7291503 100644 --- a/build/linux-install-deps.sh +++ b/build/linux-install-deps.sh @@ -31,7 +31,12 @@ if [ $PACKAGE_MANAGER == 'apt' ]; then libx11-dev \ dbus-x11 \ libsystemd0 \ + gnome-keyring \ + libsecret-tools \ + libsecret-1-dev \ + xdg-utils \ x11-xserver-utils \ + xorg \ libp11-kit-dev \ libwebkit2gtk-4.0-dev fi diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs index fbbe60611d..21fe658713 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs @@ -15,13 +15,13 @@ public static class TestUtils /// /// Get the handle of the console window for Linux /// - [DllImport("libX11")] + [DllImport("libX11.so.6")] private static extern IntPtr XOpenDisplay(string display); - [DllImport("libX11")] + [DllImport("libX11.so.6")] private static extern IntPtr XRootWindow(IntPtr display, int screen); - [DllImport("libX11")] + [DllImport("libX11.so.6")] private static extern IntPtr XDefaultRootWindow(IntPtr display); /// From 1fd20f3122150a0abda7c3ccba608d4b020eb289 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Thu, 30 Jan 2025 10:50:20 -0800 Subject: [PATCH 083/137] add list os accounts support --- .../Microsoft.Identity.Client.Broker/RuntimeBroker.cs | 2 +- .../Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs | 3 ++- tests/devapps/WAM/NetWSLWam/Class1.cs | 6 +++++- 3 files changed, 8 insertions(+), 3 deletions(-) diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index eb8cca66fa..3daec3dd82 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -480,7 +480,7 @@ public async Task> GetAccountsAsync( ICacheSessionManager cacheSessionManager, IInstanceDiscoveryManager instanceDiscoveryManager) { - if (!DesktopOsHelper.IsLinux() && !_wamOptions.ListOperatingSystemAccounts) + if (!_wamOptions.ListOperatingSystemAccounts) { _logger.Info("[RuntimeBroker] ListWindowsWorkAndSchoolAccounts option was not enabled."); return Array.Empty(); diff --git a/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs b/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs index 1a947556dd..1e28b942a7 100644 --- a/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs +++ b/src/client/Microsoft.Identity.Client/ApiConfig/BrokerOptions.cs @@ -75,8 +75,9 @@ internal static BrokerOptions CreateFromWindowsOptions(WindowsBrokerOptions winO public bool MsaPassthrough { get; set; } = false; /// - /// Currently only supported on Windows + /// Currently only supported on Windows and Linux /// Allows the Windows broker to list Work and School accounts as part of the + /// Linux broker will discover accounts as part of the /// public bool ListOperatingSystemAccounts { get; set; } diff --git a/tests/devapps/WAM/NetWSLWam/Class1.cs b/tests/devapps/WAM/NetWSLWam/Class1.cs index 23c00af45a..8a07843227 100644 --- a/tests/devapps/WAM/NetWSLWam/Class1.cs +++ b/tests/devapps/WAM/NetWSLWam/Class1.cs @@ -36,7 +36,11 @@ public static async Task InvokeBrokerAsync() var pca = PublicClientApplicationBuilder.Create("04f0c124-f2bc-4f59-8241-bf6df9866bbd") .WithAuthority("https://login.microsoftonline.com/common") .WithDefaultRedirectUri() - .WithBroker(new BrokerOptions(BrokerOptions.OperatingSystems.Linux)) + .WithBroker(new BrokerOptions(BrokerOptions.OperatingSystems.Linux){ + ListOperatingSystemAccounts = true, + MsaPassthrough = true, + Title = "MSAL WSL Test App" + }) .WithParentActivityOrWindow(consoleWindowHandleProvider) .WithLogging((x, y, z) => Console.WriteLine($"{x} {y}"), LogLevel.Verbose, true) .Build(); From e8ee2f3391a9c13332c463b6feabc746cc530a29 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Thu, 30 Jan 2025 11:23:06 -0800 Subject: [PATCH 084/137] change back --- .../HeadlessTests/RuntimeBrokerTests.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs index 081f03bb1e..366655ff84 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs @@ -222,7 +222,7 @@ public async Task WamUsernamePasswordRequestAsync() .Build(); // Acquire token using username password - var result = await pca.AcquireTokenInteractive(scopes).WithLoginHint(labResponse.User.Upn).ExecuteAsync().ConfigureAwait(false); + var result = await AcquireTokenByUsernamePassword(scopes, labResponse.User.Upn, labResponse.User.GetOrFetchPassword()).ExecuteAsync().ConfigureAwait(false); MsalAssert.AssertAuthResult(result, TokenSource.Broker, labResponse.Lab.TenantId, scopes); Assert.IsNotNull(result.AuthenticationResultMetadata.Telemetry); From 3361393de4e486597853eb00380945c657f1e7d3 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Thu, 30 Jan 2025 14:45:03 -0800 Subject: [PATCH 085/137] fix typo --- .../HeadlessTests/RuntimeBrokerTests.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs index 366655ff84..403a85dce4 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs @@ -222,7 +222,7 @@ public async Task WamUsernamePasswordRequestAsync() .Build(); // Acquire token using username password - var result = await AcquireTokenByUsernamePassword(scopes, labResponse.User.Upn, labResponse.User.GetOrFetchPassword()).ExecuteAsync().ConfigureAwait(false); + var result = await pca.AcquireTokenByUsernamePassword(scopes, labResponse.User.Upn, labResponse.User.GetOrFetchPassword()).ExecuteAsync().ConfigureAwait(false); MsalAssert.AssertAuthResult(result, TokenSource.Broker, labResponse.Lab.TenantId, scopes); Assert.IsNotNull(result.AuthenticationResultMetadata.Telemetry); From 77abed36c0e88b9027061d3bbbccb716c78a2f41 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Thu, 30 Jan 2025 17:14:52 -0800 Subject: [PATCH 086/137] fix test --- .../HeadlessTests/PoPTests.NetFwk.cs | 46 +++++++------------ 1 file changed, 17 insertions(+), 29 deletions(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs index ce698afe73..a65ff63c5b 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs @@ -16,6 +16,7 @@ using Microsoft.Identity.Client.AppConfig; using Microsoft.Identity.Client.AuthScheme.PoP; using Microsoft.Identity.Client.Extensibility; +using Microsoft.Identity.Client.Extensions.Msal; #if NET_CORE using Microsoft.Identity.Client.Broker; #endif @@ -752,43 +753,30 @@ public async Task WamUsernamePasswordRequestWithPOPAsync() public void CheckPopRuntimeBrokerSupportTest() { //Broker enabled - var pcaBuilder = PublicClientApplicationBuilder - .Create(TestConstants.ClientId); - - pcaBuilder = pcaBuilder.WithBroker(new BrokerOptions(BrokerOptions.OperatingSystems.Windows)); - - IPublicClientApplication app = pcaBuilder.Build(); - - Assert.IsTrue(app.IsProofOfPossessionSupportedByClient()); + if (SharedUtilities.IsWindowsPlatform()) { + CheckPopSupport(new BrokerOptions(BrokerOptions.OperatingSystems.Windows), true); + } //Broker disabled - pcaBuilder = PublicClientApplicationBuilder - .Create(TestConstants.ClientId); - - pcaBuilder.WithBroker(new BrokerOptions(BrokerOptions.OperatingSystems.None)); - - app = pcaBuilder.Build(); - - Assert.IsFalse(app.IsProofOfPossessionSupportedByClient()); + CheckPopSupport(new BrokerOptions(BrokerOptions.OperatingSystems.None), false); // POP is not supported on Linux - pcaBuilder = PublicClientApplicationBuilder - .Create(TestConstants.ClientId); - - pcaBuilder.WithBroker(new BrokerOptions(BrokerOptions.OperatingSystems.Linux)); - - app = pcaBuilder.Build(); + if (SharedUtilities.IsLinuxPlatform()) { + CheckPopSupport(new BrokerOptions(BrokerOptions.OperatingSystems.Linux), false); + } + } +#endif + private static void CheckPopSupport(BrokerOptions brokerOptions, bool isPopSupported) + { + var pcaBuilder = PublicClientApplicationBuilder + .Create(TestConstants.ClientId); - Assert.IsFalse(app.IsProofOfPossessionSupportedByClient()); + pcaBuilder = pcaBuilder.WithBroker(brokerOptions); - //Broker not configured - app = PublicClientApplicationBuilder - .Create(TestConstants.ClientId) - .Build(); + IPublicClientApplication app = pcaBuilder.Build(); - Assert.IsFalse(app.IsProofOfPossessionSupportedByClient()); + Assert.AreEqual(expected, app.IsProofOfPossessionSupportedByClient()); } -#endif private static X509Certificate2 GetCertificate() { From a53e8eafff94216983be79c53af3131661139e6e Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Thu, 30 Jan 2025 17:22:20 -0800 Subject: [PATCH 087/137] fix build error --- .../HeadlessTests/PoPTests.NetFwk.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs index a65ff63c5b..0cd6b217d0 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs @@ -775,7 +775,7 @@ private static void CheckPopSupport(BrokerOptions brokerOptions, bool isPopSuppo IPublicClientApplication app = pcaBuilder.Build(); - Assert.AreEqual(expected, app.IsProofOfPossessionSupportedByClient()); + Assert.AreEqual(isPopSupported, app.IsProofOfPossessionSupportedByClient()); } private static X509Certificate2 GetCertificate() From f37ffb4987e24fe3e7a42726430f8530c046b596 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Fri, 31 Jan 2025 10:48:07 -0800 Subject: [PATCH 088/137] fix Windows build --- .../HeadlessTests/PoPTests.NetFwk.cs | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs index 0cd6b217d0..3b44460bac 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs @@ -765,7 +765,7 @@ public void CheckPopRuntimeBrokerSupportTest() CheckPopSupport(new BrokerOptions(BrokerOptions.OperatingSystems.Linux), false); } } -#endif + private static void CheckPopSupport(BrokerOptions brokerOptions, bool isPopSupported) { var pcaBuilder = PublicClientApplicationBuilder @@ -777,6 +777,7 @@ private static void CheckPopSupport(BrokerOptions brokerOptions, bool isPopSuppo Assert.AreEqual(isPopSupported, app.IsProofOfPossessionSupportedByClient()); } +#endif private static X509Certificate2 GetCertificate() { From d42f7975d25abb779366779e05f5715ccb79bb7f Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 3 Feb 2025 14:58:48 -0800 Subject: [PATCH 089/137] use interactive flow --- build/template-build-and-run-all-tests.yaml | 2 +- build/template-test-on-linux.yaml | 5 ++-- .../RuntimeBroker.cs | 23 +++++++++++++++---- 3 files changed, 21 insertions(+), 9 deletions(-) diff --git a/build/template-build-and-run-all-tests.yaml b/build/template-build-and-run-all-tests.yaml index b190917fa1..1cbaa096a3 100644 --- a/build/template-build-and-run-all-tests.yaml +++ b/build/template-build-and-run-all-tests.yaml @@ -83,7 +83,7 @@ jobs: #Build and stage projects baseDefinitionId: '905' #this is the PR build and it is used as a baseline baseBranchRef: 'main' -- job: 'BuildandRunUnitTestsonLinux' +- job: 'BuildandRunIntegrationTestsonLinux' pool: vmImage: 'ubuntu-22.04' demands: diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index cd64e44dbf..5b58cfe769 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -143,13 +143,12 @@ steps: inputs: command: 'build' projects: | - # ./tests/Microsoft.Identity.Test.Common/Microsoft.Identity.Test.Common.csproj ./tests/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj + configuration: ${{ parameters.BuildConfiguration }} - script: | ls '$(System.DefaultWorkingDirectory)' - # ls '$(System.DefaultWorkingDirectory)/drop/' - dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --settings build/CodeCoverage.runsettings -l "console;verbosity=detailed" --blame-crash + dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --settings build/CodeCoverage.runsettings -l "console;verbosity=detailed" --filter FullyQualifiedName~Microsoft.Identity.Test.Integration.Broker.RuntimeBrokerTests.WamUsernamePasswordRequestAsync displayName: 'Run Integration tests .NET' env: CERTIFICATE_LOCATION: $(generateLabCert.certDir) diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index 3daec3dd82..2f9a523767 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -399,14 +399,27 @@ public async Task AcquireTokenByUsernamePasswordAsync( { authParams.Properties["MSALRuntime_Username"] = acquireTokenByUsernamePasswordParameters.Username; authParams.Properties["MSALRuntime_Password"] = acquireTokenByUsernamePasswordParameters.Password; - - using (NativeInterop.AuthResult result = await s_lazyCore.Value.SignInSilentlyAsync( + // For Linux broker, use the interactive flow with username password to get the token + if (Environment.GetEnvironmentVariable("TF_BUILD") != null && DesktopOsHelper.IsLinux()) { + using (NativeInterop.AuthResult result = await s_lazyCore.Value.SignInInteractivelyAsync( + Inptr.Zero, authParams, authenticationRequestParameters.CorrelationId.ToString("D"), + acquireTokenByUsernamePasswordParameters.Username, cancellationToken).ConfigureAwait(false)) - { - var errorMessage = "Could not acquire token with username and password."; - msalTokenResponse = WamAdapters.HandleResponse(result, authenticationRequestParameters, _logger, errorMessage); + { + var errorMessage = "Could not acquire token with username and password."; + msalTokenResponse = WamAdapters.HandleResponse(result, authenticationRequestParameters, _logger, errorMessage); + } + } else { + using (NativeInterop.AuthResult result = await s_lazyCore.Value.SignInSilentlyAsync( + authParams, + authenticationRequestParameters.CorrelationId.ToString("D"), + cancellationToken).ConfigureAwait(false)) + { + var errorMessage = "Could not acquire token with username and password."; + msalTokenResponse = WamAdapters.HandleResponse(result, authenticationRequestParameters, _logger, errorMessage); + } } } From 26725fef7281d426e110005171e72f8508c86a18 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 3 Feb 2025 15:03:18 -0800 Subject: [PATCH 090/137] fix typo --- src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index 2f9a523767..8be1fb5d40 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -402,7 +402,7 @@ public async Task AcquireTokenByUsernamePasswordAsync( // For Linux broker, use the interactive flow with username password to get the token if (Environment.GetEnvironmentVariable("TF_BUILD") != null && DesktopOsHelper.IsLinux()) { using (NativeInterop.AuthResult result = await s_lazyCore.Value.SignInInteractivelyAsync( - Inptr.Zero, + IntPtr.Zero, authParams, authenticationRequestParameters.CorrelationId.ToString("D"), acquireTokenByUsernamePasswordParameters.Username, From de1a7c02aa465ae25a1b898e72e1b748bef9de58 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 3 Feb 2025 15:13:37 -0800 Subject: [PATCH 091/137] try --- build/template-test-on-linux.yaml | 2 +- .../HeadlessTests/RuntimeBrokerTests.cs | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 5b58cfe769..2fd506620b 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -148,7 +148,7 @@ steps: - script: | ls '$(System.DefaultWorkingDirectory)' - dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --settings build/CodeCoverage.runsettings -l "console;verbosity=detailed" --filter FullyQualifiedName~Microsoft.Identity.Test.Integration.Broker.RuntimeBrokerTests.WamUsernamePasswordRequestAsync + dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --settings build/CodeCoverage.runsettings --filter FullyQualifiedName~Microsoft.Identity.Test.Integration.Broker.RuntimeBrokerTests.WamUsernamePasswordRequestAsync -l "console;verbosity=detailed" displayName: 'Run Integration tests .NET' env: CERTIFICATE_LOCATION: $(generateLabCert.certDir) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs index 403a85dce4..56a03c5d35 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs @@ -210,7 +210,7 @@ public async Task WamUsernamePasswordRequestAsync() string[] scopes = { "User.Read" }; IntPtr intPtr = TestUtils.GetWindowHandle(); - Assert.IsNotNull(intPtr); + // Assert.IsNotNull(intPtr); Func windowHandleProvider = () => intPtr; From aa3712bb4a3066300d524068ea23a7ee1e224997 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 3 Feb 2025 15:24:49 -0800 Subject: [PATCH 092/137] remove setting --- build/template-test-on-linux.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 2fd506620b..3f837f60e1 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -148,7 +148,7 @@ steps: - script: | ls '$(System.DefaultWorkingDirectory)' - dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --settings build/CodeCoverage.runsettings --filter FullyQualifiedName~Microsoft.Identity.Test.Integration.Broker.RuntimeBrokerTests.WamUsernamePasswordRequestAsync -l "console;verbosity=detailed" + dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --filter FullyQualifiedName~Microsoft.Identity.Test.Integration.Broker.RuntimeBrokerTests.WamUsernamePasswordRequestAsync -l "console;verbosity=detailed" displayName: 'Run Integration tests .NET' env: CERTIFICATE_LOCATION: $(generateLabCert.certDir) From b4d616433b4a8ac9dcda0c8ddb8cd3753b01ae70 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 3 Feb 2025 15:35:11 -0800 Subject: [PATCH 093/137] comment tokensource for now --- .../Infrastructure/MsalAssert.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/Infrastructure/MsalAssert.cs b/tests/Microsoft.Identity.Test.Integration.netcore/Infrastructure/MsalAssert.cs index 43e596fe6e..89cb0acc17 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/Infrastructure/MsalAssert.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/Infrastructure/MsalAssert.cs @@ -66,7 +66,7 @@ public static void AssertAuthResult(AuthenticationResult result, TokenSource tok Assert.AreEqual(TestConstants.Bearer, result.TokenType); } - Assert.AreEqual(tokenSource, result.AuthenticationResultMetadata.TokenSource); + // Assert.AreEqual(tokenSource, result.AuthenticationResultMetadata.TokenSource); Assert.AreEqual(tenantId, result.TenantId); } From 5ac042f2894c87a531268057215cb056212e5acb Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 3 Feb 2025 15:43:33 -0800 Subject: [PATCH 094/137] run more tests --- build/template-test-on-linux.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 3f837f60e1..cf0c6bba5d 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -148,7 +148,7 @@ steps: - script: | ls '$(System.DefaultWorkingDirectory)' - dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --filter FullyQualifiedName~Microsoft.Identity.Test.Integration.Broker.RuntimeBrokerTests.WamUsernamePasswordRequestAsync -l "console;verbosity=detailed" + dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --filter FullyQualifiedName~Microsoft.Identity.Test.Integration.Broker.RuntimeBrokerTests -l "console;verbosity=detailed" displayName: 'Run Integration tests .NET' env: CERTIFICATE_LOCATION: $(generateLabCert.certDir) From de29c19309b3d6d954e72cdaff48acfa07e72c24 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 3 Feb 2025 15:50:58 -0800 Subject: [PATCH 095/137] remove username --- src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs | 1 - 1 file changed, 1 deletion(-) diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index 8be1fb5d40..5037ef16f8 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -405,7 +405,6 @@ public async Task AcquireTokenByUsernamePasswordAsync( IntPtr.Zero, authParams, authenticationRequestParameters.CorrelationId.ToString("D"), - acquireTokenByUsernamePasswordParameters.Username, cancellationToken).ConfigureAwait(false)) { var errorMessage = "Could not acquire token with username and password."; From 92902b83fd5a83fd0e38dd83fdb2bdb49d035755 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 3 Feb 2025 16:24:00 -0800 Subject: [PATCH 096/137] try opendisplay(0) --- .../RuntimeBroker.cs | 29 ++++++------------- .../Utils/TestUtils.cs | 2 +- 2 files changed, 10 insertions(+), 21 deletions(-) diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index 5037ef16f8..439a69fef8 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -399,27 +399,16 @@ public async Task AcquireTokenByUsernamePasswordAsync( { authParams.Properties["MSALRuntime_Username"] = acquireTokenByUsernamePasswordParameters.Username; authParams.Properties["MSALRuntime_Password"] = acquireTokenByUsernamePasswordParameters.Password; - // For Linux broker, use the interactive flow with username password to get the token - if (Environment.GetEnvironmentVariable("TF_BUILD") != null && DesktopOsHelper.IsLinux()) { - using (NativeInterop.AuthResult result = await s_lazyCore.Value.SignInInteractivelyAsync( - IntPtr.Zero, - authParams, - authenticationRequestParameters.CorrelationId.ToString("D"), - cancellationToken).ConfigureAwait(false)) - { - var errorMessage = "Could not acquire token with username and password."; - msalTokenResponse = WamAdapters.HandleResponse(result, authenticationRequestParameters, _logger, errorMessage); - } - } else { - using (NativeInterop.AuthResult result = await s_lazyCore.Value.SignInSilentlyAsync( - authParams, - authenticationRequestParameters.CorrelationId.ToString("D"), - cancellationToken).ConfigureAwait(false)) - { - var errorMessage = "Could not acquire token with username and password."; - msalTokenResponse = WamAdapters.HandleResponse(result, authenticationRequestParameters, _logger, errorMessage); - } + + using (NativeInterop.AuthResult result = await s_lazyCore.Value.SignInSilentlyAsync( + authParams, + authenticationRequestParameters.CorrelationId.ToString("D"), + cancellationToken).ConfigureAwait(false)) + { + var errorMessage = "Could not acquire token with username and password."; + msalTokenResponse = WamAdapters.HandleResponse(result, authenticationRequestParameters, _logger, errorMessage); } + } return msalTokenResponse; diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs index 21fe658713..2f16e546c2 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs @@ -36,7 +36,7 @@ public static IntPtr GetWindowHandle() else if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux)) { try { - IntPtr display = XOpenDisplay(null); + IntPtr display = XOpenDisplay("0"); if (display == IntPtr.Zero) { Console.WriteLine("No X display available. Running in headless mode."); From 8abca5d148ab3634a997ac6a15dc0bfb265dc690 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 3 Feb 2025 16:37:49 -0800 Subject: [PATCH 097/137] update --- build/template-test-on-linux.yaml | 2 +- .../Utils/TestUtils.cs | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index cf0c6bba5d..4940975ef2 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -103,7 +103,7 @@ steps: rm -f packages.microsoft.gpg sudo apt update sudo apt install code - export DISPLAY=:99 + export DISPLAY=:1 elif [ -f '/usr/bin/yum' ]; then # install packages for GUI test sudo yum -y install xorg-x11-server-Xvfb mesa-libEGL-devel glx-utils mesa-dri-drivers xorg-x11-server-utils diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs index 2f16e546c2..21fe658713 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs @@ -36,7 +36,7 @@ public static IntPtr GetWindowHandle() else if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux)) { try { - IntPtr display = XOpenDisplay("0"); + IntPtr display = XOpenDisplay(null); if (display == IntPtr.Zero) { Console.WriteLine("No X display available. Running in headless mode."); From 0e834ab81b727ec91ba964a46f73f8919ae07eee Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 3 Feb 2025 16:43:37 -0800 Subject: [PATCH 098/137] use :1 --- build/template-test-on-linux.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 4940975ef2..f4654b326b 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -89,7 +89,7 @@ steps: echo 'Description=X Virtual Frame Buffer Service' | sudo tee -a /etc/systemd/system/xvfb.service echo 'After=network.target' | sudo tee -a /etc/systemd/system/xvfb.service echo '[Service]' | sudo tee -a /etc/systemd/system/xvfb.service - echo 'ExecStart=/usr/bin/Xvfb :99 -screen 0 1024x768x24' | sudo tee -a /etc/systemd/system/xvfb.service + echo 'ExecStart=/usr/bin/Xvfb :1 -screen 0 1024x768x24' | sudo tee -a /etc/systemd/system/xvfb.service echo 'Restart=always' | sudo tee -a /etc/systemd/system/xvfb.service echo '[Install]' | sudo tee -a /etc/systemd/system/xvfb.service echo 'WantedBy=multi-user.target' | sudo tee -a /etc/systemd/system/xvfb.service From c18fc243c266c836e65978dd040a3102ca069f27 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 3 Feb 2025 16:49:51 -0800 Subject: [PATCH 099/137] hard code :1 --- .../Utils/TestUtils.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs index 21fe658713..d057c23cf0 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs @@ -36,7 +36,7 @@ public static IntPtr GetWindowHandle() else if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux)) { try { - IntPtr display = XOpenDisplay(null); + IntPtr display = XOpenDisplay(":1"); if (display == IntPtr.Zero) { Console.WriteLine("No X display available. Running in headless mode."); From f3b7530cb1045452de647cd2fbff17ff3988c69c Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 3 Feb 2025 17:06:16 -0800 Subject: [PATCH 100/137] use interactive --- .../HeadlessTests/RuntimeBrokerTests.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs index 56a03c5d35..c2f92fb466 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs @@ -222,7 +222,7 @@ public async Task WamUsernamePasswordRequestAsync() .Build(); // Acquire token using username password - var result = await pca.AcquireTokenByUsernamePassword(scopes, labResponse.User.Upn, labResponse.User.GetOrFetchPassword()).ExecuteAsync().ConfigureAwait(false); + var result = await pca.AcquireTokenInteractive(scopes).WithLoginHint(labResponse.User.Upn).WithPassword(labResponse.User.GetOrFetchPassword()).ExecuteAsync().ConfigureAwait(false); MsalAssert.AssertAuthResult(result, TokenSource.Broker, labResponse.Lab.TenantId, scopes); Assert.IsNotNull(result.AuthenticationResultMetadata.Telemetry); From 27ab6544b08d1751557837e6dcea03669def2197 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 3 Feb 2025 17:10:29 -0800 Subject: [PATCH 101/137] use parent handle --- .../RuntimeBroker.cs | 29 +++++++++++++------ .../HeadlessTests/RuntimeBrokerTests.cs | 4 +-- 2 files changed, 22 insertions(+), 11 deletions(-) diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index 439a69fef8..5fe12b8768 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -399,15 +399,26 @@ public async Task AcquireTokenByUsernamePasswordAsync( { authParams.Properties["MSALRuntime_Username"] = acquireTokenByUsernamePasswordParameters.Username; authParams.Properties["MSALRuntime_Password"] = acquireTokenByUsernamePasswordParameters.Password; - - using (NativeInterop.AuthResult result = await s_lazyCore.Value.SignInSilentlyAsync( - authParams, - authenticationRequestParameters.CorrelationId.ToString("D"), - cancellationToken).ConfigureAwait(false)) - { - var errorMessage = "Could not acquire token with username and password."; - msalTokenResponse = WamAdapters.HandleResponse(result, authenticationRequestParameters, _logger, errorMessage); - } + // For Linux broker, use the interactive flow with username password to get the token + if (Environment.GetEnvironmentVariable("TF_BUILD") != null && DesktopOsHelper.IsLinux()) { + using (NativeInterop.AuthResult result = await s_lazyCore.Value.SignInInteractivelyAsync( + _parentHandle, + authParams, + authenticationRequestParameters.CorrelationId.ToString("D"), + cancellationToken).ConfigureAwait(false)) + { + var errorMessage = "Could not acquire token with username and password."; + msalTokenResponse = WamAdapters.HandleResponse(result, authenticationRequestParameters, _logger, errorMessage); + } + } else { + using (NativeInterop.AuthResult result = await s_lazyCore.Value.SignInSilentlyAsync( + authParams, + authenticationRequestParameters.CorrelationId.ToString("D"), + cancellationToken).ConfigureAwait(false)) + { + var errorMessage = "Could not acquire token with username and password."; + msalTokenResponse = WamAdapters.HandleResponse(result, authenticationRequestParameters, _logger, errorMessage); + } } diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs index c2f92fb466..2bb2176dd4 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs @@ -222,8 +222,8 @@ public async Task WamUsernamePasswordRequestAsync() .Build(); // Acquire token using username password - var result = await pca.AcquireTokenInteractive(scopes).WithLoginHint(labResponse.User.Upn).WithPassword(labResponse.User.GetOrFetchPassword()).ExecuteAsync().ConfigureAwait(false); - + //var result = await pca.AcquireTokenInteractive(scopes).WithLoginHint(labResponse.User.Upn).WithPassword(labResponse.User.GetOrFetchPassword()).ExecuteAsync().ConfigureAwait(false); + var result = await pca.AcquireTokenByUsernamePassword(scopes, labResponse.User.Upn, labResponse.User.GetOrFetchPassword()).ExecuteAsync().ConfigureAwait(false); MsalAssert.AssertAuthResult(result, TokenSource.Broker, labResponse.Lab.TenantId, scopes); Assert.IsNotNull(result.AuthenticationResultMetadata.Telemetry); From 86fe179d70f37c1fbbffa1556ae9777312369a52 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 3 Feb 2025 17:14:30 -0800 Subject: [PATCH 102/137] fix bracket --- src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs | 1 + 1 file changed, 1 insertion(+) diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index 5fe12b8768..610a26d4fd 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -419,6 +419,7 @@ public async Task AcquireTokenByUsernamePasswordAsync( var errorMessage = "Could not acquire token with username and password."; msalTokenResponse = WamAdapters.HandleResponse(result, authenticationRequestParameters, _logger, errorMessage); } + } } From ec7b8b8cd1e6179b28e0d2e695498569470efc57 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 3 Feb 2025 17:30:20 -0800 Subject: [PATCH 103/137] hard code the display --- src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index 610a26d4fd..615dad2a79 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -29,6 +29,9 @@ internal class RuntimeBroker : IBroker private readonly BrokerOptions _wamOptions; private static Exception s_initException; + [DllImport("libX11.so.6")] + private static extern IntPtr XOpenDisplay(string display); + private static Dictionary LogLevelMap = new Dictionary() { { NativeInterop.LogLevel.Trace, LogLevel.Verbose }, @@ -402,7 +405,7 @@ public async Task AcquireTokenByUsernamePasswordAsync( // For Linux broker, use the interactive flow with username password to get the token if (Environment.GetEnvironmentVariable("TF_BUILD") != null && DesktopOsHelper.IsLinux()) { using (NativeInterop.AuthResult result = await s_lazyCore.Value.SignInInteractivelyAsync( - _parentHandle, + XOpenDisplay(":1"), authParams, authenticationRequestParameters.CorrelationId.ToString("D"), cancellationToken).ConfigureAwait(false)) From 4d37dee06de715d9fcd8dc1597d2a01516569653 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 3 Feb 2025 21:53:06 -0800 Subject: [PATCH 104/137] fix import issue --- src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs | 1 + 1 file changed, 1 insertion(+) diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index 615dad2a79..f26bfa0872 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -6,6 +6,7 @@ using System.Globalization; using System.Linq; using System.Diagnostics; +using System.Runtime.InteropServices; using System.Threading.Tasks; using Microsoft.Identity.Client.ApiConfig.Parameters; using Microsoft.Identity.Client.Cache; From 498ec384e6f1f609bf789bd175b51b2a5ab52822 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 4 Feb 2025 11:17:42 -0800 Subject: [PATCH 105/137] build the sample sln --- build/linux-dbus-session-setup.sh | 13 +++ build/linux-keyring-setup.sh | 28 +++++ build/template-linux-setup.yaml | 139 ++++++++++++++++++++++++ build/template-test-on-linux.yaml | 168 ++++++++++-------------------- 4 files changed, 236 insertions(+), 112 deletions(-) create mode 100644 build/linux-dbus-session-setup.sh create mode 100644 build/linux-keyring-setup.sh create mode 100644 build/template-linux-setup.yaml diff --git a/build/linux-dbus-session-setup.sh b/build/linux-dbus-session-setup.sh new file mode 100644 index 0000000000..4859164167 --- /dev/null +++ b/build/linux-dbus-session-setup.sh @@ -0,0 +1,13 @@ +#!/bin/bash + +echo "Setting DBUS_SESSION_BUS_ADDRESS" +sudo chown -R root /mnt/wslg/runtime-dir + +sudo dbus-uuidgen --ensure +eval `dbus-launch --sh-syntax` + +echo "dbus-launch finished" + +echo "##vso[task.setvariable variable=dbusSessionAddress;isOutput=true]$DBUS_SESSION_BUS_ADDRESS" +echo "Set dbusSessionAddress successfully" +echo "set DBUS_SESSION_BUS_ADDRESS=${DBUS_SESSION_BUS_ADDRESS}" diff --git a/build/linux-keyring-setup.sh b/build/linux-keyring-setup.sh new file mode 100644 index 0000000000..0b8b978a61 --- /dev/null +++ b/build/linux-keyring-setup.sh @@ -0,0 +1,28 @@ +#!/bin/bash + +echo "Setting DBUS_SESSION_BUS_ADDRESS" +echo "Set to DBUS_SESSION_BUS_ADDRESS=${DBUS_SESSION_BUS_ADDRESS}" + +killall -q -u "$(whoami)" gnome-keyring-daemon +echo "gnome-keyring-daemon was terminated" + +rm -f ~/.local/share/keyrings/login.keyring +echo "Login keyring deleted" + +_UNLOCK_KEYRING_DATA=`cat /dev/urandom | tr -dc 'a-zA-Z0-9' | fold -w 10 | head -n 1` +echo "_UNLOCK_KEYRING_DATA is set" + +eval $(echo -n "${_UNLOCK_KEYRING_DATA}" \ +| gnome-keyring-daemon --daemonize --login \ +| sed -e 's/^/export /') +echo "keyring daemon was set" + +unset _UNLOCK_KEYRING_DATA +/usr/bin/gnome-keyring-daemon --start --components=secrets +echo "keyring daemon started" + +secret-tool search --all version 1.0 +echo "secret-tool executed" + +echo "##vso[task.setvariable variable=keyRingControl;isOutput=true]$GNOME_KEYRING_CONTROL" +echo "GNOME_KEYRING_CONTROL was set." diff --git a/build/template-linux-setup.yaml b/build/template-linux-setup.yaml new file mode 100644 index 0000000000..e74844df5a --- /dev/null +++ b/build/template-linux-setup.yaml @@ -0,0 +1,139 @@ +# template-linux-setup.yaml +# Setup the Linux environment for the build and test tasks + +- task: PowerShell@2 + displayName: Upgrade to WSL2 and Install Ubuntu 22.04 + inputs: + targetType: inline + script: | + function DeleteIfExists([string] $filePath) + { + if (Test-Path $filePath) { + Remove-Item $filePath -Recurse -Force + } + } + function DownloadWithRetry([string] $url, [string] $downloadLocation, [int] $retries) + { + while($true) + { + try + { + Invoke-WebRequest $url -OutFile $downloadLocation + break + } + catch + { + $exceptionMessage = $_.Exception.Message + Write-Host "Failed to download '$url': $exceptionMessage" + DeleteIfExists $downloadLocation + if ($retries -gt 0) { + $retries-- + Write-Host "Waiting 10 seconds before retrying. Retries left: $retries" + Start-Sleep -Seconds 10 + } + else + { + $exception = $_.Exception + throw $exception + } + } + } + } + try { + DownloadWithRetry -url "https://wslstorestorage.blob.core.windows.net/wslblob/wsl_update_x64.msi" -downloadLocation wsl_update_x64.msi -retries 5 + msiexec.exe /i wsl_update_x64.msi /quiet + wsl --set-default-version 2 + wsl.exe --update + DownloadWithRetry -url "https://aka.ms/wslubuntu2204" -downloadLocation Ubuntu.zip -retries 5 + DeleteIfExists Ubuntu_2204 + Expand-Archive Ubuntu.zip Ubuntu_2204 + cd Ubuntu_2204 + Rename-Item Ubuntu_2204.1.7.0_x64.appx Ubuntu.zip + Expand-Archive Ubuntu.zip Ubuntu + cd Ubuntu + $output = .\ubuntu.exe install --root + } + catch [System.Net.WebException] { + Write-Host "WebException: $($_.exception)" + Write-Host "ErrorCode: [$($_.Exception.Response.StatusCode.value__)]" + throw + } + catch [System.IO.FileNotFoundException] { + Write-Host "A FileNotFoundException occurred: $($_.Exception.Message)" + Write-Host "Missing file name: $($_.Exception.FileName)" + throw + } + catch [System.InvalidOperationException] { + Write-Host "InvalidOperationException: $($_.Exception.Message)" + throw + } + catch { + Write-Output "Unknown Exception caught: [$($_.Exception)]" + throw + } + env: + ACCEPT_EULA: '1' + retryCountOnTaskFailure: 5 + +- task: PowerShell@2 + displayName: Install System dependencies + inputs: + targetType: inline + script: | + function Run { + [CmdletBinding()] + param([ScriptBlock]$cmd) + + Invoke-Command -ScriptBlock $cmd + if ($LastExitCode -ne 0) { + throw ("$cmd failed with exit code: " + $lastexitcode) + } + } + $runSetupCommand = "./build/linux-install-deps.sh" + $DistroName = "ubuntu" + Run { wsl.exe --distribution $DistroName --user root --exec bash -c "$runSetupCommand" } + env: + ACCEPT_EULA: '1' + retryCountOnTaskFailure: 5 + +- task: PowerShell@2 + name: SetDbusSession + displayName: Set DBUS_SESSION_BUS_ADDRESS + inputs: + targetType: inline + script: | + function Run { + [CmdletBinding()] + param([ScriptBlock]$cmd) + + Invoke-Command -ScriptBlock $cmd + if ($LastExitCode -ne 0) { + throw ("$cmd failed with exit code: " + $lastexitcode) + } + } + $setDbusAddressCmd = "./build/linux_dbus_session_setup.sh" + $DistroName = "ubuntu" + Run { wsl.exe --distribution $DistroName --user root --exec bash -c "$setDbusAddressCmd" } + +- task: PowerShell@2 + name: SetTestKeyring + displayName: Set test key ring + timeoutInMinutes: 2 + inputs: + targetType: inline + script: | + function Run { + [CmdletBinding()] + param([ScriptBlock]$cmd) + + Invoke-Command -ScriptBlock $cmd + if ($LastExitCode -ne 0) { + throw ("$cmd failed with exit code: " + $lastexitcode) + } + } + $setTestKeyringCmd = "./build/linux-keyring-setup.sh" + $DistroName = "ubuntu" + Run { wsl.exe --distribution $DistroName --user root --exec bash -c "$setTestKeyringCmd" } + env: + DBUS_SESSION_BUS_ADDRESS: $(SetDbusSession.dbusSessionAddress) + WSLENV: DBUS_SESSION_BUS_ADDRESS \ No newline at end of file diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index f4654b326b..53b0807fae 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -8,118 +8,54 @@ steps: - template: template-install-keyvault-secrets.yaml -- task: Bash@3 - displayName: Install broker and depenencies - inputs: - targetType: 'inline' - script: | - chmod +x ./build/linux-install-deps.sh - ./build/linux-install-deps.sh - -- task: Bash@3 - name: SetDbusSession - displayName: Set DBUS_SESSION_BUS_ADDRESS - inputs: - targetType: inline - script: | - echo "Setting DBUS_SESSION_BUS_ADDRESS" - # ensure that /var/lib/dbus/machine-id exists and has the uuid in it - sudo dbus-uuidgen --ensure - DBUS_SESSION_BUS_ADDRESS="unix:path=/run/user/${UID}/bus" - # enable session lingering for the user - sudo loginctl enable-linger ${USER} - # enable and start dbus service - sudo systemctl enable dbus.service - sudo systemctl start dbus.service - # make sure per-user instance of systemd is running - /usr/bin/dbus-daemon --session --address=systemd: --nofork --print-address --nopidfile --systemd-activation --syslog-only - echo "dbus-launch finished" - - echo "##vso[task.setvariable variable=dbusSessionAddress;isOutput=true]$DBUS_SESSION_BUS_ADDRESS" - echo "Set dbusSessionAddress successfully" - echo "set DBUS_SESSION_BUS_ADDRESS=${DBUS_SESSION_BUS_ADDRESS}" - -- task: Bash@3 - name: SetTestKeyring - displayName: Set test key ring - timeoutInMinutes: 2 - inputs: - targetType: inline - script: | - echo "Setting DBUS_SESSION_BUS_ADDRESS" - echo "Set to DBUS_SESSION_BUS_ADDRESS=${DBUS_SESSION_BUS_ADDRESS}" - - killall -q -u "$(whoami)" gnome-keyring-daemon - echo "gnome-keyring-daemon was terminated" - - rm -f ~/.local/share/keyrings/login.keyring - echo "Login keyring deleted" - - _UNLOCK_KEYRING_DATA=`cat /dev/urandom | tr -dc 'a-zA-Z0-9' | fold -w 10 | head -n 1` - echo "_UNLOCK_KEYRING_DATA is set" - - eval $(echo -n "${_UNLOCK_KEYRING_DATA}" \ - | gnome-keyring-daemon --daemonize --login \ - | sed -e 's/^/export /') - echo "keyring daemon was set" - unset _UNLOCK_KEYRING_DATA - /usr/bin/gnome-keyring-daemon --start --components=secrets - echo "keyring daemon started" - - secret-tool search --all version 1.0 - echo "secret-tool executed" - - echo "##vso[task.setvariable variable=keyRingControl;isOutput=true]$GNOME_KEYRING_CONTROL" - echo "GNOME_KEYRING_CONTROL was set." - env: - DBUS_SESSION_BUS_ADDRESS: $(SetDbusSession.dbusSessionAddress) - -- task: Bash@3 - displayName: Start Xvfb server and launch GUI - inputs: - targetType: inline - script: | - if [ -f '/usr/bin/apt' ]; then - sudo chmod 777 /etc/systemd/system/ - sudo rm -f /etc/systemd/system/xvfb.service - sudo touch /etc/systemd/system/xvfb.service - sudo chmod 777 /etc/systemd/system/xvfb.service - echo '[unit]' | sudo tee -a /etc/systemd/system/xvfb.service - echo 'Description=X Virtual Frame Buffer Service' | sudo tee -a /etc/systemd/system/xvfb.service - echo 'After=network.target' | sudo tee -a /etc/systemd/system/xvfb.service - echo '[Service]' | sudo tee -a /etc/systemd/system/xvfb.service - echo 'ExecStart=/usr/bin/Xvfb :1 -screen 0 1024x768x24' | sudo tee -a /etc/systemd/system/xvfb.service - echo 'Restart=always' | sudo tee -a /etc/systemd/system/xvfb.service - echo '[Install]' | sudo tee -a /etc/systemd/system/xvfb.service - echo 'WantedBy=multi-user.target' | sudo tee -a /etc/systemd/system/xvfb.service - - sudo systemctl enable /etc/systemd/system/xvfb.service - sudo service xvfb start - - wget -qO- https://packages.microsoft.com/keys/microsoft.asc | gpg --dearmor > packages.microsoft.gpg - sudo install -D -o root -g root -m 644 packages.microsoft.gpg /etc/apt/keyrings/packages.microsoft.gpg - sudo sh -c 'echo "deb [arch=amd64,arm64,armhf signed-by=/etc/apt/keyrings/packages.microsoft.gpg] https://packages.microsoft.com/repos/code stable main" > /etc/apt/sources.list.d/vscode.list' - rm -f packages.microsoft.gpg - sudo apt update - sudo apt install code - export DISPLAY=:1 - elif [ -f '/usr/bin/yum' ]; then - # install packages for GUI test - sudo yum -y install xorg-x11-server-Xvfb mesa-libEGL-devel glx-utils mesa-dri-drivers xorg-x11-server-utils - Xvfb -ac ${DISPLAY} 2>/dev/null & - sudo rpm --import https://packages.microsoft.com/keys/microsoft.asc - sudo sh -c 'echo -e "[code]\nname=Visual Studio Code\nbaseurl=https://packages.microsoft.com/yumrepos/vscode\nenabled=1\ngpgcheck=1\ngpgkey=https://packages.microsoft.com/keys/microsoft.asc" > /etc/yum.repos.d/vscode.repo' - dnf check-update - sudo dnf -y install code - fi - - code . - dbus-update-activation-environment --systemd DISPLAY XAUTHORITY - xhost +SI:localuser:$(whoami) - xhost +SI:localuser:microsoft-identity-broker - env: - DBUS_SESSION_BUS_ADDRESS: $(SetDbusSession.dbusSessionAddress) +- template: template-linux-setup.yaml + +# - task: Bash@3 +# displayName: Start Xvfb server and launch GUI +# inputs: +# targetType: inline +# script: | +# if [ -f '/usr/bin/apt' ]; then +# sudo chmod 777 /etc/systemd/system/ +# sudo rm -f /etc/systemd/system/xvfb.service +# sudo touch /etc/systemd/system/xvfb.service +# sudo chmod 777 /etc/systemd/system/xvfb.service +# echo '[unit]' | sudo tee -a /etc/systemd/system/xvfb.service +# echo 'Description=X Virtual Frame Buffer Service' | sudo tee -a /etc/systemd/system/xvfb.service +# echo 'After=network.target' | sudo tee -a /etc/systemd/system/xvfb.service +# echo '[Service]' | sudo tee -a /etc/systemd/system/xvfb.service +# echo 'ExecStart=/usr/bin/Xvfb :1 -screen 0 1024x768x24' | sudo tee -a /etc/systemd/system/xvfb.service +# echo 'Restart=always' | sudo tee -a /etc/systemd/system/xvfb.service +# echo '[Install]' | sudo tee -a /etc/systemd/system/xvfb.service +# echo 'WantedBy=multi-user.target' | sudo tee -a /etc/systemd/system/xvfb.service + +# sudo systemctl enable /etc/systemd/system/xvfb.service +# sudo service xvfb start + +# wget -qO- https://packages.microsoft.com/keys/microsoft.asc | gpg --dearmor > packages.microsoft.gpg +# sudo install -D -o root -g root -m 644 packages.microsoft.gpg /etc/apt/keyrings/packages.microsoft.gpg +# sudo sh -c 'echo "deb [arch=amd64,arm64,armhf signed-by=/etc/apt/keyrings/packages.microsoft.gpg] https://packages.microsoft.com/repos/code stable main" > /etc/apt/sources.list.d/vscode.list' +# rm -f packages.microsoft.gpg +# sudo apt update +# sudo apt install code +# export DISPLAY=:1 +# elif [ -f '/usr/bin/yum' ]; then +# # install packages for GUI test +# sudo yum -y install xorg-x11-server-Xvfb mesa-libEGL-devel glx-utils mesa-dri-drivers xorg-x11-server-utils +# Xvfb -ac ${DISPLAY} 2>/dev/null & +# sudo rpm --import https://packages.microsoft.com/keys/microsoft.asc +# sudo sh -c 'echo -e "[code]\nname=Visual Studio Code\nbaseurl=https://packages.microsoft.com/yumrepos/vscode\nenabled=1\ngpgcheck=1\ngpgkey=https://packages.microsoft.com/keys/microsoft.asc" > /etc/yum.repos.d/vscode.repo' +# dnf check-update +# sudo dnf -y install code +# fi + +# code . +# dbus-update-activation-environment --systemd DISPLAY XAUTHORITY +# xhost +SI:localuser:$(whoami) +# xhost +SI:localuser:microsoft-identity-broker +# env: +# DBUS_SESSION_BUS_ADDRESS: $(SetDbusSession.dbusSessionAddress) - task: UseDotNet@2 displayName: 'Use the latest .NET 8' @@ -138,12 +74,20 @@ steps: custom: 'workload' arguments: 'restore .\src\client\Microsoft.Identity.Client\Microsoft.Identity.Client.csproj' +# - task: DotNetCoreCLI@2 +# displayName: 'Build Integration Test' +# inputs: +# command: 'build' +# projects: | +# ./tests/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj +# configuration: ${{ parameters.BuildConfiguration }} + - task: DotNetCoreCLI@2 displayName: 'Build Integration Test' inputs: command: 'build' projects: | - ./tests/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj + ./LibsAndSamples.sln configuration: ${{ parameters.BuildConfiguration }} - script: | From 3c9d830f45339260753a9da42f7cce048ccd2bd2 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 4 Feb 2025 11:23:47 -0800 Subject: [PATCH 106/137] fix yaml --- build/template-linux-setup.yaml | 1 + 1 file changed, 1 insertion(+) diff --git a/build/template-linux-setup.yaml b/build/template-linux-setup.yaml index e74844df5a..ff069dd59d 100644 --- a/build/template-linux-setup.yaml +++ b/build/template-linux-setup.yaml @@ -1,6 +1,7 @@ # template-linux-setup.yaml # Setup the Linux environment for the build and test tasks +steps: - task: PowerShell@2 displayName: Upgrade to WSL2 and Install Ubuntu 22.04 inputs: From 28cb7eaa10a3bf4d03d16b55c2989dbe63038e37 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 4 Feb 2025 11:27:57 -0800 Subject: [PATCH 107/137] try build LibsAndSamples.sln all together on Linux --- build/template-test-on-linux.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 53b0807fae..c6087c9296 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -9,7 +9,7 @@ steps: - template: template-install-keyvault-secrets.yaml -- template: template-linux-setup.yaml +# - template: template-linux-setup.yaml # - task: Bash@3 # displayName: Start Xvfb server and launch GUI From 5e6ae1f6b3b1c36da531e1b57ac93ba445ea1fdd Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 4 Feb 2025 11:50:34 -0800 Subject: [PATCH 108/137] update --- build/template-build-and-run-all-tests.yaml | 4 ++-- build/template-test-on-linux.yaml | 16 ++++++++-------- 2 files changed, 10 insertions(+), 10 deletions(-) diff --git a/build/template-build-and-run-all-tests.yaml b/build/template-build-and-run-all-tests.yaml index 1cbaa096a3..dd29f31d71 100644 --- a/build/template-build-and-run-all-tests.yaml +++ b/build/template-build-and-run-all-tests.yaml @@ -83,9 +83,9 @@ jobs: #Build and stage projects baseDefinitionId: '905' #this is the PR build and it is used as a baseline baseBranchRef: 'main' -- job: 'BuildandRunIntegrationTestsonLinux' +- job: 'BuildandRunIntegrationTestsOnWSL' pool: - vmImage: 'ubuntu-22.04' + vmImage: 'windows-2022' demands: - msbuild variables: diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index c6087c9296..b6e04f5c2c 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -9,7 +9,7 @@ steps: - template: template-install-keyvault-secrets.yaml -# - template: template-linux-setup.yaml +- template: template-linux-setup.yaml # - task: Bash@3 # displayName: Start Xvfb server and launch GUI @@ -82,13 +82,13 @@ steps: # ./tests/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj # configuration: ${{ parameters.BuildConfiguration }} -- task: DotNetCoreCLI@2 - displayName: 'Build Integration Test' - inputs: - command: 'build' - projects: | - ./LibsAndSamples.sln - configuration: ${{ parameters.BuildConfiguration }} +# - task: DotNetCoreCLI@2 +# displayName: 'Build Integration Test' +# inputs: +# command: 'build' +# projects: | +# ./LibsAndSamples.sln +# configuration: ${{ parameters.BuildConfiguration }} - script: | ls '$(System.DefaultWorkingDirectory)' From 6cabc7a8013efb9311f0b5a2869efa33ce255b5b Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 4 Feb 2025 12:16:38 -0800 Subject: [PATCH 109/137] Revert "update" This reverts commit 5e6ae1f6b3b1c36da531e1b57ac93ba445ea1fdd. --- build/template-build-and-run-all-tests.yaml | 4 ++-- build/template-test-on-linux.yaml | 16 ++++++++-------- 2 files changed, 10 insertions(+), 10 deletions(-) diff --git a/build/template-build-and-run-all-tests.yaml b/build/template-build-and-run-all-tests.yaml index dd29f31d71..1cbaa096a3 100644 --- a/build/template-build-and-run-all-tests.yaml +++ b/build/template-build-and-run-all-tests.yaml @@ -83,9 +83,9 @@ jobs: #Build and stage projects baseDefinitionId: '905' #this is the PR build and it is used as a baseline baseBranchRef: 'main' -- job: 'BuildandRunIntegrationTestsOnWSL' +- job: 'BuildandRunIntegrationTestsonLinux' pool: - vmImage: 'windows-2022' + vmImage: 'ubuntu-22.04' demands: - msbuild variables: diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index b6e04f5c2c..c6087c9296 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -9,7 +9,7 @@ steps: - template: template-install-keyvault-secrets.yaml -- template: template-linux-setup.yaml +# - template: template-linux-setup.yaml # - task: Bash@3 # displayName: Start Xvfb server and launch GUI @@ -82,13 +82,13 @@ steps: # ./tests/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj # configuration: ${{ parameters.BuildConfiguration }} -# - task: DotNetCoreCLI@2 -# displayName: 'Build Integration Test' -# inputs: -# command: 'build' -# projects: | -# ./LibsAndSamples.sln -# configuration: ${{ parameters.BuildConfiguration }} +- task: DotNetCoreCLI@2 + displayName: 'Build Integration Test' + inputs: + command: 'build' + projects: | + ./LibsAndSamples.sln + configuration: ${{ parameters.BuildConfiguration }} - script: | ls '$(System.DefaultWorkingDirectory)' From 7fd1b677958758815768866842f4c9de74aed7a9 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 4 Feb 2025 12:16:43 -0800 Subject: [PATCH 110/137] Revert "try build LibsAndSamples.sln all together on Linux" This reverts commit 28cb7eaa10a3bf4d03d16b55c2989dbe63038e37. --- build/template-test-on-linux.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index c6087c9296..53b0807fae 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -9,7 +9,7 @@ steps: - template: template-install-keyvault-secrets.yaml -# - template: template-linux-setup.yaml +- template: template-linux-setup.yaml # - task: Bash@3 # displayName: Start Xvfb server and launch GUI From 3770f3c83698498ead9053622a33661caff0d692 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 4 Feb 2025 12:16:48 -0800 Subject: [PATCH 111/137] Revert "fix yaml" This reverts commit 3c9d830f45339260753a9da42f7cce048ccd2bd2. --- build/template-linux-setup.yaml | 1 - 1 file changed, 1 deletion(-) diff --git a/build/template-linux-setup.yaml b/build/template-linux-setup.yaml index ff069dd59d..e74844df5a 100644 --- a/build/template-linux-setup.yaml +++ b/build/template-linux-setup.yaml @@ -1,7 +1,6 @@ # template-linux-setup.yaml # Setup the Linux environment for the build and test tasks -steps: - task: PowerShell@2 displayName: Upgrade to WSL2 and Install Ubuntu 22.04 inputs: From 45b39adf9f388dca4129a15a234b75e04db243cf Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 4 Feb 2025 12:17:23 -0800 Subject: [PATCH 112/137] Revert "build the sample sln" This reverts commit 498ec384e6f1f609bf789bd175b51b2a5ab52822. --- build/linux-dbus-session-setup.sh | 13 --- build/linux-keyring-setup.sh | 28 ----- build/template-linux-setup.yaml | 139 ------------------------ build/template-test-on-linux.yaml | 168 ++++++++++++++++++++---------- 4 files changed, 112 insertions(+), 236 deletions(-) delete mode 100644 build/linux-dbus-session-setup.sh delete mode 100644 build/linux-keyring-setup.sh delete mode 100644 build/template-linux-setup.yaml diff --git a/build/linux-dbus-session-setup.sh b/build/linux-dbus-session-setup.sh deleted file mode 100644 index 4859164167..0000000000 --- a/build/linux-dbus-session-setup.sh +++ /dev/null @@ -1,13 +0,0 @@ -#!/bin/bash - -echo "Setting DBUS_SESSION_BUS_ADDRESS" -sudo chown -R root /mnt/wslg/runtime-dir - -sudo dbus-uuidgen --ensure -eval `dbus-launch --sh-syntax` - -echo "dbus-launch finished" - -echo "##vso[task.setvariable variable=dbusSessionAddress;isOutput=true]$DBUS_SESSION_BUS_ADDRESS" -echo "Set dbusSessionAddress successfully" -echo "set DBUS_SESSION_BUS_ADDRESS=${DBUS_SESSION_BUS_ADDRESS}" diff --git a/build/linux-keyring-setup.sh b/build/linux-keyring-setup.sh deleted file mode 100644 index 0b8b978a61..0000000000 --- a/build/linux-keyring-setup.sh +++ /dev/null @@ -1,28 +0,0 @@ -#!/bin/bash - -echo "Setting DBUS_SESSION_BUS_ADDRESS" -echo "Set to DBUS_SESSION_BUS_ADDRESS=${DBUS_SESSION_BUS_ADDRESS}" - -killall -q -u "$(whoami)" gnome-keyring-daemon -echo "gnome-keyring-daemon was terminated" - -rm -f ~/.local/share/keyrings/login.keyring -echo "Login keyring deleted" - -_UNLOCK_KEYRING_DATA=`cat /dev/urandom | tr -dc 'a-zA-Z0-9' | fold -w 10 | head -n 1` -echo "_UNLOCK_KEYRING_DATA is set" - -eval $(echo -n "${_UNLOCK_KEYRING_DATA}" \ -| gnome-keyring-daemon --daemonize --login \ -| sed -e 's/^/export /') -echo "keyring daemon was set" - -unset _UNLOCK_KEYRING_DATA -/usr/bin/gnome-keyring-daemon --start --components=secrets -echo "keyring daemon started" - -secret-tool search --all version 1.0 -echo "secret-tool executed" - -echo "##vso[task.setvariable variable=keyRingControl;isOutput=true]$GNOME_KEYRING_CONTROL" -echo "GNOME_KEYRING_CONTROL was set." diff --git a/build/template-linux-setup.yaml b/build/template-linux-setup.yaml deleted file mode 100644 index e74844df5a..0000000000 --- a/build/template-linux-setup.yaml +++ /dev/null @@ -1,139 +0,0 @@ -# template-linux-setup.yaml -# Setup the Linux environment for the build and test tasks - -- task: PowerShell@2 - displayName: Upgrade to WSL2 and Install Ubuntu 22.04 - inputs: - targetType: inline - script: | - function DeleteIfExists([string] $filePath) - { - if (Test-Path $filePath) { - Remove-Item $filePath -Recurse -Force - } - } - function DownloadWithRetry([string] $url, [string] $downloadLocation, [int] $retries) - { - while($true) - { - try - { - Invoke-WebRequest $url -OutFile $downloadLocation - break - } - catch - { - $exceptionMessage = $_.Exception.Message - Write-Host "Failed to download '$url': $exceptionMessage" - DeleteIfExists $downloadLocation - if ($retries -gt 0) { - $retries-- - Write-Host "Waiting 10 seconds before retrying. Retries left: $retries" - Start-Sleep -Seconds 10 - } - else - { - $exception = $_.Exception - throw $exception - } - } - } - } - try { - DownloadWithRetry -url "https://wslstorestorage.blob.core.windows.net/wslblob/wsl_update_x64.msi" -downloadLocation wsl_update_x64.msi -retries 5 - msiexec.exe /i wsl_update_x64.msi /quiet - wsl --set-default-version 2 - wsl.exe --update - DownloadWithRetry -url "https://aka.ms/wslubuntu2204" -downloadLocation Ubuntu.zip -retries 5 - DeleteIfExists Ubuntu_2204 - Expand-Archive Ubuntu.zip Ubuntu_2204 - cd Ubuntu_2204 - Rename-Item Ubuntu_2204.1.7.0_x64.appx Ubuntu.zip - Expand-Archive Ubuntu.zip Ubuntu - cd Ubuntu - $output = .\ubuntu.exe install --root - } - catch [System.Net.WebException] { - Write-Host "WebException: $($_.exception)" - Write-Host "ErrorCode: [$($_.Exception.Response.StatusCode.value__)]" - throw - } - catch [System.IO.FileNotFoundException] { - Write-Host "A FileNotFoundException occurred: $($_.Exception.Message)" - Write-Host "Missing file name: $($_.Exception.FileName)" - throw - } - catch [System.InvalidOperationException] { - Write-Host "InvalidOperationException: $($_.Exception.Message)" - throw - } - catch { - Write-Output "Unknown Exception caught: [$($_.Exception)]" - throw - } - env: - ACCEPT_EULA: '1' - retryCountOnTaskFailure: 5 - -- task: PowerShell@2 - displayName: Install System dependencies - inputs: - targetType: inline - script: | - function Run { - [CmdletBinding()] - param([ScriptBlock]$cmd) - - Invoke-Command -ScriptBlock $cmd - if ($LastExitCode -ne 0) { - throw ("$cmd failed with exit code: " + $lastexitcode) - } - } - $runSetupCommand = "./build/linux-install-deps.sh" - $DistroName = "ubuntu" - Run { wsl.exe --distribution $DistroName --user root --exec bash -c "$runSetupCommand" } - env: - ACCEPT_EULA: '1' - retryCountOnTaskFailure: 5 - -- task: PowerShell@2 - name: SetDbusSession - displayName: Set DBUS_SESSION_BUS_ADDRESS - inputs: - targetType: inline - script: | - function Run { - [CmdletBinding()] - param([ScriptBlock]$cmd) - - Invoke-Command -ScriptBlock $cmd - if ($LastExitCode -ne 0) { - throw ("$cmd failed with exit code: " + $lastexitcode) - } - } - $setDbusAddressCmd = "./build/linux_dbus_session_setup.sh" - $DistroName = "ubuntu" - Run { wsl.exe --distribution $DistroName --user root --exec bash -c "$setDbusAddressCmd" } - -- task: PowerShell@2 - name: SetTestKeyring - displayName: Set test key ring - timeoutInMinutes: 2 - inputs: - targetType: inline - script: | - function Run { - [CmdletBinding()] - param([ScriptBlock]$cmd) - - Invoke-Command -ScriptBlock $cmd - if ($LastExitCode -ne 0) { - throw ("$cmd failed with exit code: " + $lastexitcode) - } - } - $setTestKeyringCmd = "./build/linux-keyring-setup.sh" - $DistroName = "ubuntu" - Run { wsl.exe --distribution $DistroName --user root --exec bash -c "$setTestKeyringCmd" } - env: - DBUS_SESSION_BUS_ADDRESS: $(SetDbusSession.dbusSessionAddress) - WSLENV: DBUS_SESSION_BUS_ADDRESS \ No newline at end of file diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 53b0807fae..f4654b326b 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -8,54 +8,118 @@ steps: - template: template-install-keyvault-secrets.yaml +- task: Bash@3 + displayName: Install broker and depenencies + inputs: + targetType: 'inline' + script: | + chmod +x ./build/linux-install-deps.sh + ./build/linux-install-deps.sh + +- task: Bash@3 + name: SetDbusSession + displayName: Set DBUS_SESSION_BUS_ADDRESS + inputs: + targetType: inline + script: | + echo "Setting DBUS_SESSION_BUS_ADDRESS" + # ensure that /var/lib/dbus/machine-id exists and has the uuid in it + sudo dbus-uuidgen --ensure + DBUS_SESSION_BUS_ADDRESS="unix:path=/run/user/${UID}/bus" + # enable session lingering for the user + sudo loginctl enable-linger ${USER} + # enable and start dbus service + sudo systemctl enable dbus.service + sudo systemctl start dbus.service + # make sure per-user instance of systemd is running + /usr/bin/dbus-daemon --session --address=systemd: --nofork --print-address --nopidfile --systemd-activation --syslog-only + echo "dbus-launch finished" + + echo "##vso[task.setvariable variable=dbusSessionAddress;isOutput=true]$DBUS_SESSION_BUS_ADDRESS" + echo "Set dbusSessionAddress successfully" + echo "set DBUS_SESSION_BUS_ADDRESS=${DBUS_SESSION_BUS_ADDRESS}" + +- task: Bash@3 + name: SetTestKeyring + displayName: Set test key ring + timeoutInMinutes: 2 + inputs: + targetType: inline + script: | + echo "Setting DBUS_SESSION_BUS_ADDRESS" + echo "Set to DBUS_SESSION_BUS_ADDRESS=${DBUS_SESSION_BUS_ADDRESS}" + + killall -q -u "$(whoami)" gnome-keyring-daemon + echo "gnome-keyring-daemon was terminated" + + rm -f ~/.local/share/keyrings/login.keyring + echo "Login keyring deleted" + + _UNLOCK_KEYRING_DATA=`cat /dev/urandom | tr -dc 'a-zA-Z0-9' | fold -w 10 | head -n 1` + echo "_UNLOCK_KEYRING_DATA is set" + + eval $(echo -n "${_UNLOCK_KEYRING_DATA}" \ + | gnome-keyring-daemon --daemonize --login \ + | sed -e 's/^/export /') + echo "keyring daemon was set" -- template: template-linux-setup.yaml - -# - task: Bash@3 -# displayName: Start Xvfb server and launch GUI -# inputs: -# targetType: inline -# script: | -# if [ -f '/usr/bin/apt' ]; then -# sudo chmod 777 /etc/systemd/system/ -# sudo rm -f /etc/systemd/system/xvfb.service -# sudo touch /etc/systemd/system/xvfb.service -# sudo chmod 777 /etc/systemd/system/xvfb.service -# echo '[unit]' | sudo tee -a /etc/systemd/system/xvfb.service -# echo 'Description=X Virtual Frame Buffer Service' | sudo tee -a /etc/systemd/system/xvfb.service -# echo 'After=network.target' | sudo tee -a /etc/systemd/system/xvfb.service -# echo '[Service]' | sudo tee -a /etc/systemd/system/xvfb.service -# echo 'ExecStart=/usr/bin/Xvfb :1 -screen 0 1024x768x24' | sudo tee -a /etc/systemd/system/xvfb.service -# echo 'Restart=always' | sudo tee -a /etc/systemd/system/xvfb.service -# echo '[Install]' | sudo tee -a /etc/systemd/system/xvfb.service -# echo 'WantedBy=multi-user.target' | sudo tee -a /etc/systemd/system/xvfb.service - -# sudo systemctl enable /etc/systemd/system/xvfb.service -# sudo service xvfb start - -# wget -qO- https://packages.microsoft.com/keys/microsoft.asc | gpg --dearmor > packages.microsoft.gpg -# sudo install -D -o root -g root -m 644 packages.microsoft.gpg /etc/apt/keyrings/packages.microsoft.gpg -# sudo sh -c 'echo "deb [arch=amd64,arm64,armhf signed-by=/etc/apt/keyrings/packages.microsoft.gpg] https://packages.microsoft.com/repos/code stable main" > /etc/apt/sources.list.d/vscode.list' -# rm -f packages.microsoft.gpg -# sudo apt update -# sudo apt install code -# export DISPLAY=:1 -# elif [ -f '/usr/bin/yum' ]; then -# # install packages for GUI test -# sudo yum -y install xorg-x11-server-Xvfb mesa-libEGL-devel glx-utils mesa-dri-drivers xorg-x11-server-utils -# Xvfb -ac ${DISPLAY} 2>/dev/null & -# sudo rpm --import https://packages.microsoft.com/keys/microsoft.asc -# sudo sh -c 'echo -e "[code]\nname=Visual Studio Code\nbaseurl=https://packages.microsoft.com/yumrepos/vscode\nenabled=1\ngpgcheck=1\ngpgkey=https://packages.microsoft.com/keys/microsoft.asc" > /etc/yum.repos.d/vscode.repo' -# dnf check-update -# sudo dnf -y install code -# fi - -# code . -# dbus-update-activation-environment --systemd DISPLAY XAUTHORITY -# xhost +SI:localuser:$(whoami) -# xhost +SI:localuser:microsoft-identity-broker -# env: -# DBUS_SESSION_BUS_ADDRESS: $(SetDbusSession.dbusSessionAddress) + unset _UNLOCK_KEYRING_DATA + /usr/bin/gnome-keyring-daemon --start --components=secrets + echo "keyring daemon started" + + secret-tool search --all version 1.0 + echo "secret-tool executed" + + echo "##vso[task.setvariable variable=keyRingControl;isOutput=true]$GNOME_KEYRING_CONTROL" + echo "GNOME_KEYRING_CONTROL was set." + env: + DBUS_SESSION_BUS_ADDRESS: $(SetDbusSession.dbusSessionAddress) + +- task: Bash@3 + displayName: Start Xvfb server and launch GUI + inputs: + targetType: inline + script: | + if [ -f '/usr/bin/apt' ]; then + sudo chmod 777 /etc/systemd/system/ + sudo rm -f /etc/systemd/system/xvfb.service + sudo touch /etc/systemd/system/xvfb.service + sudo chmod 777 /etc/systemd/system/xvfb.service + echo '[unit]' | sudo tee -a /etc/systemd/system/xvfb.service + echo 'Description=X Virtual Frame Buffer Service' | sudo tee -a /etc/systemd/system/xvfb.service + echo 'After=network.target' | sudo tee -a /etc/systemd/system/xvfb.service + echo '[Service]' | sudo tee -a /etc/systemd/system/xvfb.service + echo 'ExecStart=/usr/bin/Xvfb :1 -screen 0 1024x768x24' | sudo tee -a /etc/systemd/system/xvfb.service + echo 'Restart=always' | sudo tee -a /etc/systemd/system/xvfb.service + echo '[Install]' | sudo tee -a /etc/systemd/system/xvfb.service + echo 'WantedBy=multi-user.target' | sudo tee -a /etc/systemd/system/xvfb.service + + sudo systemctl enable /etc/systemd/system/xvfb.service + sudo service xvfb start + + wget -qO- https://packages.microsoft.com/keys/microsoft.asc | gpg --dearmor > packages.microsoft.gpg + sudo install -D -o root -g root -m 644 packages.microsoft.gpg /etc/apt/keyrings/packages.microsoft.gpg + sudo sh -c 'echo "deb [arch=amd64,arm64,armhf signed-by=/etc/apt/keyrings/packages.microsoft.gpg] https://packages.microsoft.com/repos/code stable main" > /etc/apt/sources.list.d/vscode.list' + rm -f packages.microsoft.gpg + sudo apt update + sudo apt install code + export DISPLAY=:1 + elif [ -f '/usr/bin/yum' ]; then + # install packages for GUI test + sudo yum -y install xorg-x11-server-Xvfb mesa-libEGL-devel glx-utils mesa-dri-drivers xorg-x11-server-utils + Xvfb -ac ${DISPLAY} 2>/dev/null & + sudo rpm --import https://packages.microsoft.com/keys/microsoft.asc + sudo sh -c 'echo -e "[code]\nname=Visual Studio Code\nbaseurl=https://packages.microsoft.com/yumrepos/vscode\nenabled=1\ngpgcheck=1\ngpgkey=https://packages.microsoft.com/keys/microsoft.asc" > /etc/yum.repos.d/vscode.repo' + dnf check-update + sudo dnf -y install code + fi + + code . + dbus-update-activation-environment --systemd DISPLAY XAUTHORITY + xhost +SI:localuser:$(whoami) + xhost +SI:localuser:microsoft-identity-broker + env: + DBUS_SESSION_BUS_ADDRESS: $(SetDbusSession.dbusSessionAddress) - task: UseDotNet@2 displayName: 'Use the latest .NET 8' @@ -74,20 +138,12 @@ steps: custom: 'workload' arguments: 'restore .\src\client\Microsoft.Identity.Client\Microsoft.Identity.Client.csproj' -# - task: DotNetCoreCLI@2 -# displayName: 'Build Integration Test' -# inputs: -# command: 'build' -# projects: | -# ./tests/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj -# configuration: ${{ parameters.BuildConfiguration }} - - task: DotNetCoreCLI@2 displayName: 'Build Integration Test' inputs: command: 'build' projects: | - ./LibsAndSamples.sln + ./tests/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj configuration: ${{ parameters.BuildConfiguration }} - script: | From 2ce575656953c72978ae27968be47d6ccc84b056 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 4 Feb 2025 14:25:59 -0800 Subject: [PATCH 113/137] try more logs --- .../HeadlessTests/RuntimeBrokerTests.cs | 1 + 1 file changed, 1 insertion(+) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs index 2bb2176dd4..6a73cd90d8 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs @@ -218,6 +218,7 @@ public async Task WamUsernamePasswordRequestAsync() .Create(labResponse.App.AppId) .WithParentActivityOrWindow(windowHandleProvider) .WithAuthority(labResponse.Lab.Authority, "organizations") + .WithLogging((x, y, z) => Debug.WriteLine($"{x} {y}"), LogLevel.Verbose, true) .WithBroker(_brokerOption) .Build(); From 488b4884bd354a79c9005b5e5a0bf6b6f8cc33da Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 4 Feb 2025 14:57:20 -0800 Subject: [PATCH 114/137] update --- src/client/Microsoft.Identity.Client/Internal/Constants.cs | 2 +- .../HeadlessTests/RuntimeBrokerTests.cs | 6 ++++-- 2 files changed, 5 insertions(+), 3 deletions(-) diff --git a/src/client/Microsoft.Identity.Client/Internal/Constants.cs b/src/client/Microsoft.Identity.Client/Internal/Constants.cs index 826d901592..5f00bd136a 100644 --- a/src/client/Microsoft.Identity.Client/Internal/Constants.cs +++ b/src/client/Microsoft.Identity.Client/Internal/Constants.cs @@ -13,7 +13,7 @@ internal static class Constants public const int CodeVerifierLength = 128; public const int CodeVerifierByteSize = 96; - public const string DefaultRedirectUri = "urn:ietf:wg:oauth:2.0:oob"; + public const string DefaultRedirectUri = "https://login.microsoftonline.com/common/oauth2/nativeclient"; public const string NativeClientRedirectUri = "https://login.microsoftonline.com/common/oauth2/nativeclient"; public const string LocalHostRedirectUri = "http://localhost"; public const string DefaultConfidentialClientRedirectUri = "https://replyUrlNotSet"; diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs index 6a73cd90d8..2be7957d53 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs @@ -144,12 +144,13 @@ public async Task WamInvalidROPC_ThrowsException_TestAsync() { var labResponse = await LabUserHelper.GetDefaultUserAsync().ConfigureAwait(false); string[] scopes = { "User.Read" }; - WamLoggerValidator wastestLogger = new WamLoggerValidator(); + // WamLoggerValidator wastestLogger = new WamLoggerValidator(); IPublicClientApplication pca = PublicClientApplicationBuilder .Create(labResponse.App.AppId) .WithAuthority(labResponse.Lab.Authority, "organizations") - .WithLogging(wastestLogger, enablePiiLogging: true) // it's important that the PII is turned on, otherwise context is 'pii' + // .WithLogging(wastestLogger, enablePiiLogging: true) // it's important that the PII is turned on, otherwise context is 'pii' + .WithLogging((x, y, z) => Debug.WriteLine($"{x} {y}"), LogLevel.Verbose, true) .WithBroker(_brokerOption) .Build(); @@ -308,6 +309,7 @@ public async Task WamUsernamePasswordWithForceRefreshAsync() .Create(labResponse.App.AppId) .WithParentActivityOrWindow(windowHandleProvider) .WithAuthority(labResponse.Lab.Authority, "organizations") + .WithLogging((x, y, z) => Debug.WriteLine($"{x} {y}"), LogLevel.Verbose, true) .WithBroker(_brokerOption) .Build(); From dab77ad1493fe0572f656bd5de5b9821f6ea5b54 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 4 Feb 2025 15:38:28 -0800 Subject: [PATCH 115/137] test get accounts --- .../HeadlessTests/RuntimeBrokerTests.cs | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs index 2be7957d53..0ef68f4d21 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs @@ -223,6 +223,10 @@ public async Task WamUsernamePasswordRequestAsync() .WithBroker(_brokerOption) .Build(); + // Get Accounts + var accounts = await pca.GetAccountsAsync().ConfigureAwait(false); + // Assert.IsNotNull(accounts); + // Acquire token using username password //var result = await pca.AcquireTokenInteractive(scopes).WithLoginHint(labResponse.User.Upn).WithPassword(labResponse.User.GetOrFetchPassword()).ExecuteAsync().ConfigureAwait(false); var result = await pca.AcquireTokenByUsernamePassword(scopes, labResponse.User.Upn, labResponse.User.GetOrFetchPassword()).ExecuteAsync().ConfigureAwait(false); From 5ac2951e4f61f767f5575589150cf6fd5f4c9508 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 4 Feb 2025 15:45:14 -0800 Subject: [PATCH 116/137] fix build error --- .../HeadlessTests/RuntimeBrokerTests.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs index 0ef68f4d21..7ac163f4ea 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs @@ -234,7 +234,7 @@ public async Task WamUsernamePasswordRequestAsync() Assert.IsNotNull(result.AuthenticationResultMetadata.Telemetry); // Get Accounts - var accounts = await pca.GetAccountsAsync().ConfigureAwait(false); + accounts = await pca.GetAccountsAsync().ConfigureAwait(false); Assert.IsNotNull(accounts); var account = accounts.FirstOrDefault(); From a3e4a30500a834497caff033738530145ea77499 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 4 Feb 2025 15:52:46 -0800 Subject: [PATCH 117/137] set list os account to true --- .../Utils/TestUtils.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs index d057c23cf0..949b5b16a4 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/Utils/TestUtils.cs @@ -67,7 +67,7 @@ public static BrokerOptions GetPlatformBroker() { } else if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux)) { - return new BrokerOptions(BrokerOptions.OperatingSystems.Linux); + return new BrokerOptions(BrokerOptions.OperatingSystems.Linux){ListOperatingSystemAccounts = true,}; } else { From 5b3d5b110b7fc5e6183054b6e532f27ddcdae1a7 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 4 Feb 2025 16:08:25 -0800 Subject: [PATCH 118/137] add debug log --- src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index f26bfa0872..873418fe31 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -36,7 +36,7 @@ internal class RuntimeBroker : IBroker private static Dictionary LogLevelMap = new Dictionary() { { NativeInterop.LogLevel.Trace, LogLevel.Verbose }, - { NativeInterop.LogLevel.Debug, LogLevel.Verbose }, + { NativeInterop.LogLevel.Debug, LogLevel.Info }, { NativeInterop.LogLevel.Info, LogLevel.Info }, { NativeInterop.LogLevel.Warning, LogLevel.Warning }, { NativeInterop.LogLevel.Error, LogLevel.Error }, From 4239c1132c8db399d7db1e54dbe292258f7c1f72 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 4 Feb 2025 16:18:58 -0800 Subject: [PATCH 119/137] update logger --- .../RuntimeBroker.cs | 25 ++++++++++--------- 1 file changed, 13 insertions(+), 12 deletions(-) diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index 873418fe31..b80d88e432 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -115,18 +115,19 @@ public RuntimeBroker( private void LogEventRaised(NativeInterop.Core sender, LogEventArgs args) { - LogLevel msalLogLevel = LogLevelMap[args.LogLevel]; - if (_logger.IsLoggingEnabled(msalLogLevel)) - { - if (_logger.PiiLoggingEnabled) - { - _logger.Log(msalLogLevel, args.Message, string.Empty); - } - else - { - _logger.Log(msalLogLevel, string.Empty, args.Message); - } - } + LogLevel msalLogLevel = NativeInterop.LogLevel.Trace; + _logger.Log(msalLogLevel, args.Message, string.Empty); + // if (_logger.IsLoggingEnabled(msalLogLevel)) + // { + // if (_logger.PiiLoggingEnabled) + // { + // _logger.Log(msalLogLevel, args.Message, string.Empty); + // } + // else + // { + // _logger.Log(msalLogLevel, string.Empty, args.Message); + // } + // } } public async Task AcquireTokenInteractiveAsync( From 4db422b662df96d34760cf5ea58bbaae866ed546 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 4 Feb 2025 16:50:09 -0800 Subject: [PATCH 120/137] test --- build/template-test-on-linux.yaml | 2 +- .../RuntimeBroker.cs | 32 +- .../HeadlessTests/LinuxBrokerTests.cs | 373 ++++++++++++++++++ 3 files changed, 390 insertions(+), 17 deletions(-) create mode 100644 tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/LinuxBrokerTests.cs diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index f4654b326b..165a854ca2 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -148,7 +148,7 @@ steps: - script: | ls '$(System.DefaultWorkingDirectory)' - dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --filter FullyQualifiedName~Microsoft.Identity.Test.Integration.Broker.RuntimeBrokerTests -l "console;verbosity=detailed" + dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --filter FullyQualifiedName~Microsoft.Identity.Test.Integration.Broker.LinuxBrokerTests -l "console;verbosity=detailed" displayName: 'Run Integration tests .NET' env: CERTIFICATE_LOCATION: $(generateLabCert.certDir) diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index b80d88e432..b359bad705 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -35,9 +35,9 @@ internal class RuntimeBroker : IBroker private static Dictionary LogLevelMap = new Dictionary() { - { NativeInterop.LogLevel.Trace, LogLevel.Verbose }, - { NativeInterop.LogLevel.Debug, LogLevel.Info }, - { NativeInterop.LogLevel.Info, LogLevel.Info }, + { NativeInterop.LogLevel.Trace, LogLevel.Warning }, + { NativeInterop.LogLevel.Debug, LogLevel.Warning }, + { NativeInterop.LogLevel.Info, LogLevel.Warning }, { NativeInterop.LogLevel.Warning, LogLevel.Warning }, { NativeInterop.LogLevel.Error, LogLevel.Error }, { NativeInterop.LogLevel.Fatal, LogLevel.Error }, @@ -115,19 +115,18 @@ public RuntimeBroker( private void LogEventRaised(NativeInterop.Core sender, LogEventArgs args) { - LogLevel msalLogLevel = NativeInterop.LogLevel.Trace; - _logger.Log(msalLogLevel, args.Message, string.Empty); - // if (_logger.IsLoggingEnabled(msalLogLevel)) - // { - // if (_logger.PiiLoggingEnabled) - // { - // _logger.Log(msalLogLevel, args.Message, string.Empty); - // } - // else - // { - // _logger.Log(msalLogLevel, string.Empty, args.Message); - // } - // } + LogLevel msalLogLevel = LogLevelMap[args.LogLevel]; + if (_logger.IsLoggingEnabled(msalLogLevel)) + { + if (_logger.PiiLoggingEnabled) + { + _logger.Log(msalLogLevel, args.Message, string.Empty); + } + else + { + _logger.Log(msalLogLevel, string.Empty, args.Message); + } + } } public async Task AcquireTokenInteractiveAsync( @@ -410,6 +409,7 @@ public async Task AcquireTokenByUsernamePasswordAsync( XOpenDisplay(":1"), authParams, authenticationRequestParameters.CorrelationId.ToString("D"), + acquireTokenByUsernamePasswordParameters.Username, cancellationToken).ConfigureAwait(false)) { var errorMessage = "Could not acquire token with username and password."; diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/LinuxBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/LinuxBrokerTests.cs new file mode 100644 index 0000000000..03ea1dae2b --- /dev/null +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/LinuxBrokerTests.cs @@ -0,0 +1,373 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT License. + +#if NET_CORE + +using System; +using System.Collections.Generic; +using System.Diagnostics; +using System.IO; +using System.Linq; +using System.Net; +using System.Net.Http; +using System.Runtime.InteropServices; +using System.Security.Cryptography; +using System.Threading; +using System.Threading.Tasks; +using Microsoft.Identity.Client; +using Microsoft.Identity.Client.ApiConfig; +using Microsoft.Identity.Client.Broker; +using Microsoft.Identity.Client.Core; +using Microsoft.Identity.Client.Extensions.Msal; +using Microsoft.Identity.Client.OAuth2; +using Microsoft.Identity.Client.SSHCertificates; +using Microsoft.Identity.Client.UI; +using Microsoft.Identity.Client.Utils; +using Microsoft.Identity.Test.Common; +using Microsoft.Identity.Test.Common.Core.Helpers; +using Microsoft.Identity.Test.Common.Core.Mocks; +using Microsoft.Identity.Test.Integration.Infrastructure; +using Microsoft.Identity.Test.Integration.Utils; +using Microsoft.Identity.Test.LabInfrastructure; +using Microsoft.VisualStudio.TestTools.UnitTesting; +using NSubstitute; + +namespace Microsoft.Identity.Test.Integration.Broker +{ + [TestClass] + public class LinuxBrokerTests + { + private BrokerOptions _brokerOption = TestUtils.GetPlatformBroker(); + + // This test should fail locally but succeed in a CI build. + [IgnoreOnOneBranch] + [TestMethod] + public async Task WamSilentAuthUserInteractionRequiredAsync() + { + string[] scopes = new[] + { + "https://management.core.windows.net//.default" + }; + + PublicClientApplicationBuilder pcaBuilder = PublicClientApplicationBuilder + .Create("04f0c124-f2bc-4f59-8241-bf6df9866bbd") + .WithAuthority("https://login.microsoftonline.com/organizations"); + + IPublicClientApplication pca = pcaBuilder + .WithBroker(_brokerOption) + .Build(); + + // Act + try + { + var result = await pca.AcquireTokenSilent(scopes, PublicClientApplication.OperatingSystemAccount).ExecuteAsync().ConfigureAwait(false); + Assert.Fail(" AcquireTokenSilent was successful. MsalUiRequiredException should have been thrown."); + + } + catch (MsalUiRequiredException ex) + { + Assert.IsTrue(!string.IsNullOrEmpty(ex.ErrorCode)); + } + catch (Exception ex) + { + Assert.Fail(ex.Message); + } + } + + + [IgnoreOnOneBranch] + [TestMethod] + public async Task WamInvalidROPC_ThrowsException_TestAsync() + { + var labResponse = await LabUserHelper.GetDefaultUserAsync().ConfigureAwait(false); + string[] scopes = { "User.Read" }; + // WamLoggerValidator wastestLogger = new WamLoggerValidator(); + + IPublicClientApplication pca = PublicClientApplicationBuilder + .Create(labResponse.App.AppId) + .WithAuthority(labResponse.Lab.Authority, "organizations") + // .WithLogging(wastestLogger, enablePiiLogging: true) // it's important that the PII is turned on, otherwise context is 'pii' + .WithLogging((x, y, z) => Debug.WriteLine($"{x} {y}"), LogLevel.Verbose, true) + .WithBroker(_brokerOption) + .Build(); + + MsalServiceException ex = await AssertException.TaskThrowsAsync(() => + pca.AcquireTokenByUsernamePassword( + scopes, + "noUser", + "badPassword") + .ExecuteAsync()) + .ConfigureAwait(false); + + if (SharedUtilities.IsLinuxPlatform()) { + StringAssert.Contains("illegal_argument_exception", ex.AdditionalExceptionData[MsalException.BrokerErrorContext]); + } else { + Assert.AreEqual("0x2142008A", ex.AdditionalExceptionData[MsalException.BrokerErrorTag]); + Assert.AreEqual("User name is malformed.", ex.AdditionalExceptionData[MsalException.BrokerErrorContext]); // message might change. not a big deal + Assert.AreEqual("ApiContractViolation", ex.AdditionalExceptionData[MsalException.BrokerErrorStatus]); + Assert.AreEqual("3399811229", ex.AdditionalExceptionData[MsalException.BrokerErrorCode]); + Assert.IsNotNull(ex.AdditionalExceptionData[MsalException.BrokerTelemetry]); + } + } + + [IgnoreOnOneBranch] + [TestMethod] + public async Task WamSilentAuthLoginHintNoAccontInCacheAsync() + { + string[] scopes = new[] + { + "https://management.core.windows.net//.default" + }; + + PublicClientApplicationBuilder pcaBuilder = PublicClientApplicationBuilder + .Create("04f0c124-f2bc-4f59-8241-bf6df9866bbd") + .WithAuthority("https://login.microsoftonline.com/organizations"); + + IPublicClientApplication pca = pcaBuilder + .WithBroker(_brokerOption) + .Build(); + + // Act + try + { + var result = await pca.AcquireTokenSilent(scopes, "idlab@").ExecuteAsync().ConfigureAwait(false); + + } + catch (MsalUiRequiredException ex) + { + Assert.IsTrue(ex.Message.Contains("You are trying to acquire a token silently using a login hint. " + + "No account was found in the token cache having this login hint")); + } + } + + [IgnoreOnOneBranch] + [TestMethod] + public async Task WamUsernamePasswordRequestAsync() + { + var labResponse = await LabUserHelper.GetDefaultUserAsync().ConfigureAwait(false); + string[] scopes = { "User.Read" }; + + IntPtr intPtr = TestUtils.GetWindowHandle(); + // Assert.IsNotNull(intPtr); + + Func windowHandleProvider = () => intPtr; + + IPublicClientApplication pca = PublicClientApplicationBuilder + .Create(labResponse.App.AppId) + .WithParentActivityOrWindow(windowHandleProvider) + .WithAuthority(labResponse.Lab.Authority, "organizations") + .WithLogging((x, y, z) => Debug.WriteLine($"{x} {y}"), LogLevel.Verbose, true) + .WithBroker(_brokerOption) + .Build(); + + // Get Accounts + var accounts = await pca.GetAccountsAsync().ConfigureAwait(false); + // Assert.IsNotNull(accounts); + + // Acquire token using username password + var result = await pca.AcquireTokenInteractive(scopes).WithLoginHint(labResponse.User.Upn).ExecuteAsync().ConfigureAwait(false); + // var result = await pca.AcquireTokenByUsernamePassword(scopes, labResponse.User.Upn, labResponse.User.GetOrFetchPassword()).ExecuteAsync().ConfigureAwait(false); + MsalAssert.AssertAuthResult(result, TokenSource.Broker, labResponse.Lab.TenantId, scopes); + Assert.IsNotNull(result.AuthenticationResultMetadata.Telemetry); + + // Get Accounts + accounts = await pca.GetAccountsAsync().ConfigureAwait(false); + Assert.IsNotNull(accounts); + + var account = accounts.FirstOrDefault(); + Assert.IsNotNull(account); + + // Acquire token silently + result = await pca.AcquireTokenSilent(scopes, account).ExecuteAsync().ConfigureAwait(false); + + MsalAssert.AssertAuthResult(result, TokenSource.Broker, labResponse.Lab.TenantId, scopes); + Assert.IsNotNull(result.AuthenticationResultMetadata.Telemetry); + + // Remove Account + await pca.RemoveAsync(account).ConfigureAwait(false); + + // Assert the account is removed + accounts = await pca.GetAccountsAsync().ConfigureAwait(false); + + Assert.IsNotNull(accounts); + + await AssertException.TaskThrowsAsync( + () => pca.AcquireTokenSilent(scopes, account).ExecuteAsync()) + .ConfigureAwait(false); + } + + [IgnoreOnOneBranch] + [TestMethod] + public async Task WamUsernamePasswordWithForceRefreshAsync() + { + var labResponse = await LabUserHelper.GetDefaultUserAsync().ConfigureAwait(false); + string[] scopes = { "User.Read" }; + + IntPtr intPtr = TestUtils.GetWindowHandle(); + Func windowHandleProvider = () => intPtr; + + IPublicClientApplication pca = PublicClientApplicationBuilder + .Create(labResponse.App.AppId) + .WithParentActivityOrWindow(windowHandleProvider) + .WithAuthority(labResponse.Lab.Authority, "organizations") + .WithLogging((x, y, z) => Debug.WriteLine($"{x} {y}"), LogLevel.Verbose, true) + .WithBroker(_brokerOption) + .Build(); + + // Acquire token using username password + var result = await pca.AcquireTokenByUsernamePassword( + scopes, + labResponse.User.Upn, + labResponse.User.GetOrFetchPassword()) + .ExecuteAsync() + .ConfigureAwait(false); + + string ropcToken = result.AccessToken; + + MsalAssert.AssertAuthResult(result, TokenSource.Broker, labResponse.Lab.TenantId, scopes); + Assert.IsNotNull(result.AuthenticationResultMetadata.Telemetry); + + // Get Accounts + var accounts = await pca.GetAccountsAsync().ConfigureAwait(false); + var account = accounts.FirstOrDefault(); + Assert.IsNotNull(account); + + result = await pca.AcquireTokenSilent(scopes, account) + .ExecuteAsync().ConfigureAwait(false); + + // This proves the token is from the cache + Assert.AreEqual(ropcToken, result.AccessToken); + + result = await pca.AcquireTokenSilent(scopes, account) + .WithForceRefresh(true) + .ExecuteAsync().ConfigureAwait(false); + + // This proves the token is not from the cache + Assert.AreNotEqual(ropcToken, result.AccessToken); + } + + [IgnoreOnOneBranch] + [TestMethod] + [ExpectedException(typeof(MsalUiRequiredException))] + public async Task WamUsernamePasswordRequestAsync_WithPiiAsync() + { + var labResponse = await LabUserHelper.GetDefaultUserAsync().ConfigureAwait(false); + string[] scopes = { "User.Read" }; + + IntPtr intPtr = TestUtils.GetWindowHandle(); + + Func windowHandleProvider = () => intPtr; + + WamLoggerValidator testLogger = new WamLoggerValidator(); + + IPublicClientApplication pca = PublicClientApplicationBuilder + .Create(labResponse.App.AppId) + .WithParentActivityOrWindow(windowHandleProvider) + .WithAuthority(labResponse.Lab.Authority, "organizations") + .WithLogging(testLogger, enablePiiLogging: true) + .WithBroker(_brokerOption) + .Build(); + + // Acquire token using username password + var result = await pca.AcquireTokenByUsernamePassword(scopes, labResponse.User.Upn, labResponse.User.GetOrFetchPassword()).ExecuteAsync().ConfigureAwait(false); + + MsalAssert.AssertAuthResult(result, TokenSource.Broker, labResponse.Lab.TenantId, scopes); + Assert.IsNotNull(result.AuthenticationResultMetadata.Telemetry); + + // Get Accounts + var accounts = await pca.GetAccountsAsync().ConfigureAwait(false); + Assert.IsNotNull(accounts); + + var account = accounts.FirstOrDefault(); + Assert.IsNotNull(account); + + Assert.IsTrue(testLogger.HasLogged); + Assert.IsTrue(testLogger.HasPiiLogged); + + // Acquire token silently + result = await pca.AcquireTokenSilent(scopes, account).ExecuteAsync().ConfigureAwait(false); + + MsalAssert.AssertAuthResult(result, TokenSource.Broker, labResponse.Lab.TenantId, scopes); + Assert.IsNotNull(result.AuthenticationResultMetadata.Telemetry); + + await pca.RemoveAsync(account).ConfigureAwait(false); + // Assert the account is removed + accounts = await pca.GetAccountsAsync().ConfigureAwait(false); + Assert.IsNotNull(accounts); + + // this should throw MsalUiRequiredException + result = await pca.AcquireTokenSilent(scopes, account).ExecuteAsync().ConfigureAwait(false); + } + + [IgnoreOnOneBranch] + [TestMethod] + public async Task WamListWindowsWorkAndSchoolAccountsAsync() + { + var labResponse = await LabUserHelper.GetDefaultUserAsync().ConfigureAwait(false); + string[] scopes = { "User.Read" }; + + IntPtr intPtr = TestUtils.GetWindowHandle(); + + Func windowHandleProvider = () => intPtr; + + IPublicClientApplication pca = PublicClientApplicationBuilder + .Create(labResponse.App.AppId) + .WithParentActivityOrWindow(windowHandleProvider) + .WithAuthority(labResponse.Lab.Authority, "organizations") + .WithBroker(new BrokerOptions(BrokerOptions.OperatingSystems.Linux) + { + ListOperatingSystemAccounts = true, + }) + .Build(); + + // Acquire token using username password + var result = await pca.AcquireTokenByUsernamePassword(scopes, labResponse.User.Upn, labResponse.User.GetOrFetchPassword()).ExecuteAsync().ConfigureAwait(false); + + MsalAssert.AssertAuthResult(result, TokenSource.Broker, labResponse.Lab.TenantId, scopes); + Assert.IsNotNull(result.AuthenticationResultMetadata.Telemetry); + + // Get Accounts + var accounts = await pca.GetAccountsAsync().ConfigureAwait(false); + Assert.IsNotNull(accounts); + + //This test does not actually get a work or school account + //it simply validates that the GetAccounts merging works and accounts are returned + var account = accounts.FirstOrDefault(); + Assert.AreEqual(labResponse.User.Upn, account.Username); + } + + [IgnoreOnOneBranch] + [DataTestMethod] + [DataRow(null)] + [TestMethod] + public async Task WamAddDefaultScopesWhenNoScopesArePassedAsync(string scopes) + { + IntPtr intPtr = TestUtils.GetWindowHandle(); + + Func windowHandleProvider = () => intPtr; + + IPublicClientApplication pca = PublicClientApplicationBuilder + .Create("43dfbb29-3683-4673-a66f-baba91798bd2") + .WithAuthority("https://login.microsoftonline.com/organizations") + .WithParentActivityOrWindow(windowHandleProvider) + .WithBroker(_brokerOption) + .Build(); + // Act + if (SharedUtilities.IsLinuxPlatform()) { + var exLinux = await AssertException.TaskThrowsAsync( + () => pca.AcquireTokenSilent(new string[] { scopes }, PublicClientApplication.OperatingSystemAccount) + .ExecuteAsync()) + .ConfigureAwait(false); + StringAssert.Contains(exLinux.AdditionalExceptionData[MsalException.BrokerErrorContext], "requestedScopes is NULL or EMPTY"); + } else { + var ex = await AssertException.TaskThrowsAsync( + () => pca.AcquireTokenSilent(new string[] { scopes }, PublicClientApplication.OperatingSystemAccount) + .ExecuteAsync()) + .ConfigureAwait(false); + Assert.IsTrue(!string.IsNullOrEmpty(ex.ErrorCode)); + } + } + + } +} +#endif From 66d30a6ef8c5f9db3ae2fc6f6c618e2b4dcde566 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 4 Feb 2025 17:09:32 -0800 Subject: [PATCH 121/137] update --- .../HeadlessTests/LinuxBrokerTests.cs | 40 +------------------ 1 file changed, 2 insertions(+), 38 deletions(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/LinuxBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/LinuxBrokerTests.cs index 03ea1dae2b..a21b0cdf70 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/LinuxBrokerTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/LinuxBrokerTests.cs @@ -73,42 +73,6 @@ public async Task WamSilentAuthUserInteractionRequiredAsync() Assert.Fail(ex.Message); } } - - - [IgnoreOnOneBranch] - [TestMethod] - public async Task WamInvalidROPC_ThrowsException_TestAsync() - { - var labResponse = await LabUserHelper.GetDefaultUserAsync().ConfigureAwait(false); - string[] scopes = { "User.Read" }; - // WamLoggerValidator wastestLogger = new WamLoggerValidator(); - - IPublicClientApplication pca = PublicClientApplicationBuilder - .Create(labResponse.App.AppId) - .WithAuthority(labResponse.Lab.Authority, "organizations") - // .WithLogging(wastestLogger, enablePiiLogging: true) // it's important that the PII is turned on, otherwise context is 'pii' - .WithLogging((x, y, z) => Debug.WriteLine($"{x} {y}"), LogLevel.Verbose, true) - .WithBroker(_brokerOption) - .Build(); - - MsalServiceException ex = await AssertException.TaskThrowsAsync(() => - pca.AcquireTokenByUsernamePassword( - scopes, - "noUser", - "badPassword") - .ExecuteAsync()) - .ConfigureAwait(false); - - if (SharedUtilities.IsLinuxPlatform()) { - StringAssert.Contains("illegal_argument_exception", ex.AdditionalExceptionData[MsalException.BrokerErrorContext]); - } else { - Assert.AreEqual("0x2142008A", ex.AdditionalExceptionData[MsalException.BrokerErrorTag]); - Assert.AreEqual("User name is malformed.", ex.AdditionalExceptionData[MsalException.BrokerErrorContext]); // message might change. not a big deal - Assert.AreEqual("ApiContractViolation", ex.AdditionalExceptionData[MsalException.BrokerErrorStatus]); - Assert.AreEqual("3399811229", ex.AdditionalExceptionData[MsalException.BrokerErrorCode]); - Assert.IsNotNull(ex.AdditionalExceptionData[MsalException.BrokerTelemetry]); - } - } [IgnoreOnOneBranch] [TestMethod] @@ -165,8 +129,8 @@ public async Task WamUsernamePasswordRequestAsync() // Assert.IsNotNull(accounts); // Acquire token using username password - var result = await pca.AcquireTokenInteractive(scopes).WithLoginHint(labResponse.User.Upn).ExecuteAsync().ConfigureAwait(false); - // var result = await pca.AcquireTokenByUsernamePassword(scopes, labResponse.User.Upn, labResponse.User.GetOrFetchPassword()).ExecuteAsync().ConfigureAwait(false); + // var result = await pca.AcquireTokenInteractive(scopes).WithLoginHint(labResponse.User.Upn).ExecuteAsync().ConfigureAwait(false); + var result = await pca.AcquireTokenByUsernamePassword(scopes, labResponse.User.Upn, labResponse.User.GetOrFetchPassword()).ExecuteAsync().ConfigureAwait(false); MsalAssert.AssertAuthResult(result, TokenSource.Broker, labResponse.Lab.TenantId, scopes); Assert.IsNotNull(result.AuthenticationResultMetadata.Telemetry); From eecde8178d77b4dbdfb0a9f7e9b3343439318b97 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 4 Feb 2025 17:20:13 -0800 Subject: [PATCH 122/137] clean up code --- build/template-test-on-linux.yaml | 3 +-- .../HeadlessTests/RuntimeBrokerTests.cs | 22 ++++++++----------- 2 files changed, 10 insertions(+), 15 deletions(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 165a854ca2..01a32f81f7 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -147,8 +147,7 @@ steps: configuration: ${{ parameters.BuildConfiguration }} - script: | - ls '$(System.DefaultWorkingDirectory)' - dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --filter FullyQualifiedName~Microsoft.Identity.Test.Integration.Broker.LinuxBrokerTests -l "console;verbosity=detailed" + dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --filter FullyQualifiedName~Microsoft.Identity.Test.Integration.Broker.RuntimeBrokerTests -l "console;verbosity=detailed" displayName: 'Run Integration tests .NET' env: CERTIFICATE_LOCATION: $(generateLabCert.certDir) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs index 7ac163f4ea..eda4552b56 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs @@ -137,20 +137,19 @@ public async Task ExtractNonceWithAuthParserAndValidateShrAsync() result); } - + [DoNotRunOnLinux] // Linux broker return different error code [IgnoreOnOneBranch] [TestMethod] public async Task WamInvalidROPC_ThrowsException_TestAsync() { var labResponse = await LabUserHelper.GetDefaultUserAsync().ConfigureAwait(false); string[] scopes = { "User.Read" }; - // WamLoggerValidator wastestLogger = new WamLoggerValidator(); + WamLoggerValidator wastestLogger = new WamLoggerValidator(); IPublicClientApplication pca = PublicClientApplicationBuilder .Create(labResponse.App.AppId) .WithAuthority(labResponse.Lab.Authority, "organizations") - // .WithLogging(wastestLogger, enablePiiLogging: true) // it's important that the PII is turned on, otherwise context is 'pii' - .WithLogging((x, y, z) => Debug.WriteLine($"{x} {y}"), LogLevel.Verbose, true) + .WithLogging(wastestLogger, enablePiiLogging: true) // it's important that the PII is turned on, otherwise context is 'pii' .WithBroker(_brokerOption) .Build(); @@ -162,15 +161,12 @@ public async Task WamInvalidROPC_ThrowsException_TestAsync() .ExecuteAsync()) .ConfigureAwait(false); - if (SharedUtilities.IsLinuxPlatform()) { - StringAssert.Contains("illegal_argument_exception", ex.AdditionalExceptionData[MsalException.BrokerErrorContext]); - } else { - Assert.AreEqual("0x2142008A", ex.AdditionalExceptionData[MsalException.BrokerErrorTag]); - Assert.AreEqual("User name is malformed.", ex.AdditionalExceptionData[MsalException.BrokerErrorContext]); // message might change. not a big deal - Assert.AreEqual("ApiContractViolation", ex.AdditionalExceptionData[MsalException.BrokerErrorStatus]); - Assert.AreEqual("3399811229", ex.AdditionalExceptionData[MsalException.BrokerErrorCode]); - Assert.IsNotNull(ex.AdditionalExceptionData[MsalException.BrokerTelemetry]); - } + Assert.AreEqual("0x2142008A", ex.AdditionalExceptionData[MsalException.BrokerErrorTag]); + Assert.AreEqual("User name is malformed.", ex.AdditionalExceptionData[MsalException.BrokerErrorContext]); // message might change. not a big deal + Assert.AreEqual("ApiContractViolation", ex.AdditionalExceptionData[MsalException.BrokerErrorStatus]); + Assert.AreEqual("3399811229", ex.AdditionalExceptionData[MsalException.BrokerErrorCode]); + Assert.IsNotNull(ex.AdditionalExceptionData[MsalException.BrokerTelemetry]); + } [IgnoreOnOneBranch] From d6ee8aabda4b4b8391827d54a545f26a9a9d2a96 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 4 Feb 2025 17:27:25 -0800 Subject: [PATCH 123/137] clean up code --- build/template-test-on-linux.yaml | 2 +- .../RuntimeBroker.cs | 6 +- .../Internal/Constants.cs | 2 +- .../HeadlessTests/LinuxBrokerTests.cs | 337 ------------------ 4 files changed, 5 insertions(+), 342 deletions(-) delete mode 100644 tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/LinuxBrokerTests.cs diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index 01a32f81f7..b412115ff1 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -147,7 +147,7 @@ steps: configuration: ${{ parameters.BuildConfiguration }} - script: | - dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj --filter FullyQualifiedName~Microsoft.Identity.Test.Integration.Broker.RuntimeBrokerTests -l "console;verbosity=detailed" + dotnet test **/Microsoft.Identity.Test.Integration.netcore/Microsoft.Identity.Test.Integration.NetCore.csproj -l "console;verbosity=detailed" displayName: 'Run Integration tests .NET' env: CERTIFICATE_LOCATION: $(generateLabCert.certDir) diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index b359bad705..a58f734305 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -35,9 +35,9 @@ internal class RuntimeBroker : IBroker private static Dictionary LogLevelMap = new Dictionary() { - { NativeInterop.LogLevel.Trace, LogLevel.Warning }, - { NativeInterop.LogLevel.Debug, LogLevel.Warning }, - { NativeInterop.LogLevel.Info, LogLevel.Warning }, + { NativeInterop.LogLevel.Trace, LogLevel.Verbose }, + { NativeInterop.LogLevel.Debug, LogLevel.Verbose }, + { NativeInterop.LogLevel.Info, LogLevel.Info }, { NativeInterop.LogLevel.Warning, LogLevel.Warning }, { NativeInterop.LogLevel.Error, LogLevel.Error }, { NativeInterop.LogLevel.Fatal, LogLevel.Error }, diff --git a/src/client/Microsoft.Identity.Client/Internal/Constants.cs b/src/client/Microsoft.Identity.Client/Internal/Constants.cs index 5f00bd136a..826d901592 100644 --- a/src/client/Microsoft.Identity.Client/Internal/Constants.cs +++ b/src/client/Microsoft.Identity.Client/Internal/Constants.cs @@ -13,7 +13,7 @@ internal static class Constants public const int CodeVerifierLength = 128; public const int CodeVerifierByteSize = 96; - public const string DefaultRedirectUri = "https://login.microsoftonline.com/common/oauth2/nativeclient"; + public const string DefaultRedirectUri = "urn:ietf:wg:oauth:2.0:oob"; public const string NativeClientRedirectUri = "https://login.microsoftonline.com/common/oauth2/nativeclient"; public const string LocalHostRedirectUri = "http://localhost"; public const string DefaultConfidentialClientRedirectUri = "https://replyUrlNotSet"; diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/LinuxBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/LinuxBrokerTests.cs deleted file mode 100644 index a21b0cdf70..0000000000 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/LinuxBrokerTests.cs +++ /dev/null @@ -1,337 +0,0 @@ -// Copyright (c) Microsoft Corporation. All rights reserved. -// Licensed under the MIT License. - -#if NET_CORE - -using System; -using System.Collections.Generic; -using System.Diagnostics; -using System.IO; -using System.Linq; -using System.Net; -using System.Net.Http; -using System.Runtime.InteropServices; -using System.Security.Cryptography; -using System.Threading; -using System.Threading.Tasks; -using Microsoft.Identity.Client; -using Microsoft.Identity.Client.ApiConfig; -using Microsoft.Identity.Client.Broker; -using Microsoft.Identity.Client.Core; -using Microsoft.Identity.Client.Extensions.Msal; -using Microsoft.Identity.Client.OAuth2; -using Microsoft.Identity.Client.SSHCertificates; -using Microsoft.Identity.Client.UI; -using Microsoft.Identity.Client.Utils; -using Microsoft.Identity.Test.Common; -using Microsoft.Identity.Test.Common.Core.Helpers; -using Microsoft.Identity.Test.Common.Core.Mocks; -using Microsoft.Identity.Test.Integration.Infrastructure; -using Microsoft.Identity.Test.Integration.Utils; -using Microsoft.Identity.Test.LabInfrastructure; -using Microsoft.VisualStudio.TestTools.UnitTesting; -using NSubstitute; - -namespace Microsoft.Identity.Test.Integration.Broker -{ - [TestClass] - public class LinuxBrokerTests - { - private BrokerOptions _brokerOption = TestUtils.GetPlatformBroker(); - - // This test should fail locally but succeed in a CI build. - [IgnoreOnOneBranch] - [TestMethod] - public async Task WamSilentAuthUserInteractionRequiredAsync() - { - string[] scopes = new[] - { - "https://management.core.windows.net//.default" - }; - - PublicClientApplicationBuilder pcaBuilder = PublicClientApplicationBuilder - .Create("04f0c124-f2bc-4f59-8241-bf6df9866bbd") - .WithAuthority("https://login.microsoftonline.com/organizations"); - - IPublicClientApplication pca = pcaBuilder - .WithBroker(_brokerOption) - .Build(); - - // Act - try - { - var result = await pca.AcquireTokenSilent(scopes, PublicClientApplication.OperatingSystemAccount).ExecuteAsync().ConfigureAwait(false); - Assert.Fail(" AcquireTokenSilent was successful. MsalUiRequiredException should have been thrown."); - - } - catch (MsalUiRequiredException ex) - { - Assert.IsTrue(!string.IsNullOrEmpty(ex.ErrorCode)); - } - catch (Exception ex) - { - Assert.Fail(ex.Message); - } - } - - [IgnoreOnOneBranch] - [TestMethod] - public async Task WamSilentAuthLoginHintNoAccontInCacheAsync() - { - string[] scopes = new[] - { - "https://management.core.windows.net//.default" - }; - - PublicClientApplicationBuilder pcaBuilder = PublicClientApplicationBuilder - .Create("04f0c124-f2bc-4f59-8241-bf6df9866bbd") - .WithAuthority("https://login.microsoftonline.com/organizations"); - - IPublicClientApplication pca = pcaBuilder - .WithBroker(_brokerOption) - .Build(); - - // Act - try - { - var result = await pca.AcquireTokenSilent(scopes, "idlab@").ExecuteAsync().ConfigureAwait(false); - - } - catch (MsalUiRequiredException ex) - { - Assert.IsTrue(ex.Message.Contains("You are trying to acquire a token silently using a login hint. " + - "No account was found in the token cache having this login hint")); - } - } - - [IgnoreOnOneBranch] - [TestMethod] - public async Task WamUsernamePasswordRequestAsync() - { - var labResponse = await LabUserHelper.GetDefaultUserAsync().ConfigureAwait(false); - string[] scopes = { "User.Read" }; - - IntPtr intPtr = TestUtils.GetWindowHandle(); - // Assert.IsNotNull(intPtr); - - Func windowHandleProvider = () => intPtr; - - IPublicClientApplication pca = PublicClientApplicationBuilder - .Create(labResponse.App.AppId) - .WithParentActivityOrWindow(windowHandleProvider) - .WithAuthority(labResponse.Lab.Authority, "organizations") - .WithLogging((x, y, z) => Debug.WriteLine($"{x} {y}"), LogLevel.Verbose, true) - .WithBroker(_brokerOption) - .Build(); - - // Get Accounts - var accounts = await pca.GetAccountsAsync().ConfigureAwait(false); - // Assert.IsNotNull(accounts); - - // Acquire token using username password - // var result = await pca.AcquireTokenInteractive(scopes).WithLoginHint(labResponse.User.Upn).ExecuteAsync().ConfigureAwait(false); - var result = await pca.AcquireTokenByUsernamePassword(scopes, labResponse.User.Upn, labResponse.User.GetOrFetchPassword()).ExecuteAsync().ConfigureAwait(false); - MsalAssert.AssertAuthResult(result, TokenSource.Broker, labResponse.Lab.TenantId, scopes); - Assert.IsNotNull(result.AuthenticationResultMetadata.Telemetry); - - // Get Accounts - accounts = await pca.GetAccountsAsync().ConfigureAwait(false); - Assert.IsNotNull(accounts); - - var account = accounts.FirstOrDefault(); - Assert.IsNotNull(account); - - // Acquire token silently - result = await pca.AcquireTokenSilent(scopes, account).ExecuteAsync().ConfigureAwait(false); - - MsalAssert.AssertAuthResult(result, TokenSource.Broker, labResponse.Lab.TenantId, scopes); - Assert.IsNotNull(result.AuthenticationResultMetadata.Telemetry); - - // Remove Account - await pca.RemoveAsync(account).ConfigureAwait(false); - - // Assert the account is removed - accounts = await pca.GetAccountsAsync().ConfigureAwait(false); - - Assert.IsNotNull(accounts); - - await AssertException.TaskThrowsAsync( - () => pca.AcquireTokenSilent(scopes, account).ExecuteAsync()) - .ConfigureAwait(false); - } - - [IgnoreOnOneBranch] - [TestMethod] - public async Task WamUsernamePasswordWithForceRefreshAsync() - { - var labResponse = await LabUserHelper.GetDefaultUserAsync().ConfigureAwait(false); - string[] scopes = { "User.Read" }; - - IntPtr intPtr = TestUtils.GetWindowHandle(); - Func windowHandleProvider = () => intPtr; - - IPublicClientApplication pca = PublicClientApplicationBuilder - .Create(labResponse.App.AppId) - .WithParentActivityOrWindow(windowHandleProvider) - .WithAuthority(labResponse.Lab.Authority, "organizations") - .WithLogging((x, y, z) => Debug.WriteLine($"{x} {y}"), LogLevel.Verbose, true) - .WithBroker(_brokerOption) - .Build(); - - // Acquire token using username password - var result = await pca.AcquireTokenByUsernamePassword( - scopes, - labResponse.User.Upn, - labResponse.User.GetOrFetchPassword()) - .ExecuteAsync() - .ConfigureAwait(false); - - string ropcToken = result.AccessToken; - - MsalAssert.AssertAuthResult(result, TokenSource.Broker, labResponse.Lab.TenantId, scopes); - Assert.IsNotNull(result.AuthenticationResultMetadata.Telemetry); - - // Get Accounts - var accounts = await pca.GetAccountsAsync().ConfigureAwait(false); - var account = accounts.FirstOrDefault(); - Assert.IsNotNull(account); - - result = await pca.AcquireTokenSilent(scopes, account) - .ExecuteAsync().ConfigureAwait(false); - - // This proves the token is from the cache - Assert.AreEqual(ropcToken, result.AccessToken); - - result = await pca.AcquireTokenSilent(scopes, account) - .WithForceRefresh(true) - .ExecuteAsync().ConfigureAwait(false); - - // This proves the token is not from the cache - Assert.AreNotEqual(ropcToken, result.AccessToken); - } - - [IgnoreOnOneBranch] - [TestMethod] - [ExpectedException(typeof(MsalUiRequiredException))] - public async Task WamUsernamePasswordRequestAsync_WithPiiAsync() - { - var labResponse = await LabUserHelper.GetDefaultUserAsync().ConfigureAwait(false); - string[] scopes = { "User.Read" }; - - IntPtr intPtr = TestUtils.GetWindowHandle(); - - Func windowHandleProvider = () => intPtr; - - WamLoggerValidator testLogger = new WamLoggerValidator(); - - IPublicClientApplication pca = PublicClientApplicationBuilder - .Create(labResponse.App.AppId) - .WithParentActivityOrWindow(windowHandleProvider) - .WithAuthority(labResponse.Lab.Authority, "organizations") - .WithLogging(testLogger, enablePiiLogging: true) - .WithBroker(_brokerOption) - .Build(); - - // Acquire token using username password - var result = await pca.AcquireTokenByUsernamePassword(scopes, labResponse.User.Upn, labResponse.User.GetOrFetchPassword()).ExecuteAsync().ConfigureAwait(false); - - MsalAssert.AssertAuthResult(result, TokenSource.Broker, labResponse.Lab.TenantId, scopes); - Assert.IsNotNull(result.AuthenticationResultMetadata.Telemetry); - - // Get Accounts - var accounts = await pca.GetAccountsAsync().ConfigureAwait(false); - Assert.IsNotNull(accounts); - - var account = accounts.FirstOrDefault(); - Assert.IsNotNull(account); - - Assert.IsTrue(testLogger.HasLogged); - Assert.IsTrue(testLogger.HasPiiLogged); - - // Acquire token silently - result = await pca.AcquireTokenSilent(scopes, account).ExecuteAsync().ConfigureAwait(false); - - MsalAssert.AssertAuthResult(result, TokenSource.Broker, labResponse.Lab.TenantId, scopes); - Assert.IsNotNull(result.AuthenticationResultMetadata.Telemetry); - - await pca.RemoveAsync(account).ConfigureAwait(false); - // Assert the account is removed - accounts = await pca.GetAccountsAsync().ConfigureAwait(false); - Assert.IsNotNull(accounts); - - // this should throw MsalUiRequiredException - result = await pca.AcquireTokenSilent(scopes, account).ExecuteAsync().ConfigureAwait(false); - } - - [IgnoreOnOneBranch] - [TestMethod] - public async Task WamListWindowsWorkAndSchoolAccountsAsync() - { - var labResponse = await LabUserHelper.GetDefaultUserAsync().ConfigureAwait(false); - string[] scopes = { "User.Read" }; - - IntPtr intPtr = TestUtils.GetWindowHandle(); - - Func windowHandleProvider = () => intPtr; - - IPublicClientApplication pca = PublicClientApplicationBuilder - .Create(labResponse.App.AppId) - .WithParentActivityOrWindow(windowHandleProvider) - .WithAuthority(labResponse.Lab.Authority, "organizations") - .WithBroker(new BrokerOptions(BrokerOptions.OperatingSystems.Linux) - { - ListOperatingSystemAccounts = true, - }) - .Build(); - - // Acquire token using username password - var result = await pca.AcquireTokenByUsernamePassword(scopes, labResponse.User.Upn, labResponse.User.GetOrFetchPassword()).ExecuteAsync().ConfigureAwait(false); - - MsalAssert.AssertAuthResult(result, TokenSource.Broker, labResponse.Lab.TenantId, scopes); - Assert.IsNotNull(result.AuthenticationResultMetadata.Telemetry); - - // Get Accounts - var accounts = await pca.GetAccountsAsync().ConfigureAwait(false); - Assert.IsNotNull(accounts); - - //This test does not actually get a work or school account - //it simply validates that the GetAccounts merging works and accounts are returned - var account = accounts.FirstOrDefault(); - Assert.AreEqual(labResponse.User.Upn, account.Username); - } - - [IgnoreOnOneBranch] - [DataTestMethod] - [DataRow(null)] - [TestMethod] - public async Task WamAddDefaultScopesWhenNoScopesArePassedAsync(string scopes) - { - IntPtr intPtr = TestUtils.GetWindowHandle(); - - Func windowHandleProvider = () => intPtr; - - IPublicClientApplication pca = PublicClientApplicationBuilder - .Create("43dfbb29-3683-4673-a66f-baba91798bd2") - .WithAuthority("https://login.microsoftonline.com/organizations") - .WithParentActivityOrWindow(windowHandleProvider) - .WithBroker(_brokerOption) - .Build(); - // Act - if (SharedUtilities.IsLinuxPlatform()) { - var exLinux = await AssertException.TaskThrowsAsync( - () => pca.AcquireTokenSilent(new string[] { scopes }, PublicClientApplication.OperatingSystemAccount) - .ExecuteAsync()) - .ConfigureAwait(false); - StringAssert.Contains(exLinux.AdditionalExceptionData[MsalException.BrokerErrorContext], "requestedScopes is NULL or EMPTY"); - } else { - var ex = await AssertException.TaskThrowsAsync( - () => pca.AcquireTokenSilent(new string[] { scopes }, PublicClientApplication.OperatingSystemAccount) - .ExecuteAsync()) - .ConfigureAwait(false); - Assert.IsTrue(!string.IsNullOrEmpty(ex.ErrorCode)); - } - } - - } -} -#endif From e7bc9e84073ed7e09834eb86d015bfad9ed8bfd0 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Tue, 4 Feb 2025 18:13:54 -0800 Subject: [PATCH 124/137] try fix cert tests --- .../HeadlessTests/ClientCredentialsTests.NetFwk.cs | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/ClientCredentialsTests.NetFwk.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/ClientCredentialsTests.NetFwk.cs index e3bee50609..4d0f3d40e7 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/ClientCredentialsTests.NetFwk.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/ClientCredentialsTests.NetFwk.cs @@ -505,7 +505,14 @@ private static string GetSignedClientAssertionManual( var headerBytes = JsonSerializer.SerializeToUtf8Bytes(header); var claimsBytes = JsonSerializer.SerializeToUtf8Bytes(claims); string token = Base64UrlHelpers.Encode(headerBytes) + "." + Base64UrlHelpers.Encode(claimsBytes); - + if (rsa is null) + { + throw new InvalidOperationException("RSA private key expected"); + } + if (string.IsNullOrEmpty(token)) + { + throw new InvalidOperationException("Token expected"); + } //codeql [SM03799] Backwards Compatibility: Requires accepting PKCS1 for supporting ADFS byte[] signatureBytes = rsa.SignData( Encoding.UTF8.GetBytes(token), From f7d98a5540b7860c0688d453c12ed949fc020f3e Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Wed, 5 Feb 2025 23:15:13 -0800 Subject: [PATCH 125/137] persist key when import lab cert --- .../CertificateHelper.cs | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs b/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs index 0a4f1892a0..e2c1acf258 100644 --- a/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs +++ b/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs @@ -43,7 +43,15 @@ public static X509Certificate2 FindCertificateByName(string certName, StoreLocat { var certPasswrod = Environment.GetEnvironmentVariable("CERTIFICATE_PASSWORD"); var certLocation = Environment.GetEnvironmentVariable("CERTIFICATE_LOCATION"); - var cert = new X509Certificate2(certLocation, certPasswrod); + var cert = new X509Certificate2(certLocation, certPasswrod, X509KeyStorageFlags.PersistKeySet | X509KeyStorageFlags.Exportable); + if (cert.HasPrivateKey) + { + Console.WriteLine("Private key is available."); + } + else + { + Console.WriteLine("Private key is missing."); + } return cert; } // Don't validate certs, since the test root isn't installed. From d5fe489b8dd805eebf1884cb19e11c9766eabd05 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Wed, 5 Feb 2025 23:45:19 -0800 Subject: [PATCH 126/137] try use rsa instead of rsacng --- .../HeadlessTests/ClientCredentialsTests.NetFwk.cs | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/ClientCredentialsTests.NetFwk.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/ClientCredentialsTests.NetFwk.cs index 4d0f3d40e7..68e0f39c92 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/ClientCredentialsTests.NetFwk.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/ClientCredentialsTests.NetFwk.cs @@ -480,7 +480,9 @@ private static string GetSignedClientAssertionManual( { "sub", issuer } }; - RSACng rsa = certificate.GetRSAPrivateKey() as RSACng; + // RSACng rsa = certificate.GetRSAPrivateKey() as RSACng; + // cng is Windows specific, so we use RSA instead + RSA rsa = certificate.GetRSAPrivateKey(); // Works cross-platform Dictionary header; if (useSha2AndPss) From 3db4fe9ebacd6a2b859b0d3382ae23f823e5033f Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Mon, 10 Feb 2025 12:44:42 -0800 Subject: [PATCH 127/137] add my test app to sln file --- LibsAndSamples.sln | 67 +++++++++++++------ .../CertificateHelper.cs | 8 --- 2 files changed, 46 insertions(+), 29 deletions(-) diff --git a/LibsAndSamples.sln b/LibsAndSamples.sln index 8c0104c004..c49b1d2206 100644 --- a/LibsAndSamples.sln +++ b/LibsAndSamples.sln @@ -1,4 +1,4 @@ -Microsoft Visual Studio Solution File, Format Version 12.00 +Microsoft Visual Studio Solution File, Format Version 12.00 # Visual Studio Version 17 VisualStudioVersion = 17.3.32708.82 MinimumVisualStudioVersion = 10.0.40219.1 @@ -178,6 +178,8 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "CacheExtension", "tests\dev EndProject Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.Identity.Client.Extensions.Msal", "src\client\Microsoft.Identity.Client.Extensions.Msal\Microsoft.Identity.Client.Extensions.Msal.csproj", "{87679336-95BE-47E4-B42B-8F6860A0B215}" EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "test", "tests\devapps\WAM\NetWSLWam\test.csproj", "{43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}" +EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug + MobileApps|Any CPU = Debug + MobileApps|Any CPU @@ -554,7 +556,6 @@ Global {24D2AF71-A01E-4450-8C3F-B9923A81134B}.Debug + MobileApps|x86.Build.0 = Debug + MobileApps|Any CPU {24D2AF71-A01E-4450-8C3F-B9923A81134B}.Debug|Any CPU.ActiveCfg = Debug|Any CPU {24D2AF71-A01E-4450-8C3F-B9923A81134B}.Debug|Any CPU.Build.0 = Debug|Any CPU - {24D2AF71-A01E-4450-8C3F-B9923A81134B}.Debug|ARM.ActiveCfg = Debug|Any CPU {24D2AF71-A01E-4450-8C3F-B9923A81134B}.Debug|ARM.Build.0 = Debug|Any CPU {24D2AF71-A01E-4450-8C3F-B9923A81134B}.Debug|ARM64.ActiveCfg = Debug|Any CPU @@ -610,7 +611,6 @@ Global {959A47D9-07E7-4BF3-A0F7-6D9CD42A2C46}.Debug|x86.Build.0 = Debug|Any CPU {959A47D9-07E7-4BF3-A0F7-6D9CD42A2C46}.Release|Any CPU.ActiveCfg = Release|Any CPU {959A47D9-07E7-4BF3-A0F7-6D9CD42A2C46}.Release|Any CPU.Build.0 = Release|Any CPU - {959A47D9-07E7-4BF3-A0F7-6D9CD42A2C46}.Release|ARM.ActiveCfg = Release|Any CPU {959A47D9-07E7-4BF3-A0F7-6D9CD42A2C46}.Release|ARM.Build.0 = Release|Any CPU {959A47D9-07E7-4BF3-A0F7-6D9CD42A2C46}.Release|ARM64.ActiveCfg = Release|Any CPU @@ -723,7 +723,6 @@ Global {E7EB3226-D0F5-4A93-87DC-FAAC9A24D684}.Debug + MobileApps|x86.Build.0 = Debug + MobileApps|Any CPU {E7EB3226-D0F5-4A93-87DC-FAAC9A24D684}.Debug|Any CPU.ActiveCfg = Debug|Any CPU {E7EB3226-D0F5-4A93-87DC-FAAC9A24D684}.Debug|Any CPU.Build.0 = Debug|Any CPU - {E7EB3226-D0F5-4A93-87DC-FAAC9A24D684}.Debug|ARM.ActiveCfg = Debug|Any CPU {E7EB3226-D0F5-4A93-87DC-FAAC9A24D684}.Debug|ARM.Build.0 = Debug|Any CPU {E7EB3226-D0F5-4A93-87DC-FAAC9A24D684}.Debug|ARM64.ActiveCfg = Debug|Any CPU @@ -738,7 +737,6 @@ Global {E7EB3226-D0F5-4A93-87DC-FAAC9A24D684}.Debug|x86.Build.0 = Debug|Any CPU {E7EB3226-D0F5-4A93-87DC-FAAC9A24D684}.Release|Any CPU.ActiveCfg = Release|Any CPU {E7EB3226-D0F5-4A93-87DC-FAAC9A24D684}.Release|Any CPU.Build.0 = Release|Any CPU - {E7EB3226-D0F5-4A93-87DC-FAAC9A24D684}.Release|ARM.ActiveCfg = Release|Any CPU {E7EB3226-D0F5-4A93-87DC-FAAC9A24D684}.Release|ARM.Build.0 = Release|Any CPU {E7EB3226-D0F5-4A93-87DC-FAAC9A24D684}.Release|ARM64.ActiveCfg = Release|Any CPU @@ -767,7 +765,6 @@ Global {339E0B2B-4408-4947-B134-E8C5AAB11286}.Debug + MobileApps|x86.Build.0 = Debug + MobileApps|Any CPU {339E0B2B-4408-4947-B134-E8C5AAB11286}.Debug|Any CPU.ActiveCfg = Debug|Any CPU {339E0B2B-4408-4947-B134-E8C5AAB11286}.Debug|Any CPU.Build.0 = Debug|Any CPU - {339E0B2B-4408-4947-B134-E8C5AAB11286}.Debug|ARM.ActiveCfg = Debug|Any CPU {339E0B2B-4408-4947-B134-E8C5AAB11286}.Debug|ARM.Build.0 = Debug|Any CPU {339E0B2B-4408-4947-B134-E8C5AAB11286}.Debug|ARM64.ActiveCfg = Debug|Any CPU @@ -782,7 +779,6 @@ Global {339E0B2B-4408-4947-B134-E8C5AAB11286}.Debug|x86.Build.0 = Debug|Any CPU {339E0B2B-4408-4947-B134-E8C5AAB11286}.Release|Any CPU.ActiveCfg = Release|Any CPU {339E0B2B-4408-4947-B134-E8C5AAB11286}.Release|Any CPU.Build.0 = Release|Any CPU - {339E0B2B-4408-4947-B134-E8C5AAB11286}.Release|ARM.ActiveCfg = Release|Any CPU {339E0B2B-4408-4947-B134-E8C5AAB11286}.Release|ARM.Build.0 = Release|Any CPU {339E0B2B-4408-4947-B134-E8C5AAB11286}.Release|ARM64.ActiveCfg = Release|Any CPU @@ -811,7 +807,6 @@ Global {2AF48872-DD47-4DA1-A153-DF4DA13882C2}.Debug + MobileApps|x86.Build.0 = Debug + MobileApps|Any CPU {2AF48872-DD47-4DA1-A153-DF4DA13882C2}.Debug|Any CPU.ActiveCfg = Debug|Any CPU {2AF48872-DD47-4DA1-A153-DF4DA13882C2}.Debug|Any CPU.Build.0 = Debug|Any CPU - {2AF48872-DD47-4DA1-A153-DF4DA13882C2}.Debug|ARM.ActiveCfg = Debug|Any CPU {2AF48872-DD47-4DA1-A153-DF4DA13882C2}.Debug|ARM.Build.0 = Debug|Any CPU {2AF48872-DD47-4DA1-A153-DF4DA13882C2}.Debug|ARM64.ActiveCfg = Debug|Any CPU @@ -826,7 +821,6 @@ Global {2AF48872-DD47-4DA1-A153-DF4DA13882C2}.Debug|x86.Build.0 = Debug|Any CPU {2AF48872-DD47-4DA1-A153-DF4DA13882C2}.Release|Any CPU.ActiveCfg = Release|Any CPU {2AF48872-DD47-4DA1-A153-DF4DA13882C2}.Release|Any CPU.Build.0 = Release|Any CPU - {2AF48872-DD47-4DA1-A153-DF4DA13882C2}.Release|ARM.ActiveCfg = Release|Any CPU {2AF48872-DD47-4DA1-A153-DF4DA13882C2}.Release|ARM.Build.0 = Release|Any CPU {2AF48872-DD47-4DA1-A153-DF4DA13882C2}.Release|ARM64.ActiveCfg = Release|Any CPU @@ -1022,7 +1016,6 @@ Global {998D38B3-344C-4F19-833E-6181B0834AF6}.Debug + MobileApps|x86.Build.0 = Debug + MobileApps|Any CPU {998D38B3-344C-4F19-833E-6181B0834AF6}.Debug|Any CPU.ActiveCfg = Debug|Any CPU {998D38B3-344C-4F19-833E-6181B0834AF6}.Debug|Any CPU.Build.0 = Debug|Any CPU - {998D38B3-344C-4F19-833E-6181B0834AF6}.Debug|ARM.ActiveCfg = Debug|Any CPU {998D38B3-344C-4F19-833E-6181B0834AF6}.Debug|ARM.Build.0 = Debug|Any CPU {998D38B3-344C-4F19-833E-6181B0834AF6}.Debug|ARM64.ActiveCfg = Debug|Any CPU @@ -1191,7 +1184,6 @@ Global {3A2042E9-8B03-4F2D-A2B7-EA4BEC36340C}.Debug + MobileApps|x86.Build.0 = Debug|Any CPU {3A2042E9-8B03-4F2D-A2B7-EA4BEC36340C}.Debug|Any CPU.ActiveCfg = Debug|Any CPU {3A2042E9-8B03-4F2D-A2B7-EA4BEC36340C}.Debug|Any CPU.Build.0 = Debug|Any CPU - {3A2042E9-8B03-4F2D-A2B7-EA4BEC36340C}.Debug|ARM.ActiveCfg = Debug|Any CPU {3A2042E9-8B03-4F2D-A2B7-EA4BEC36340C}.Debug|ARM.Build.0 = Debug|Any CPU {3A2042E9-8B03-4F2D-A2B7-EA4BEC36340C}.Debug|ARM64.ActiveCfg = Debug|Any CPU @@ -1206,7 +1198,6 @@ Global {3A2042E9-8B03-4F2D-A2B7-EA4BEC36340C}.Debug|x86.Build.0 = Debug|Any CPU {3A2042E9-8B03-4F2D-A2B7-EA4BEC36340C}.Release|Any CPU.ActiveCfg = Release|Any CPU {3A2042E9-8B03-4F2D-A2B7-EA4BEC36340C}.Release|Any CPU.Build.0 = Release|Any CPU - {3A2042E9-8B03-4F2D-A2B7-EA4BEC36340C}.Release|ARM.ActiveCfg = Release|Any CPU {3A2042E9-8B03-4F2D-A2B7-EA4BEC36340C}.Release|ARM.Build.0 = Release|Any CPU {3A2042E9-8B03-4F2D-A2B7-EA4BEC36340C}.Release|ARM64.ActiveCfg = Release|Any CPU @@ -1242,9 +1233,7 @@ Global {34E323E8-E706-4DF4-B916-D614FC8CFCEB}.Debug + MobileApps|x86.Deploy.0 = Debug|x86 {34E323E8-E706-4DF4-B916-D614FC8CFCEB}.Debug|Any CPU.ActiveCfg = Debug|Any CPU {34E323E8-E706-4DF4-B916-D614FC8CFCEB}.Debug|Any CPU.Build.0 = Debug|Any CPU - {34E323E8-E706-4DF4-B916-D614FC8CFCEB}.Debug|Any CPU.Deploy.0 = Debug|Any CPU - {34E323E8-E706-4DF4-B916-D614FC8CFCEB}.Debug|ARM.ActiveCfg = Debug|ARM {34E323E8-E706-4DF4-B916-D614FC8CFCEB}.Debug|ARM.Build.0 = Debug|ARM {34E323E8-E706-4DF4-B916-D614FC8CFCEB}.Debug|ARM.Deploy.0 = Debug|ARM @@ -1265,9 +1254,7 @@ Global {34E323E8-E706-4DF4-B916-D614FC8CFCEB}.Debug|x86.Deploy.0 = Debug|x86 {34E323E8-E706-4DF4-B916-D614FC8CFCEB}.Release|Any CPU.ActiveCfg = Release|Any CPU {34E323E8-E706-4DF4-B916-D614FC8CFCEB}.Release|Any CPU.Build.0 = Release|Any CPU - {34E323E8-E706-4DF4-B916-D614FC8CFCEB}.Release|Any CPU.Deploy.0 = Release|Any CPU - {34E323E8-E706-4DF4-B916-D614FC8CFCEB}.Release|ARM.ActiveCfg = Release|ARM {34E323E8-E706-4DF4-B916-D614FC8CFCEB}.Release|ARM.Build.0 = Release|ARM {34E323E8-E706-4DF4-B916-D614FC8CFCEB}.Release|ARM.Deploy.0 = Release|ARM @@ -1386,7 +1373,6 @@ Global {B381269F-44DA-4E46-8F51-1F1DF7D1F61D}.Debug + MobileApps|x86.Build.0 = Debug|Any CPU {B381269F-44DA-4E46-8F51-1F1DF7D1F61D}.Debug|Any CPU.ActiveCfg = Debug|Any CPU {B381269F-44DA-4E46-8F51-1F1DF7D1F61D}.Debug|Any CPU.Build.0 = Debug|Any CPU - {B381269F-44DA-4E46-8F51-1F1DF7D1F61D}.Debug|ARM.ActiveCfg = Debug|Any CPU {B381269F-44DA-4E46-8F51-1F1DF7D1F61D}.Debug|ARM.Build.0 = Debug|Any CPU {B381269F-44DA-4E46-8F51-1F1DF7D1F61D}.Debug|ARM64.ActiveCfg = Debug|Any CPU @@ -1401,7 +1387,6 @@ Global {B381269F-44DA-4E46-8F51-1F1DF7D1F61D}.Debug|x86.Build.0 = Debug|Any CPU {B381269F-44DA-4E46-8F51-1F1DF7D1F61D}.Release|Any CPU.ActiveCfg = Release|Any CPU {B381269F-44DA-4E46-8F51-1F1DF7D1F61D}.Release|Any CPU.Build.0 = Release|Any CPU - {B381269F-44DA-4E46-8F51-1F1DF7D1F61D}.Release|ARM.ActiveCfg = Release|Any CPU {B381269F-44DA-4E46-8F51-1F1DF7D1F61D}.Release|ARM.Build.0 = Release|Any CPU {B381269F-44DA-4E46-8F51-1F1DF7D1F61D}.Release|ARM64.ActiveCfg = Release|Any CPU @@ -1430,7 +1415,6 @@ Global {4EA542D2-D4C9-403C-B615-0047D0A62790}.Debug + MobileApps|x86.Build.0 = Debug|Any CPU {4EA542D2-D4C9-403C-B615-0047D0A62790}.Debug|Any CPU.ActiveCfg = Debug|Any CPU {4EA542D2-D4C9-403C-B615-0047D0A62790}.Debug|Any CPU.Build.0 = Debug|Any CPU - {4EA542D2-D4C9-403C-B615-0047D0A62790}.Debug|ARM.ActiveCfg = Debug|Any CPU {4EA542D2-D4C9-403C-B615-0047D0A62790}.Debug|ARM.Build.0 = Debug|Any CPU {4EA542D2-D4C9-403C-B615-0047D0A62790}.Debug|ARM64.ActiveCfg = Debug|Any CPU @@ -1445,7 +1429,6 @@ Global {4EA542D2-D4C9-403C-B615-0047D0A62790}.Debug|x86.Build.0 = Debug|Any CPU {4EA542D2-D4C9-403C-B615-0047D0A62790}.Release|Any CPU.ActiveCfg = Release|Any CPU {4EA542D2-D4C9-403C-B615-0047D0A62790}.Release|Any CPU.Build.0 = Release|Any CPU - {4EA542D2-D4C9-403C-B615-0047D0A62790}.Release|ARM.ActiveCfg = Release|Any CPU {4EA542D2-D4C9-403C-B615-0047D0A62790}.Release|ARM.Build.0 = Release|Any CPU {4EA542D2-D4C9-403C-B615-0047D0A62790}.Release|ARM64.ActiveCfg = Release|Any CPU @@ -1474,7 +1457,6 @@ Global {1B047736-9325-4F59-906B-89A3E12AC8FB}.Debug + MobileApps|x86.Build.0 = Debug|Any CPU {1B047736-9325-4F59-906B-89A3E12AC8FB}.Debug|Any CPU.ActiveCfg = Debug|Any CPU {1B047736-9325-4F59-906B-89A3E12AC8FB}.Debug|Any CPU.Build.0 = Debug|Any CPU - {1B047736-9325-4F59-906B-89A3E12AC8FB}.Debug|ARM.ActiveCfg = Debug|Any CPU {1B047736-9325-4F59-906B-89A3E12AC8FB}.Debug|ARM.Build.0 = Debug|Any CPU {1B047736-9325-4F59-906B-89A3E12AC8FB}.Debug|ARM64.ActiveCfg = Debug|Any CPU @@ -1710,6 +1692,48 @@ Global {87679336-95BE-47E4-B42B-8F6860A0B215}.Release|x64.Build.0 = Release|Any CPU {87679336-95BE-47E4-B42B-8F6860A0B215}.Release|x86.ActiveCfg = Release|Any CPU {87679336-95BE-47E4-B42B-8F6860A0B215}.Release|x86.Build.0 = Release|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug + MobileApps|Any CPU.ActiveCfg = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug + MobileApps|Any CPU.Build.0 = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug + MobileApps|ARM.ActiveCfg = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug + MobileApps|ARM.Build.0 = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug + MobileApps|ARM64.ActiveCfg = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug + MobileApps|ARM64.Build.0 = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug + MobileApps|iPhone.ActiveCfg = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug + MobileApps|iPhone.Build.0 = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug + MobileApps|iPhoneSimulator.ActiveCfg = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug + MobileApps|iPhoneSimulator.Build.0 = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug + MobileApps|x64.ActiveCfg = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug + MobileApps|x64.Build.0 = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug + MobileApps|x86.ActiveCfg = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug + MobileApps|x86.Build.0 = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug|Any CPU.Build.0 = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug|ARM.ActiveCfg = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug|ARM.Build.0 = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug|ARM64.ActiveCfg = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug|ARM64.Build.0 = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug|iPhone.ActiveCfg = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug|iPhone.Build.0 = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug|iPhoneSimulator.ActiveCfg = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug|iPhoneSimulator.Build.0 = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug|x64.ActiveCfg = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug|x64.Build.0 = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug|x86.ActiveCfg = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Debug|x86.Build.0 = Debug|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Release|Any CPU.ActiveCfg = Release|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Release|Any CPU.Build.0 = Release|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Release|ARM.ActiveCfg = Release|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Release|ARM.Build.0 = Release|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Release|ARM64.ActiveCfg = Release|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Release|ARM64.Build.0 = Release|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Release|iPhone.ActiveCfg = Release|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Release|iPhone.Build.0 = Release|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Release|iPhoneSimulator.ActiveCfg = Release|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Release|iPhoneSimulator.Build.0 = Release|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Release|x64.ActiveCfg = Release|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Release|x64.Build.0 = Release|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Release|x86.ActiveCfg = Release|Any CPU + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8}.Release|x86.Build.0 = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE @@ -1761,6 +1785,7 @@ Global {74805FE3-2E0D-4EAB-8CFE-A9D46F8D5972} = {34BE693E-3496-45A4-B1D2-D3A0E068EEDB} {92064C48-0136-48CD-AE8D-C6FEDBC7B639} = {74805FE3-2E0D-4EAB-8CFE-A9D46F8D5972} {87679336-95BE-47E4-B42B-8F6860A0B215} = {1A37FD75-94E9-4D6F-953A-0DABBD7B49E9} + {43BCA8C7-E9F4-4067-9F54-C2127B82B5E8} = {5FAAD966-36B8-4C19-A5FA-5410DD53063D} EndGlobalSection GlobalSection(ExtensibilityGlobals) = postSolution SolutionGuid = {020399A9-DC27-4B82-9CAA-EF488665AC27} diff --git a/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs b/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs index e2c1acf258..1a2b3e2e43 100644 --- a/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs +++ b/tests/Microsoft.Identity.Test.LabInfrastructure/CertificateHelper.cs @@ -44,14 +44,6 @@ public static X509Certificate2 FindCertificateByName(string certName, StoreLocat var certPasswrod = Environment.GetEnvironmentVariable("CERTIFICATE_PASSWORD"); var certLocation = Environment.GetEnvironmentVariable("CERTIFICATE_LOCATION"); var cert = new X509Certificate2(certLocation, certPasswrod, X509KeyStorageFlags.PersistKeySet | X509KeyStorageFlags.Exportable); - if (cert.HasPrivateKey) - { - Console.WriteLine("Private key is available."); - } - else - { - Console.WriteLine("Private key is missing."); - } return cert; } // Don't validate certs, since the test root isn't installed. From 08f28293c51ece3abbef9777cbea630fe56976e5 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Wed, 19 Feb 2025 22:11:08 -0800 Subject: [PATCH 128/137] Clean up code and address comments --- .../PlatformsCommon/Shared/DesktopOsHelper.cs | 13 ++++++--- .../ClientCredentialsTests.NetFwk.cs | 1 - .../HeadlessTests/RuntimeBrokerTests.cs | 27 +++++++++---------- .../Infrastructure/MsalAssert.cs | 2 +- 4 files changed, 23 insertions(+), 20 deletions(-) diff --git a/src/client/Microsoft.Identity.Client/PlatformsCommon/Shared/DesktopOsHelper.cs b/src/client/Microsoft.Identity.Client/PlatformsCommon/Shared/DesktopOsHelper.cs index ecd0408eeb..84b87cfb18 100644 --- a/src/client/Microsoft.Identity.Client/PlatformsCommon/Shared/DesktopOsHelper.cs +++ b/src/client/Microsoft.Identity.Client/PlatformsCommon/Shared/DesktopOsHelper.cs @@ -58,11 +58,18 @@ public static bool IsMac() #endif } - public static bool IsWslEnv() + private static bool IsWslEnv() { if (IsLinux()) { - var versionInfo = File.ReadAllText("/proc/version"); - return versionInfo.Contains("Microsoft") || versionInfo.Contains("WSL"); + try + { + var versionInfo = File.ReadAllText("/proc/version"); + return versionInfo.Contains("Microsoft") || versionInfo.Contains("WSL"); + } + catch + { + return false; // if we can't read the file, we can't determine if it's WSL + } } return false; } diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/ClientCredentialsTests.NetFwk.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/ClientCredentialsTests.NetFwk.cs index 68e0f39c92..d1c7b042a6 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/ClientCredentialsTests.NetFwk.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/ClientCredentialsTests.NetFwk.cs @@ -480,7 +480,6 @@ private static string GetSignedClientAssertionManual( { "sub", issuer } }; - // RSACng rsa = certificate.GetRSAPrivateKey() as RSACng; // cng is Windows specific, so we use RSA instead RSA rsa = certificate.GetRSAPrivateKey(); // Works cross-platform diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs index eda4552b56..455a047d4f 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/RuntimeBrokerTests.cs @@ -42,7 +42,7 @@ public class RuntimeBrokerTests //SSH User impersonation scope required for this test private string[] _SSH_scopes = new[] { "https://pas.windows.net/CheckMyAccess/Linux/user_impersonation" }; - private BrokerOptions _brokerOption = TestUtils.GetPlatformBroker(); + private BrokerOptions _brokerOptions = TestUtils.GetPlatformBroker(); private string CreateJwk() { @@ -71,7 +71,7 @@ public async Task WamSilentAuthUserInteractionRequiredAsync() .WithAuthority("https://login.microsoftonline.com/organizations"); IPublicClientApplication pca = pcaBuilder - .WithBroker(_brokerOption) + .WithBroker(_brokerOptions) .Build(); // Act @@ -106,7 +106,7 @@ public async Task ExtractNonceWithAuthParserAndValidateShrAsync() IPublicClientApplication pca = PublicClientApplicationBuilder .Create(labResponse.App.AppId) .WithAuthority(labResponse.Lab.Authority, "organizations") - .WithBroker(_brokerOption) + .WithBroker(_brokerOptions) .Build(); Assert.IsTrue(pca.IsProofOfPossessionSupportedByClient(), "Either the broker is not configured or it does not support POP."); @@ -150,7 +150,7 @@ public async Task WamInvalidROPC_ThrowsException_TestAsync() .Create(labResponse.App.AppId) .WithAuthority(labResponse.Lab.Authority, "organizations") .WithLogging(wastestLogger, enablePiiLogging: true) // it's important that the PII is turned on, otherwise context is 'pii' - .WithBroker(_brokerOption) + .WithBroker(_brokerOptions) .Build(); MsalServiceException ex = await AssertException.TaskThrowsAsync(() => @@ -183,7 +183,7 @@ public async Task WamSilentAuthLoginHintNoAccontInCacheAsync() .WithAuthority("https://login.microsoftonline.com/organizations"); IPublicClientApplication pca = pcaBuilder - .WithBroker(_brokerOption) + .WithBroker(_brokerOptions) .Build(); // Act @@ -207,7 +207,6 @@ public async Task WamUsernamePasswordRequestAsync() string[] scopes = { "User.Read" }; IntPtr intPtr = TestUtils.GetWindowHandle(); - // Assert.IsNotNull(intPtr); Func windowHandleProvider = () => intPtr; @@ -216,15 +215,13 @@ public async Task WamUsernamePasswordRequestAsync() .WithParentActivityOrWindow(windowHandleProvider) .WithAuthority(labResponse.Lab.Authority, "organizations") .WithLogging((x, y, z) => Debug.WriteLine($"{x} {y}"), LogLevel.Verbose, true) - .WithBroker(_brokerOption) + .WithBroker(_brokerOptions) .Build(); // Get Accounts var accounts = await pca.GetAccountsAsync().ConfigureAwait(false); - // Assert.IsNotNull(accounts); // Acquire token using username password - //var result = await pca.AcquireTokenInteractive(scopes).WithLoginHint(labResponse.User.Upn).WithPassword(labResponse.User.GetOrFetchPassword()).ExecuteAsync().ConfigureAwait(false); var result = await pca.AcquireTokenByUsernamePassword(scopes, labResponse.User.Upn, labResponse.User.GetOrFetchPassword()).ExecuteAsync().ConfigureAwait(false); MsalAssert.AssertAuthResult(result, TokenSource.Broker, labResponse.Lab.TenantId, scopes); Assert.IsNotNull(result.AuthenticationResultMetadata.Telemetry); @@ -269,7 +266,7 @@ public async Task WamWithSSHCertificateAuthenticationSchemeAsync() .WithTestLogging() .WithAuthority(labResponse.Lab.Authority, "organizations") .WithParentActivityOrWindow(windowHandleProvider) - .WithBroker(_brokerOption) + .WithBroker(_brokerOptions) .Build(); string jwk = CreateJwk(); @@ -310,7 +307,7 @@ public async Task WamUsernamePasswordWithForceRefreshAsync() .WithParentActivityOrWindow(windowHandleProvider) .WithAuthority(labResponse.Lab.Authority, "organizations") .WithLogging((x, y, z) => Debug.WriteLine($"{x} {y}"), LogLevel.Verbose, true) - .WithBroker(_brokerOption) + .WithBroker(_brokerOptions) .Build(); // Acquire token using username password @@ -364,7 +361,7 @@ public async Task WamUsernamePasswordRequestAsync_WithPiiAsync() .WithParentActivityOrWindow(windowHandleProvider) .WithAuthority(labResponse.Lab.Authority, "organizations") .WithLogging(testLogger, enablePiiLogging: true) - .WithBroker(_brokerOption) + .WithBroker(_brokerOptions) .Build(); // Acquire token using username password @@ -450,7 +447,7 @@ public async Task WamAddDefaultScopesWhenNoScopesArePassedAsync(string scopes) .Create("43dfbb29-3683-4673-a66f-baba91798bd2") .WithAuthority("https://login.microsoftonline.com/organizations") .WithParentActivityOrWindow(windowHandleProvider) - .WithBroker(_brokerOption) + .WithBroker(_brokerOptions) .Build(); // Act if (SharedUtilities.IsLinuxPlatform()) { @@ -488,7 +485,7 @@ public async Task WamUsernamePasswordPopTokenEnforcedWithCaOnValidResourceAsync( .Create(labResponse.App.AppId) .WithParentActivityOrWindow(windowHandleProvider) .WithAuthority(labResponse.Lab.Authority, "organizations") - .WithBroker(_brokerOption) + .WithBroker(_brokerOptions) .Build(); // Acquire token using username password with POP on a valid resource @@ -524,7 +521,7 @@ public async Task WamUsernamePasswordPopTokenEnforcedWithCaOnInValidResourceAsyn .Create(labResponse.App.AppId) .WithParentActivityOrWindow(windowHandleProvider) .WithAuthority(labResponse.Lab.Authority, "organizations") - .WithBroker(_brokerOption) + .WithBroker(_brokerOptions) .Build(); // Acquire token using username password with POP on a resource not in the CA policy diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/Infrastructure/MsalAssert.cs b/tests/Microsoft.Identity.Test.Integration.netcore/Infrastructure/MsalAssert.cs index 89cb0acc17..43e596fe6e 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/Infrastructure/MsalAssert.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/Infrastructure/MsalAssert.cs @@ -66,7 +66,7 @@ public static void AssertAuthResult(AuthenticationResult result, TokenSource tok Assert.AreEqual(TestConstants.Bearer, result.TokenType); } - // Assert.AreEqual(tokenSource, result.AuthenticationResultMetadata.TokenSource); + Assert.AreEqual(tokenSource, result.AuthenticationResultMetadata.TokenSource); Assert.AreEqual(tenantId, result.TenantId); } From 5334092af930d8243e003ad61b77f5b34dced2c0 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Thu, 20 Feb 2025 21:49:51 -0800 Subject: [PATCH 129/137] Address comment --- build/template-build-and-prep-automation.yaml | 10 ++++++++++ build/template-test-on-linux.yaml | 2 +- 2 files changed, 11 insertions(+), 1 deletion(-) diff --git a/build/template-build-and-prep-automation.yaml b/build/template-build-and-prep-automation.yaml index d942634bf3..e2a5797395 100644 --- a/build/template-build-and-prep-automation.yaml +++ b/build/template-build-and-prep-automation.yaml @@ -102,6 +102,16 @@ steps: } } + #check Linux runtime files + $linuxRuntimes = 'runtimes/linux-x64/native/libmsalruntime.so'; + $LinuxAppsToCheck = 'NetWSLWam\bin\Release\net8.0\'; + $appFullPath = $searchInFolder+$LinuxAppsToCheck+$linuxRuntimes + Write-Host $appFullPath + if (-not(Test-Path -Path $appFullPath -PathType Leaf)) + { + $errors += "Failed to find Linux runtime files in : " + $SearchInFolder + $app + "`n"; + } + #exit if there are errors IF (![string]::IsNullOrWhitespace($errors)) { diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index b412115ff1..b5b41e89ce 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -132,7 +132,7 @@ steps: script: 'nuget locals all -clear' - task: DotNetCoreCLI@2 - displayName: 'dotnet workload restore' + displayName: 'Wotnet workload restore' inputs: command: 'custom' custom: 'workload' From c0e17aaf40e20beee417c78da6ae2c1f04a0ee70 Mon Sep 17 00:00:00 2001 From: xinyuxu1026 <93947208+xinyuxu1026@users.noreply.github.com> Date: Thu, 20 Feb 2025 21:51:03 -0800 Subject: [PATCH 130/137] Update build/template-test-on-linux.yaml Co-authored-by: Gladwin Johnson <90415114+gladjohn@users.noreply.github.com> --- build/template-test-on-linux.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build/template-test-on-linux.yaml b/build/template-test-on-linux.yaml index b5b41e89ce..f0eca6131a 100644 --- a/build/template-test-on-linux.yaml +++ b/build/template-test-on-linux.yaml @@ -9,7 +9,7 @@ steps: - template: template-install-keyvault-secrets.yaml - task: Bash@3 - displayName: Install broker and depenencies + displayName: Install broker and dependencies inputs: targetType: 'inline' script: | From 5a021c8c8d680d7e77d6b958eb7c5e2b0325cece Mon Sep 17 00:00:00 2001 From: xinyuxu1026 <93947208+xinyuxu1026@users.noreply.github.com> Date: Thu, 20 Feb 2025 21:55:04 -0800 Subject: [PATCH 131/137] Update build/template-build-and-run-all-tests.yaml Co-authored-by: Gladwin Johnson <90415114+gladjohn@users.noreply.github.com> --- build/template-build-and-run-all-tests.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build/template-build-and-run-all-tests.yaml b/build/template-build-and-run-all-tests.yaml index 1cbaa096a3..8ae22e11b0 100644 --- a/build/template-build-and-run-all-tests.yaml +++ b/build/template-build-and-run-all-tests.yaml @@ -83,7 +83,7 @@ jobs: #Build and stage projects baseDefinitionId: '905' #this is the PR build and it is used as a baseline baseBranchRef: 'main' -- job: 'BuildandRunIntegrationTestsonLinux' +- job: 'BuildandRunIntegrationTestsOnLinux' pool: vmImage: 'ubuntu-22.04' demands: From 39bc569df4dbfe6908a405ec8473fff826b79cd9 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Thu, 20 Feb 2025 22:07:16 -0800 Subject: [PATCH 132/137] update slashes --- build/template-build-and-prep-automation.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build/template-build-and-prep-automation.yaml b/build/template-build-and-prep-automation.yaml index e2a5797395..0a8aeba828 100644 --- a/build/template-build-and-prep-automation.yaml +++ b/build/template-build-and-prep-automation.yaml @@ -103,7 +103,7 @@ steps: } #check Linux runtime files - $linuxRuntimes = 'runtimes/linux-x64/native/libmsalruntime.so'; + $linuxRuntimes = 'runtimes\linux-x64\native\libmsalruntime.so'; $LinuxAppsToCheck = 'NetWSLWam\bin\Release\net8.0\'; $appFullPath = $searchInFolder+$LinuxAppsToCheck+$linuxRuntimes Write-Host $appFullPath From 15d32b0be99a082dd07615c4dd60bc12fe518ac8 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Thu, 20 Feb 2025 22:18:41 -0800 Subject: [PATCH 133/137] add more comments --- tests/devapps/WAM/NetWSLWam/Class1.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/devapps/WAM/NetWSLWam/Class1.cs b/tests/devapps/WAM/NetWSLWam/Class1.cs index 8a07843227..826bddf419 100644 --- a/tests/devapps/WAM/NetWSLWam/Class1.cs +++ b/tests/devapps/WAM/NetWSLWam/Class1.cs @@ -33,7 +33,7 @@ public static async Task InvokeBrokerAsync() Func consoleWindowHandleProvider = () => _parentHandle; // 1. Configuration - read below about redirect URI - var pca = PublicClientApplicationBuilder.Create("04f0c124-f2bc-4f59-8241-bf6df9866bbd") + var pca = PublicClientApplicationBuilder.Create("4b0db8c2-9f26-4417-8bde-3f0e3656f8e0"/*Lab Public Multi-Tenant*/) .WithAuthority("https://login.microsoftonline.com/common") .WithDefaultRedirectUri() .WithBroker(new BrokerOptions(BrokerOptions.OperatingSystems.Linux){ From aa48c67be9b33c4871eb828700aeb9cdcccfd5a1 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Fri, 21 Feb 2025 13:54:00 -0800 Subject: [PATCH 134/137] add more comments --- .../Microsoft.Identity.Client.Broker/RuntimeBroker.cs | 10 +++++++--- .../HeadlessTests/PoPTests.NetFwk.cs | 1 - 2 files changed, 7 insertions(+), 4 deletions(-) diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index a58f734305..1704c12a2e 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -30,8 +30,12 @@ internal class RuntimeBroker : IBroker private readonly BrokerOptions _wamOptions; private static Exception s_initException; - [DllImport("libX11.so.6")] - private static extern IntPtr XOpenDisplay(string display); + // Linux broker's username password flow is via interactive calls + if (Environment.GetEnvironmentVariable("TF_BUILD") != null && DesktopOsHelper.IsLinux()) + { + [DllImport("libX11.so.6")] + private static extern IntPtr XOpenDisplay(string display); + } private static Dictionary LogLevelMap = new Dictionary() { @@ -406,7 +410,7 @@ public async Task AcquireTokenByUsernamePasswordAsync( // For Linux broker, use the interactive flow with username password to get the token if (Environment.GetEnvironmentVariable("TF_BUILD") != null && DesktopOsHelper.IsLinux()) { using (NativeInterop.AuthResult result = await s_lazyCore.Value.SignInInteractivelyAsync( - XOpenDisplay(":1"), + XOpenDisplay(Environment.GetEnvironmentVariable("DISPLAY")), authParams, authenticationRequestParameters.CorrelationId.ToString("D"), acquireTokenByUsernamePasswordParameters.Username, diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs index 3b44460bac..fc1fd96cc6 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs @@ -71,7 +71,6 @@ public async Task PoP_BearerAndPoP_CanCoexist_Async() await BearerAndPoP_CanCoexist_Async().ConfigureAwait(false); } - [DoNotRunOnLinux] // POP is not supported on Linux [TestMethod] public async Task HappyPath_Async() { From b4208ef509de06103a1cccf222fe328e5a03a81c Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Fri, 21 Feb 2025 14:04:04 -0800 Subject: [PATCH 135/137] fix --- .../Microsoft.Identity.Client.Broker/RuntimeBroker.cs | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-) diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index 1704c12a2e..5e974ac5da 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -31,11 +31,8 @@ internal class RuntimeBroker : IBroker private static Exception s_initException; // Linux broker's username password flow is via interactive calls - if (Environment.GetEnvironmentVariable("TF_BUILD") != null && DesktopOsHelper.IsLinux()) - { - [DllImport("libX11.so.6")] - private static extern IntPtr XOpenDisplay(string display); - } + [DllImport("libX11.so.6")] + private static extern IntPtr XOpenDisplay(string display); private static Dictionary LogLevelMap = new Dictionary() { From 028ad8f63e4df61f84b80e4802973ac2b56514a3 Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Fri, 21 Feb 2025 14:30:18 -0800 Subject: [PATCH 136/137] update --- src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs index 5e974ac5da..bf455109f3 100644 --- a/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs +++ b/src/client/Microsoft.Identity.Client.Broker/RuntimeBroker.cs @@ -407,7 +407,7 @@ public async Task AcquireTokenByUsernamePasswordAsync( // For Linux broker, use the interactive flow with username password to get the token if (Environment.GetEnvironmentVariable("TF_BUILD") != null && DesktopOsHelper.IsLinux()) { using (NativeInterop.AuthResult result = await s_lazyCore.Value.SignInInteractivelyAsync( - XOpenDisplay(Environment.GetEnvironmentVariable("DISPLAY")), + XOpenDisplay(":1"), authParams, authenticationRequestParameters.CorrelationId.ToString("D"), acquireTokenByUsernamePasswordParameters.Username, From e8abd4ffee624e780419d712d3ca06d2431c51dd Mon Sep 17 00:00:00 2001 From: Xinyu Xu Date: Fri, 21 Feb 2025 15:04:52 -0800 Subject: [PATCH 137/137] try enable pop --- .../HeadlessTests/PoPTests.NetFwk.cs | 1 - 1 file changed, 1 deletion(-) diff --git a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs index fc1fd96cc6..a2e2757708 100644 --- a/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs +++ b/tests/Microsoft.Identity.Test.Integration.netcore/HeadlessTests/PoPTests.NetFwk.cs @@ -56,7 +56,6 @@ public void TestInitialize() TestCommon.ResetInternalStaticCaches(); } - [DoNotRunOnLinux] // POP is not supported on Linux [RunOn(TargetFrameworks.NetCore)] public async Task PoP_MultipleKeys_Async() {