diff --git a/src/CredentialManager/CredentialManager.cs b/src/CredentialManager/CredentialManager.cs index e9447b5..f9c00aa 100644 --- a/src/CredentialManager/CredentialManager.cs +++ b/src/CredentialManager/CredentialManager.cs @@ -1,6 +1,5 @@ using System; -using GitCredentialManager.Interop.MacOS; -using GitCredentialManager.Interop.Windows; +using System.Collections.Generic; namespace GitCredentialManager; @@ -18,13 +17,108 @@ public static class CredentialManager /// The . public static ICredentialStore Create(string? @namespace = default) { - if (PlatformUtils.IsWindows()) - return new WindowsCredentialManager(@namespace); - else if (PlatformUtils.IsMacOS()) - return new MacOSKeychain(@namespace); - else if (PlatformUtils.IsLinux()) - return new CommandContext().CredentialStore; - else - throw new PlatformNotSupportedException(); + using var context = new CommandContextWrapper(new CommandContext(), @namespace); + // The context already does the check for the platform and configured store to initialize. + // By overriding the settings with our wrapper, we ensure just the namespace is overriden. + return context.CredentialStore; + } + + class CommandContextWrapper(CommandContext context, string? @namespace) : ICommandContext + { + ISettings settings = new SettingsWrapper(context.Settings, @namespace); + + public ISettings Settings => settings; + + #region pass-through impl. + + public string ApplicationPath { get => ((ICommandContext)context).ApplicationPath; set => ((ICommandContext)context).ApplicationPath = value; } + + public string InstallationDirectory => ((ICommandContext)context).InstallationDirectory; + + public IStandardStreams Streams => ((ICommandContext)context).Streams; + + public ITerminal Terminal => ((ICommandContext)context).Terminal; + + public ISessionManager SessionManager => ((ICommandContext)context).SessionManager; + + public ITrace Trace => ((ICommandContext)context).Trace; + + public ITrace2 Trace2 => ((ICommandContext)context).Trace2; + + public IFileSystem FileSystem => ((ICommandContext)context).FileSystem; + + public ICredentialStore CredentialStore => ((ICommandContext)context).CredentialStore; + + public IHttpClientFactory HttpClientFactory => ((ICommandContext)context).HttpClientFactory; + + public IGit Git => ((ICommandContext)context).Git; + + public IEnvironment Environment => ((ICommandContext)context).Environment; + + public IProcessManager ProcessManager => ((ICommandContext)context).ProcessManager; + + public void Dispose() => ((IDisposable)context).Dispose(); + + #endregion + } + + class SettingsWrapper(ISettings settings, string? @namespace) : ISettings + { + // Overriden namespace to scope credential operations. + public string CredentialNamespace => @namespace ?? settings.CredentialNamespace; + + #region pass-through impl. + + public Uri RemoteUri { get => settings.RemoteUri; set => settings.RemoteUri = value; } + + public bool IsDebuggingEnabled => settings.IsDebuggingEnabled; + + public bool IsTerminalPromptsEnabled => settings.IsTerminalPromptsEnabled; + + public bool IsGuiPromptsEnabled { get => settings.IsGuiPromptsEnabled; set => settings.IsGuiPromptsEnabled = value; } + + public bool IsInteractionAllowed => settings.IsInteractionAllowed; + + public bool IsSecretTracingEnabled => settings.IsSecretTracingEnabled; + + public bool IsMsalTracingEnabled => settings.IsMsalTracingEnabled; + + public string ProviderOverride => settings.ProviderOverride; + + public string LegacyAuthorityOverride => settings.LegacyAuthorityOverride; + + public bool IsWindowsIntegratedAuthenticationEnabled => settings.IsWindowsIntegratedAuthenticationEnabled; + + public bool IsCertificateVerificationEnabled => settings.IsCertificateVerificationEnabled; + + public bool AutomaticallyUseClientCertificates => settings.AutomaticallyUseClientCertificates; + + public string ParentWindowId => settings.ParentWindowId; + + public string CredentialBackingStore => settings.CredentialBackingStore; + + public string CustomCertificateBundlePath => settings.CustomCertificateBundlePath; + + public string CustomCookieFilePath => settings.CustomCookieFilePath; + + public TlsBackend TlsBackend => settings.TlsBackend; + + public bool UseCustomCertificateBundleWithSchannel => settings.UseCustomCertificateBundleWithSchannel; + + public int AutoDetectProviderTimeout => settings.AutoDetectProviderTimeout; + + public bool UseMsAuthDefaultAccount => settings.UseMsAuthDefaultAccount; + + public bool UseSoftwareRendering => settings.UseSoftwareRendering; + + public void Dispose() => settings.Dispose(); + public ProxyConfiguration GetProxyConfiguration() => settings.GetProxyConfiguration(); + public IEnumerable GetSettingValues(string envarName, string section, string property, bool isPath) => settings.GetSettingValues(envarName, section, property, isPath); + public Trace2Settings GetTrace2Settings() => settings.GetTrace2Settings(); + public bool GetTracingEnabled(out string value) => settings.GetTracingEnabled(out value); + public bool TryGetPathSetting(string envarName, string section, string property, out string value) => settings.TryGetPathSetting(envarName, section, property, out value); + public bool TryGetSetting(string envarName, string section, string property, out string value) => settings.TryGetSetting(envarName, section, property, out value); + + #endregion } }