Skip to content

Commit

Permalink
Drop WPF-based UI helpers on Windows (#1417)
Browse files Browse the repository at this point in the history
We've been shipping with the in-process Avalonia-based UI helpers on all
platforms, including Windows, since [GCM
2.1.2](https://github.com/git-ecosystem/git-credential-manager/releases/tag/v2.1.2),
and have not seen any major issues.

Drop all the WPF projects and code, but retain then UI helper command
infrastructure as this is useful for reference and future testing and UI
mocking.
  • Loading branch information
mjcheetham authored Sep 21, 2023
2 parents 6e49d9e + 1e904d1 commit ac0b264
Show file tree
Hide file tree
Showing 71 changed files with 61 additions and 3,753 deletions.
65 changes: 0 additions & 65 deletions Git-Credential-Manager.sln
Original file line number Diff line number Diff line change
Expand Up @@ -35,24 +35,14 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Atlassian.Bitbucket", "src\
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Atlassian.Bitbucket.Tests", "src\shared\Atlassian.Bitbucket.Tests\Atlassian.Bitbucket.Tests.csproj", "{025E5329-A0B1-4BA9-9203-B70B44A5F9E0}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Core.UI.Windows", "src\windows\Core.UI.Windows\Core.UI.Windows.csproj", "{2B3CD8FF-84A6-4B53-A28B-D7A75B0AB4D7}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Packaging.Linux", "src\linux\Packaging.Linux\Packaging.Linux.csproj", "{AD2A935F-3720-4802-8119-6A9B35B254DF}"
EndProject
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "linux", "linux", "{8F9D7E67-7DD7-4E32-9134-423281AF00E9}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "GitHub.UI.Windows", "src\windows\GitHub.UI.Windows\GitHub.UI.Windows.csproj", "{0A86ED89-1FC5-42AA-925C-4578FA30607A}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Atlassian.Bitbucket.UI.Windows", "src\windows\Atlassian.Bitbucket.UI.Windows\Atlassian.Bitbucket.UI.Windows.csproj", "{3F015046-DAF2-4D2A-96EC-F9782F169E45}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "GitLab", "src\shared\GitLab\GitLab.csproj", "{570897DC-A85C-4598-B793-9A00CF710119}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "GitLab.Tests", "src\shared\GitLab.Tests\GitLab.Tests.csproj", "{1AF9F7C5-FA2E-48F1-B216-4D5E9A27F393}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "GitLab.UI.Windows", "src\windows\GitLab.UI.Windows\GitLab.UI.Windows.csproj", "{83EAC1F9-8E1F-41FC-8FC9-2C452452D64E}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Git-Credential-Manager.UI.Windows", "src\windows\Git-Credential-Manager.UI.Windows\Git-Credential-Manager.UI.Windows.csproj", "{01BF56EC-AAC1-4BCA-8204-EE51D968DF5C}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
Expand Down Expand Up @@ -245,16 +235,6 @@ Global
{025E5329-A0B1-4BA9-9203-B70B44A5F9E0}.MacRelease|Any CPU.Build.0 = Release|Any CPU
{025E5329-A0B1-4BA9-9203-B70B44A5F9E0}.WindowsRelease|Any CPU.ActiveCfg = Release|Any CPU
{025E5329-A0B1-4BA9-9203-B70B44A5F9E0}.WindowsRelease|Any CPU.Build.0 = Release|Any CPU
{2B3CD8FF-84A6-4B53-A28B-D7A75B0AB4D7}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{2B3CD8FF-84A6-4B53-A28B-D7A75B0AB4D7}.MacDebug|Any CPU.ActiveCfg = Debug|Any CPU
{2B3CD8FF-84A6-4B53-A28B-D7A75B0AB4D7}.Release|Any CPU.ActiveCfg = Release|Any CPU
{2B3CD8FF-84A6-4B53-A28B-D7A75B0AB4D7}.WindowsDebug|Any CPU.ActiveCfg = Debug|Any CPU
{2B3CD8FF-84A6-4B53-A28B-D7A75B0AB4D7}.WindowsDebug|Any CPU.Build.0 = Debug|Any CPU
{2B3CD8FF-84A6-4B53-A28B-D7A75B0AB4D7}.MacRelease|Any CPU.ActiveCfg = Release|Any CPU
{2B3CD8FF-84A6-4B53-A28B-D7A75B0AB4D7}.WindowsRelease|Any CPU.ActiveCfg = Release|Any CPU
{2B3CD8FF-84A6-4B53-A28B-D7A75B0AB4D7}.WindowsRelease|Any CPU.Build.0 = Release|Any CPU
{2B3CD8FF-84A6-4B53-A28B-D7A75B0AB4D7}.LinuxDebug|Any CPU.ActiveCfg = Debug|Any CPU
{2B3CD8FF-84A6-4B53-A28B-D7A75B0AB4D7}.LinuxRelease|Any CPU.ActiveCfg = Release|Any CPU
{AD2A935F-3720-4802-8119-6A9B35B254DF}.LinuxDebug|Any CPU.ActiveCfg = Debug|Any CPU
{AD2A935F-3720-4802-8119-6A9B35B254DF}.LinuxDebug|Any CPU.Build.0 = Debug|Any CPU
{AD2A935F-3720-4802-8119-6A9B35B254DF}.LinuxRelease|Any CPU.ActiveCfg = Release|Any CPU
Expand All @@ -265,26 +245,6 @@ Global
{AD2A935F-3720-4802-8119-6A9B35B254DF}.WindowsDebug|Any CPU.ActiveCfg = Debug|Any CPU
{AD2A935F-3720-4802-8119-6A9B35B254DF}.WindowsRelease|Any CPU.ActiveCfg = Release|Any CPU
{AD2A935F-3720-4802-8119-6A9B35B254DF}.LinuxRelease|Any CPU.Build.0 = Release|Any CPU
{0A86ED89-1FC5-42AA-925C-4578FA30607A}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{0A86ED89-1FC5-42AA-925C-4578FA30607A}.MacDebug|Any CPU.ActiveCfg = Debug|Any CPU
{0A86ED89-1FC5-42AA-925C-4578FA30607A}.Release|Any CPU.ActiveCfg = Release|Any CPU
{0A86ED89-1FC5-42AA-925C-4578FA30607A}.WindowsDebug|Any CPU.ActiveCfg = Debug|Any CPU
{0A86ED89-1FC5-42AA-925C-4578FA30607A}.WindowsDebug|Any CPU.Build.0 = Debug|Any CPU
{0A86ED89-1FC5-42AA-925C-4578FA30607A}.LinuxDebug|Any CPU.ActiveCfg = Debug|Any CPU
{0A86ED89-1FC5-42AA-925C-4578FA30607A}.LinuxRelease|Any CPU.ActiveCfg = Release|Any CPU
{0A86ED89-1FC5-42AA-925C-4578FA30607A}.MacRelease|Any CPU.ActiveCfg = Release|Any CPU
{0A86ED89-1FC5-42AA-925C-4578FA30607A}.WindowsRelease|Any CPU.ActiveCfg = Release|Any CPU
{0A86ED89-1FC5-42AA-925C-4578FA30607A}.WindowsRelease|Any CPU.Build.0 = Release|Any CPU
{3F015046-DAF2-4D2A-96EC-F9782F169E45}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{3F015046-DAF2-4D2A-96EC-F9782F169E45}.MacDebug|Any CPU.ActiveCfg = Debug|Any CPU
{3F015046-DAF2-4D2A-96EC-F9782F169E45}.Release|Any CPU.ActiveCfg = Release|Any CPU
{3F015046-DAF2-4D2A-96EC-F9782F169E45}.WindowsDebug|Any CPU.ActiveCfg = Debug|Any CPU
{3F015046-DAF2-4D2A-96EC-F9782F169E45}.WindowsDebug|Any CPU.Build.0 = Debug|Any CPU
{3F015046-DAF2-4D2A-96EC-F9782F169E45}.LinuxDebug|Any CPU.ActiveCfg = Debug|Any CPU
{3F015046-DAF2-4D2A-96EC-F9782F169E45}.LinuxRelease|Any CPU.ActiveCfg = Release|Any CPU
{3F015046-DAF2-4D2A-96EC-F9782F169E45}.MacRelease|Any CPU.ActiveCfg = Release|Any CPU
{3F015046-DAF2-4D2A-96EC-F9782F169E45}.WindowsRelease|Any CPU.ActiveCfg = Release|Any CPU
{3F015046-DAF2-4D2A-96EC-F9782F169E45}.WindowsRelease|Any CPU.Build.0 = Release|Any CPU
{570897DC-A85C-4598-B793-9A00CF710119}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{570897DC-A85C-4598-B793-9A00CF710119}.Debug|Any CPU.Build.0 = Debug|Any CPU
{570897DC-A85C-4598-B793-9A00CF710119}.MacDebug|Any CPU.ActiveCfg = Debug|Any CPU
Expand Down Expand Up @@ -317,26 +277,6 @@ Global
{1AF9F7C5-FA2E-48F1-B216-4D5E9A27F393}.MacRelease|Any CPU.Build.0 = Release|Any CPU
{1AF9F7C5-FA2E-48F1-B216-4D5E9A27F393}.WindowsRelease|Any CPU.ActiveCfg = Release|Any CPU
{1AF9F7C5-FA2E-48F1-B216-4D5E9A27F393}.WindowsRelease|Any CPU.Build.0 = Release|Any CPU
{83EAC1F9-8E1F-41FC-8FC9-2C452452D64E}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{83EAC1F9-8E1F-41FC-8FC9-2C452452D64E}.MacDebug|Any CPU.ActiveCfg = Debug|Any CPU
{83EAC1F9-8E1F-41FC-8FC9-2C452452D64E}.Release|Any CPU.ActiveCfg = Release|Any CPU
{83EAC1F9-8E1F-41FC-8FC9-2C452452D64E}.WindowsDebug|Any CPU.ActiveCfg = Debug|Any CPU
{83EAC1F9-8E1F-41FC-8FC9-2C452452D64E}.WindowsDebug|Any CPU.Build.0 = Debug|Any CPU
{83EAC1F9-8E1F-41FC-8FC9-2C452452D64E}.LinuxDebug|Any CPU.ActiveCfg = Debug|Any CPU
{83EAC1F9-8E1F-41FC-8FC9-2C452452D64E}.LinuxRelease|Any CPU.ActiveCfg = Release|Any CPU
{83EAC1F9-8E1F-41FC-8FC9-2C452452D64E}.MacRelease|Any CPU.ActiveCfg = Release|Any CPU
{83EAC1F9-8E1F-41FC-8FC9-2C452452D64E}.WindowsRelease|Any CPU.ActiveCfg = Release|Any CPU
{83EAC1F9-8E1F-41FC-8FC9-2C452452D64E}.WindowsRelease|Any CPU.Build.0 = Release|Any CPU
{01BF56EC-AAC1-4BCA-8204-EE51D968DF5C}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{01BF56EC-AAC1-4BCA-8204-EE51D968DF5C}.MacDebug|Any CPU.ActiveCfg = Debug|Any CPU
{01BF56EC-AAC1-4BCA-8204-EE51D968DF5C}.MacRelease|Any CPU.ActiveCfg = Release|Any CPU
{01BF56EC-AAC1-4BCA-8204-EE51D968DF5C}.Release|Any CPU.ActiveCfg = Release|Any CPU
{01BF56EC-AAC1-4BCA-8204-EE51D968DF5C}.WindowsDebug|Any CPU.ActiveCfg = Debug|Any CPU
{01BF56EC-AAC1-4BCA-8204-EE51D968DF5C}.WindowsDebug|Any CPU.Build.0 = Debug|Any CPU
{01BF56EC-AAC1-4BCA-8204-EE51D968DF5C}.WindowsRelease|Any CPU.ActiveCfg = Debug|Any CPU
{01BF56EC-AAC1-4BCA-8204-EE51D968DF5C}.WindowsRelease|Any CPU.Build.0 = Release|Any CPU
{01BF56EC-AAC1-4BCA-8204-EE51D968DF5C}.LinuxDebug|Any CPU.ActiveCfg = Debug|Any CPU
{01BF56EC-AAC1-4BCA-8204-EE51D968DF5C}.LinuxRelease|Any CPU.ActiveCfg = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
Expand All @@ -357,15 +297,10 @@ Global
{85903170-9E52-4B53-A6E4-3F416F684FAE} = {66722747-1B61-40E4-A89B-1AC8E6D62EA9}
{B49881A6-E734-490E-8EA7-FB0D9E296CFB} = {D5277A0E-997E-453A-8CB9-4EFCC8B16A29}
{025E5329-A0B1-4BA9-9203-B70B44A5F9E0} = {D5277A0E-997E-453A-8CB9-4EFCC8B16A29}
{2B3CD8FF-84A6-4B53-A28B-D7A75B0AB4D7} = {66722747-1B61-40E4-A89B-1AC8E6D62EA9}
{8F9D7E67-7DD7-4E32-9134-423281AF00E9} = {A7FC1234-95E3-4496-B5F7-4306F41E6A0E}
{AD2A935F-3720-4802-8119-6A9B35B254DF} = {8F9D7E67-7DD7-4E32-9134-423281AF00E9}
{0A86ED89-1FC5-42AA-925C-4578FA30607A} = {66722747-1B61-40E4-A89B-1AC8E6D62EA9}
{3F015046-DAF2-4D2A-96EC-F9782F169E45} = {66722747-1B61-40E4-A89B-1AC8E6D62EA9}
{570897DC-A85C-4598-B793-9A00CF710119} = {D5277A0E-997E-453A-8CB9-4EFCC8B16A29}
{1AF9F7C5-FA2E-48F1-B216-4D5E9A27F393} = {D5277A0E-997E-453A-8CB9-4EFCC8B16A29}
{83EAC1F9-8E1F-41FC-8FC9-2C452452D64E} = {66722747-1B61-40E4-A89B-1AC8E6D62EA9}
{01BF56EC-AAC1-4BCA-8204-EE51D968DF5C} = {66722747-1B61-40E4-A89B-1AC8E6D62EA9}
EndGlobalSection
GlobalSection(ExtensibilityGlobals) = postSolution
SolutionGuid = {0EF9FC65-E6BA-45D4-A455-262A9EA4366B}
Expand Down
96 changes: 10 additions & 86 deletions src/shared/Core/Authentication/MicrosoftAuthentication.cs
Original file line number Diff line number Diff line change
Expand Up @@ -11,13 +11,12 @@
using System.Text;
using System.Threading;
using GitCredentialManager.UI;
using GitCredentialManager.UI.Controls;
using GitCredentialManager.UI.ViewModels;
using GitCredentialManager.UI.Views;
using Microsoft.Identity.Client.AppConfig;

#if NETFRAMEWORK
using System.Drawing;
using System.Windows.Forms;
using Microsoft.Identity.Client.Broker;
#endif

Expand Down Expand Up @@ -118,10 +117,6 @@ public class MicrosoftAuthentication : AuthenticationBase, IMicrosoftAuthenticat
"live", "liveconnect", "liveid",
};

#if NETFRAMEWORK
private DummyWindow _dummyWindow;
#endif

public MicrosoftAuthentication(ICommandContext context)
: base(context) { }

Expand All @@ -130,6 +125,8 @@ public MicrosoftAuthentication(ICommandContext context)
public async Task<IMicrosoftAuthenticationResult> GetTokenForUserAsync(
string authority, string clientId, Uri redirectUri, string[] scopes, string userName, bool msaPt)
{
var uiCts = new CancellationTokenSource();

// Check if we can and should use OS broker authentication
bool useBroker = CanUseBroker();
Context.Trace.WriteLine(useBroker
Expand All @@ -144,7 +141,7 @@ public async Task<IMicrosoftAuthenticationResult> GetTokenForUserAsync(
try
{
// Create the public client application for authentication
IPublicClientApplication app = await CreatePublicClientApplicationAsync(authority, clientId, redirectUri, useBroker, msaPt);
IPublicClientApplication app = await CreatePublicClientApplicationAsync(authority, clientId, redirectUri, useBroker, msaPt, uiCts);

AuthenticationResult result = null;

Expand Down Expand Up @@ -261,10 +258,8 @@ public async Task<IMicrosoftAuthenticationResult> GetTokenForUserAsync(
}
finally
{
#if NETFRAMEWORK
// If we created a dummy window during authentication we should dispose of it now that we're done
_dummyWindow?.Dispose();
#endif
// If we created some global UI (e.g. progress) during authentication we should dismiss them now that we're done
uiCts.Cancel();
}
}

Expand Down Expand Up @@ -451,8 +446,8 @@ private async Task<AuthenticationResult> GetAccessTokenSilentlyAsync(
}
}

private async Task<IPublicClientApplication> CreatePublicClientApplicationAsync(
string authority, string clientId, Uri redirectUri, bool enableBroker, bool msaPt)
private async Task<IPublicClientApplication> CreatePublicClientApplicationAsync(string authority,
string clientId, Uri redirectUri, bool enableBroker, bool msaPt, CancellationTokenSource uiCts)
{
var httpFactoryAdaptor = new MsalHttpClientFactoryAdaptor(Context.HttpClientFactory);

Expand Down Expand Up @@ -495,11 +490,8 @@ private async Task<IPublicClientApplication> CreatePublicClientApplicationAsync(
}
else if (enableBroker) // Only actually need to set a parent window when using the Windows broker
{
#if NETFRAMEWORK
Context.Trace.WriteLine($"Using dummy parent window for MSAL authentication dialogs.");
_dummyWindow = new DummyWindow();
appBuilder.WithParentActivityOrWindow(_dummyWindow.ShowAndGetHandle);
#endif
Context.Trace.WriteLine("Using progress parent window for MSAL authentication dialogs.");
appBuilder.WithParentActivityOrWindow(() => ProgressWindow.ShowAndGetHandle(uiCts.Token));
}
}
}
Expand Down Expand Up @@ -899,73 +891,5 @@ public MsalResult(AuthenticationResult msalResult)
public string AccessToken => _msalResult.AccessToken;
public string AccountUpn => _msalResult.Account?.Username;
}

#if NETFRAMEWORK
private class DummyWindow : IDisposable
{
private readonly Thread _staThread;
private readonly ManualResetEventSlim _readyEvent;
private Form _window;
private IntPtr _handle;

public DummyWindow()
{
_staThread = new Thread(ThreadProc);
_staThread.SetApartmentState(ApartmentState.STA);
_readyEvent = new ManualResetEventSlim();
}

public IntPtr ShowAndGetHandle()
{
_staThread.Start();
_readyEvent.Wait();
return _handle;
}

public void Dispose()
{
_window?.Invoke(() => _window.Close());

if (_staThread.IsAlive)
{
_staThread.Join();
}
}

private void ThreadProc()
{
System.Windows.Forms.Application.EnableVisualStyles();
_window = new Form
{
TopMost = true,
ControlBox = false,
MaximizeBox = false,
MinimizeBox = false,
ClientSize = new Size(182, 46),
FormBorderStyle = FormBorderStyle.None,
StartPosition = FormStartPosition.CenterScreen,
};

var progress = new ProgressBar
{
Style = ProgressBarStyle.Marquee,
Location = new Point(12, 12),
Size = new Size(158, 23),
MarqueeAnimationSpeed = 30,
};

_window.Controls.Add(progress);
_window.Shown += (s, e) =>
{
_handle = _window.Handle;
_readyEvent.Set();
};

_window.ShowDialog();
_window.Dispose();
_window = null;
}
}
#endif
}
}
14 changes: 14 additions & 0 deletions src/shared/Core/UI/Controls/ProgressWindow.axaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
<Window xmlns="https://github.com/avaloniaui"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d" d:DesignWidth="182" d:DesignHeight="46"
SizeToContent="WidthAndHeight" CanResize="False" Topmost="True"
ExtendClientAreaChromeHints="NoChrome" ExtendClientAreaToDecorationsHint="True"
ShowInTaskbar="False" Title="Git Credential Manager" WindowStartupLocation="CenterScreen"
x:Class="GitCredentialManager.UI.Controls.ProgressWindow">
<ProgressBar Orientation="Horizontal"
IsIndeterminate="True"
Margin="20"
Width="158" Height="23" />
</Window>
37 changes: 37 additions & 0 deletions src/shared/Core/UI/Controls/ProgressWindow.axaml.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
using System;
using System.Threading;
using System.Threading.Tasks;
using Avalonia;
using Avalonia.Controls;
using Avalonia.Markup.Xaml;

namespace GitCredentialManager.UI.Controls;

public partial class ProgressWindow : Window
{
public ProgressWindow()
{
InitializeComponent();
}

private void InitializeComponent()
{
AvaloniaXamlLoader.Load(this);
}

public static IntPtr ShowAndGetHandle(CancellationToken ct)
{
var tsc = new TaskCompletionSource<IntPtr>();

Window CreateWindow()
{
var window = new ProgressWindow();
window.Loaded += (s, e) => tsc.SetResult(window.TryGetPlatformHandle()?.Handle ?? IntPtr.Zero);
return window;
}

Task _ = AvaloniaUi.ShowWindowAsync(CreateWindow, IntPtr.Zero, ct);

return tsc.Task.GetAwaiter().GetResult();
}
}
6 changes: 0 additions & 6 deletions src/windows/Atlassian.Bitbucket.UI.Windows/Assets/Styles.xaml

This file was deleted.

Binary file not shown.

This file was deleted.

This file was deleted.

Loading

0 comments on commit ac0b264

Please sign in to comment.