694 строки
26 KiB
C#
694 строки
26 KiB
C#
/**** Git Credential Manager for Windows ****
|
|
*
|
|
* Copyright (c) Microsoft Corporation
|
|
* All rights reserved.
|
|
*
|
|
* MIT License
|
|
*
|
|
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
* of this software and associated documentation files (the """"Software""""), to deal
|
|
* in the Software without restriction, including without limitation the rights to
|
|
* use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
|
|
* the Software, and to permit persons to whom the Software is furnished to do so,
|
|
* subject to the following conditions:
|
|
*
|
|
* The above copyright notice and this permission notice shall be included in all
|
|
* copies or substantial portions of the Software.
|
|
*
|
|
* THE SOFTWARE IS PROVIDED *AS IS*, WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
|
|
* FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
|
|
* COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
|
|
* AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
|
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE."
|
|
**/
|
|
|
|
using System;
|
|
using System.Collections.Generic;
|
|
using System.Diagnostics;
|
|
using System.IO;
|
|
using System.Net;
|
|
using System.Runtime.CompilerServices;
|
|
using System.Threading;
|
|
using System.Threading.Tasks;
|
|
using Microsoft.Alm.Authentication;
|
|
using Azure = AzureDevOps.Authentication;
|
|
using Bitbucket = Atlassian.Bitbucket.Authentication;
|
|
using Git = Microsoft.Alm.Authentication.Git;
|
|
using Github = GitHub.Authentication;
|
|
|
|
namespace Microsoft.Alm.Cli
|
|
{
|
|
enum KeyType
|
|
{
|
|
Authority,
|
|
ConfigNoLocal,
|
|
ConfigNoSystem,
|
|
DevOpsScope,
|
|
HttpPath,
|
|
HttpProxy,
|
|
HttpsProxy,
|
|
HttpTimeout,
|
|
HttpUserAgent,
|
|
Interactive,
|
|
ModalPrompt,
|
|
Namespace,
|
|
PreserveCredentials,
|
|
TokenDuration,
|
|
UrlOverride,
|
|
Username,
|
|
Validate,
|
|
ParentHwnd,
|
|
VstsScope,
|
|
Writelog,
|
|
}
|
|
|
|
partial class Program
|
|
{
|
|
public const string SourceUrl = "https://github.com/Microsoft/Git-Credential-Manager-for-Windows";
|
|
public const string EventSource = "Git Credential Manager";
|
|
|
|
internal static readonly StringComparer ConfigKeyComparer = StringComparer.OrdinalIgnoreCase;
|
|
internal static readonly StringComparer ConfigValueComparer = StringComparer.OrdinalIgnoreCase;
|
|
|
|
internal const string EnvironConfigDebugKey = "GCM_DEBUG";
|
|
internal const string EnvironConfigTraceKey = "GCM_TRACE";
|
|
|
|
internal static readonly StringComparer EnvironKeyComparer = StringComparer.OrdinalIgnoreCase;
|
|
|
|
internal const string ConfigPrefix = "credential";
|
|
internal const string SecretsNamespace = "git";
|
|
|
|
internal static readonly Azure.TokenScope DevOpsCredentialScope = Azure.TokenScope.CodeWrite | Azure.TokenScope.PackagingRead;
|
|
internal static readonly Github.TokenScope GitHubCredentialScope = Github.TokenScope.Gist | Github.TokenScope.Repo;
|
|
|
|
internal BasicCredentialPromptDelegate _basicCredentialPrompt = ConsoleFunctions.CredentialPrompt;
|
|
internal BitbucketCredentialPromptDelegate _bitbucketCredentialPrompt = BitbucketFunctions.CredentialPrompt;
|
|
internal BitbucketOAuthPromptDelegate _bitbucketOauthPrompt = BitbucketFunctions.OAuthPrompt;
|
|
internal CreateAuthenticationDelegate _createAuthentication = CommonFunctions.CreateAuthentication;
|
|
internal DeleteCredentialsDelegate _deleteCredentials = CommonFunctions.DeleteCredentials;
|
|
internal DieExceptionDelegate _dieException = CommonFunctions.DieException;
|
|
internal DieMessageDelegate _dieMessage = CommonFunctions.DieMessage;
|
|
internal EnableTraceLoggingDelegate _enableTraceLogging = CommonFunctions.EnableTraceLogging;
|
|
internal EnableTraceLoggingFileDelegate _enableTraceLoggingFile = CommonFunctions.EnableTraceLoggingFile;
|
|
internal ExitDelegate _exit = ConsoleFunctions.Exit;
|
|
internal GitHubAuthCodePromptDelegate _gitHubAuthCodePrompt = GitHubFunctions.AuthCodePrompt;
|
|
internal GitHubCredentialPromptDelegate _gitHubCredentialPrompt = GitHubFunctions.CredentialPrompt;
|
|
internal LoadOperationArgumentsDelegate _loadOperationArguments = CommonFunctions.LoadOperationArguments;
|
|
internal LogEventDelegate _logEvent = CommonFunctions.LogEvent;
|
|
internal ModalPromptDisplayDialogDelegate _modalPromptDisplayDialog = DialogFunctions.DisplayModal;
|
|
internal ModalPromptForCredentialsDelegate _modalPromptForCredentials = DialogFunctions.CredentialPrompt;
|
|
internal ModalPromptForPasswordDelegate _modalPromptForPassword = DialogFunctions.PasswordPrompt;
|
|
internal OpenStandardHandleDelegate _openStandardErrorStream = ConsoleFunctions.OpenStandardErrorStream;
|
|
internal GetStandardWriterDelegate _openStandardErrorWriter = ConsoleFunctions.OpenStandardErrorWriter;
|
|
internal OpenStandardHandleDelegate _openStandardInputStream = ConsoleFunctions.OpenStandardInputStream;
|
|
internal GetStandardReaderDelegate _openStandardInputReader = ConsoleFunctions.OpenStandardInputReader;
|
|
internal OpenStandardHandleDelegate _openStandardOutputStream = ConsoleFunctions.OpenStandardOutputStream;
|
|
internal GetStandardWriterDelegate _openStandardOutputWriter = ConsoleFunctions.OpenStandardOutputWriter;
|
|
internal PrintArgsDelegate _printArgs = CommonFunctions.PrintArgs;
|
|
internal QueryCredentialsDelegate _queryCredentials = CommonFunctions.QueryCredentials;
|
|
internal ReadGitRemoteDetailsDelegate _readGitRemoteDetails = CommonFunctions.ReadGitRemoteDetails;
|
|
internal ReadKeyDelegate _readKey = ConsoleFunctions.ReadKey;
|
|
internal SetStandardWriterDelegate _setStandardErrorWriter = ConsoleFunctions.SetStandardErrorWriter;
|
|
internal SetStandardReaderDelegate _setStandardInputReader = ConsoleFunctions.SetStandardInputReader;
|
|
internal SetStandardWriterDelegate _setStandardOutputWriter = ConsoleFunctions.SetStandardOutputWriter;
|
|
internal StandardHandleIsTtyDelegate _standardHandleIsTty = ConsoleFunctions.StandardHandleIsTty;
|
|
internal TryReadBooleanDelegate _tryReadBoolean = CommonFunctions.TryReadBoolean;
|
|
internal TryReadStringDelegate _tryReadString = CommonFunctions.TryReadString;
|
|
internal WriteDelegate _write = ConsoleFunctions.Write;
|
|
internal WriteLineDelegate _writeLine = ConsoleFunctions.WriteLine;
|
|
|
|
internal readonly Dictionary<KeyType, string> _configurationKeys = new Dictionary<KeyType, string>()
|
|
{
|
|
{ KeyType.Authority, "authority" },
|
|
{ KeyType.DevOpsScope, "devopsScope" },
|
|
{ KeyType.HttpProxy, "httpProxy" },
|
|
{ KeyType.HttpsProxy, "httpsProxy" },
|
|
{ KeyType.Interactive, "interactive" },
|
|
{ KeyType.ModalPrompt, "modalPrompt" },
|
|
{ KeyType.Namespace, "namespace" },
|
|
{ KeyType.PreserveCredentials, "preserve" },
|
|
{ KeyType.TokenDuration, "tokenDuration" },
|
|
{ KeyType.HttpPath, "useHttpPath" },
|
|
{ KeyType.HttpTimeout, "httpTimeout" },
|
|
{ KeyType.Username, "username" },
|
|
{ KeyType.Validate, "validate" },
|
|
{ KeyType.VstsScope,"vstsScope" },
|
|
{ KeyType.Writelog, "writeLog" },
|
|
};
|
|
internal readonly Dictionary<KeyType, string> _environmentKeys = new Dictionary<KeyType, string>()
|
|
{
|
|
{ KeyType.Authority, "GCM_AUTHORITY" },
|
|
{ KeyType.ConfigNoLocal, "GCM_CONFIG_NOLOCAL" },
|
|
{ KeyType.ConfigNoSystem, "GCM_CONFIG_NOSYSTEM" },
|
|
{ KeyType.DevOpsScope, "GCM_DEVOPS_SCOPE" },
|
|
{ KeyType.HttpProxy, "HTTP_PROXY" },
|
|
{ KeyType.HttpsProxy, "HTTPS_PROXY" },
|
|
{ KeyType.HttpTimeout, "GCM_HTTP_TIMEOUT" },
|
|
{ KeyType.HttpUserAgent, "GCM_HTTP_USER_AGENT" },
|
|
{ KeyType.Interactive, "GCM_INTERACTIVE" },
|
|
{ KeyType.ModalPrompt, "GCM_MODAL_PROMPT" },
|
|
{ KeyType.Namespace, "GCM_NAMESPACE" },
|
|
{ KeyType.ParentHwnd, "GCM_MODAL_PARENTHWND" },
|
|
{ KeyType.PreserveCredentials, "GCM_PRESERVE" },
|
|
{ KeyType.TokenDuration, "GCM_TOKEN_DURATION" },
|
|
{ KeyType.UrlOverride, "GCM_URL_OVERRIDE" },
|
|
{ KeyType.Validate, "GCM_VALIDATE" },
|
|
{ KeyType.VstsScope, "GCM_VSTS_SCOPE" },
|
|
{ KeyType.Writelog, "GCM_WRITELOG" },
|
|
};
|
|
|
|
[System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Performance", "CA1810:InitializeReferenceTypeStaticFieldsInline")]
|
|
static Program()
|
|
{
|
|
ServicePointManager.SecurityProtocol = ServicePointManager.SecurityProtocol | SecurityProtocolType.Tls12;
|
|
}
|
|
|
|
private string _executablePath;
|
|
private readonly RuntimeContext _context;
|
|
private string _location;
|
|
private string _name;
|
|
private char[] _newlineChars;
|
|
private IntPtr _parentHwnd;
|
|
private Stream _stdErrStream;
|
|
private TextWriter _stdErrWriter;
|
|
private Stream _stdInStream;
|
|
private TextReader _stdInReader;
|
|
private Stream _stdOutStream;
|
|
private TextWriter _stdOutWriter;
|
|
private readonly object _syncpoint = new object();
|
|
private string _title;
|
|
private Version _version;
|
|
|
|
public IReadOnlyDictionary<KeyType, string> ConfigurationKeys
|
|
=> _configurationKeys;
|
|
|
|
public IReadOnlyDictionary<KeyType, string> EnvironmentKeys
|
|
=> _environmentKeys;
|
|
|
|
/// <summary>
|
|
/// Gets the path to the executable.
|
|
/// </summary>
|
|
public string ExecutablePath
|
|
{
|
|
get
|
|
{
|
|
lock (_syncpoint)
|
|
{
|
|
if (_executablePath is null)
|
|
{
|
|
LoadAssemblyInformation();
|
|
}
|
|
return _executablePath;
|
|
}
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Gets the directory where the executable is contained.
|
|
/// </summary>
|
|
public string Location
|
|
{
|
|
get
|
|
{
|
|
lock (_syncpoint)
|
|
{
|
|
if (_location is null)
|
|
{
|
|
LoadAssemblyInformation();
|
|
}
|
|
return _location;
|
|
}
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Gets the name of the application.
|
|
/// </summary>
|
|
public string Name
|
|
{
|
|
get
|
|
{
|
|
lock (_syncpoint)
|
|
{
|
|
if (_name is null)
|
|
{
|
|
LoadAssemblyInformation();
|
|
}
|
|
return _name;
|
|
}
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// <para>Gets <see langword="true"/> if stderr is a TTY device; otherwise <see langword="false"/>.</para>
|
|
/// <para>
|
|
/// If TTY, then it is very likely stderr is attached to a console and interactions with the
|
|
/// user are possible.
|
|
/// </para>
|
|
/// </summary>
|
|
public bool StandardErrorIsTty
|
|
{
|
|
get { return StandardHandleIsTty(NativeMethods.StandardHandleType.Error); }
|
|
}
|
|
|
|
/// <summary>
|
|
/// <para>Gets <see langword="true"/> if stdin is a TTY device; otherwise <see langword="false"/>.</para>
|
|
/// <para>
|
|
/// If TTY, then it is very likely stdin is attached to a console and interactions with the
|
|
/// user are possible.
|
|
/// </para>
|
|
/// </summary>
|
|
public bool StandardInputIsTty
|
|
{
|
|
get { return StandardHandleIsTty(NativeMethods.StandardHandleType.Input); }
|
|
}
|
|
|
|
/// <summary>
|
|
/// <para>Gets <see langword="true"/> if stdout is a TTY device; otherwise <see langword="false"/>.</para>
|
|
/// <para>
|
|
/// If TTY, then it is very likely stdout is attached to a console and interaction with the
|
|
/// user are possible.
|
|
/// </para>
|
|
/// </summary>
|
|
public bool StandardOutputIsTty
|
|
{
|
|
get { return StandardHandleIsTty(NativeMethods.StandardHandleType.Output); }
|
|
}
|
|
|
|
/// <summary>
|
|
/// Gets the titles of the application.
|
|
/// </summary>
|
|
public string Title
|
|
{
|
|
get { return _title; }
|
|
private set
|
|
{
|
|
if (value is null)
|
|
throw new ArgumentNullException(nameof(Title));
|
|
|
|
_title = value;
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Gets the version of the application.
|
|
/// </summary>
|
|
public Version Version
|
|
{
|
|
get
|
|
{
|
|
lock (_syncpoint)
|
|
{
|
|
if (_version is null)
|
|
{
|
|
LoadAssemblyInformation();
|
|
}
|
|
return _version;
|
|
}
|
|
}
|
|
}
|
|
|
|
internal RuntimeContext Context
|
|
=> _context;
|
|
|
|
internal TextWriter Error
|
|
{
|
|
get
|
|
{
|
|
lock (_syncpoint)
|
|
{
|
|
if (_stdErrWriter is null)
|
|
{
|
|
_stdErrWriter = _openStandardErrorWriter(this);
|
|
}
|
|
|
|
return _stdErrWriter;
|
|
}
|
|
}
|
|
}
|
|
|
|
internal Stream ErrorStream
|
|
{
|
|
get
|
|
{
|
|
lock (_syncpoint)
|
|
{
|
|
if (_stdErrStream is null)
|
|
{
|
|
_stdErrStream = _openStandardErrorStream(this);
|
|
}
|
|
|
|
return _stdErrStream;
|
|
}
|
|
}
|
|
}
|
|
|
|
internal TextReader In
|
|
{
|
|
get
|
|
{
|
|
lock (_syncpoint)
|
|
{
|
|
if (_stdInReader is null)
|
|
{
|
|
_stdInReader = _openStandardInputReader(this);
|
|
}
|
|
|
|
return _stdInReader;
|
|
}
|
|
}
|
|
}
|
|
|
|
internal Stream InStream
|
|
{
|
|
get
|
|
{
|
|
lock (_syncpoint)
|
|
{
|
|
if (_stdInStream is null)
|
|
{
|
|
_stdInStream = _openStandardInputStream(this);
|
|
}
|
|
|
|
return _stdInStream;
|
|
}
|
|
}
|
|
}
|
|
|
|
internal INetwork Network
|
|
=> _context.Network;
|
|
|
|
internal char[] NewLineChars
|
|
{
|
|
get
|
|
{
|
|
lock (_syncpoint)
|
|
{
|
|
if (_newlineChars is null)
|
|
{
|
|
_newlineChars = Settings.NewLine.ToCharArray();
|
|
}
|
|
|
|
return _newlineChars;
|
|
}
|
|
}
|
|
}
|
|
|
|
internal TextWriter Out
|
|
{
|
|
get
|
|
{
|
|
lock (_syncpoint)
|
|
{
|
|
if (_stdOutWriter is null)
|
|
{
|
|
_stdOutWriter = _openStandardOutputWriter(this);
|
|
}
|
|
|
|
return _stdOutWriter;
|
|
}
|
|
}
|
|
}
|
|
|
|
internal Stream OutStream
|
|
{
|
|
get
|
|
{
|
|
lock (_syncpoint)
|
|
{
|
|
if (_stdOutStream is null)
|
|
{
|
|
_stdOutStream = _openStandardOutputStream(this);
|
|
}
|
|
|
|
return _stdOutStream;
|
|
}
|
|
}
|
|
}
|
|
|
|
internal IntPtr ParentHwnd
|
|
{
|
|
get { lock (_syncpoint) return _parentHwnd; }
|
|
set { lock (_syncpoint) _parentHwnd = value; }
|
|
}
|
|
|
|
internal ISettings Settings
|
|
=> _context.Settings;
|
|
|
|
internal IStorage Storage
|
|
=> _context.Storage;
|
|
|
|
internal Git.ITrace Trace
|
|
=> _context.Trace;
|
|
|
|
internal Git.IUtilities Utilities
|
|
=> _context.Utilities;
|
|
|
|
internal Git.IWhere Where
|
|
=> _context.Where;
|
|
|
|
internal static void DebuggerLaunch(Program program)
|
|
{
|
|
if (program is null)
|
|
throw new ArgumentNullException(nameof(program));
|
|
|
|
if (Debugger.IsAttached)
|
|
return;
|
|
|
|
string debug = program.Settings.GetEnvironmentVariable(EnvironConfigDebugKey);
|
|
if (debug != null
|
|
&& (StringComparer.OrdinalIgnoreCase.Equals(debug, "true")
|
|
|| StringComparer.OrdinalIgnoreCase.Equals(debug, "1")
|
|
|| StringComparer.OrdinalIgnoreCase.Equals(debug, "debug")))
|
|
{
|
|
program.Trace.WriteLine($"'{EnvironConfigDebugKey}': '{debug}', launching debugger...");
|
|
|
|
Debugger.Launch();
|
|
}
|
|
}
|
|
|
|
internal void DetectTraceEnvironmentKey(string environmentKey)
|
|
{
|
|
if (environmentKey is null)
|
|
throw new ArgumentNullException(nameof(environmentKey));
|
|
|
|
try
|
|
{
|
|
string traceValue = Settings.GetEnvironmentVariable(environmentKey);
|
|
|
|
if (traceValue is null)
|
|
return;
|
|
|
|
// If the value is true or a number greater than zero, then trace to standard error.
|
|
if (Git.Configuration.PaserBoolean(traceValue))
|
|
{
|
|
Trace.AddListener(Error);
|
|
}
|
|
// If the value is a rooted path, then trace to that file and not to the console.
|
|
else if (Path.IsPathRooted(traceValue))
|
|
{
|
|
// Open or create the log file.
|
|
var stream = Storage.FileOpen(traceValue, FileMode.Append, FileAccess.Write, FileShare.ReadWrite);
|
|
|
|
// Create the writer and add it to the list.
|
|
var writer = new StreamWriter(stream, System.Text.Encoding.UTF8, 4096, true);
|
|
Trace.AddListener(writer);
|
|
}
|
|
}
|
|
catch { /* squelch */ }
|
|
}
|
|
|
|
internal void Die(Exception exception,
|
|
[CallerFilePath] string path = "",
|
|
[CallerLineNumber] int line = 0,
|
|
[CallerMemberName] string name = "")
|
|
=> _dieException(this, exception, path, line, name);
|
|
|
|
internal void Die(string message,
|
|
[CallerFilePath] string path = "",
|
|
[CallerLineNumber] int line = 0,
|
|
[CallerMemberName] string name = "")
|
|
=> _dieMessage(this, message, path, line, name);
|
|
|
|
internal void Exit(int exitcode = 0,
|
|
string message = null,
|
|
[CallerFilePath] string path = "",
|
|
[CallerLineNumber] int line = 0,
|
|
[CallerMemberName] string name = "")
|
|
=> _exit(this, exitcode, message, path, line, name);
|
|
|
|
internal Task LoadOperationArguments(OperationArguments operationArguments)
|
|
=> _loadOperationArguments(this, operationArguments);
|
|
|
|
internal void LogEvent(string message, EventLogEntryType eventType)
|
|
=> _logEvent(this, message, eventType);
|
|
|
|
internal Task<Credential> QueryCredentials(OperationArguments operationArguments)
|
|
=> _queryCredentials(this, operationArguments);
|
|
|
|
internal ConsoleKeyInfo ReadKey(bool intercept = true)
|
|
=> _readKey(this, intercept);
|
|
|
|
internal void Write(string message)
|
|
=> _write(this, message);
|
|
|
|
internal void WriteLine(string message = null)
|
|
=> _writeLine(this, message);
|
|
|
|
internal Credential BasicCredentialPrompt(TargetUri targetUri)
|
|
{
|
|
string message = "Please enter your credentials for ";
|
|
return BasicCredentialPrompt(targetUri, message);
|
|
}
|
|
|
|
internal Credential BasicCredentialPrompt(TargetUri targetUri, string titleMessage)
|
|
=> _basicCredentialPrompt(this, targetUri, titleMessage);
|
|
|
|
internal Task<BaseAuthentication> CreateAuthentication(OperationArguments operationArguments)
|
|
=> _createAuthentication(this, operationArguments);
|
|
|
|
internal Task<bool> DeleteCredentials(OperationArguments operationArguments)
|
|
=> _deleteCredentials(this, operationArguments);
|
|
|
|
internal void PrintArgs(string[] args)
|
|
=> _printArgs(this, args);
|
|
|
|
[Conditional("DEBUG")]
|
|
internal void EnableDebugTrace()
|
|
{
|
|
// Use the stderr stream for the trace as stdout is used in the cross-process
|
|
// communications protocol
|
|
_context.Trace.AddListener(Error);
|
|
}
|
|
|
|
internal void EnableTraceLogging(OperationArguments operationArguments)
|
|
=> _enableTraceLogging(this, operationArguments);
|
|
|
|
internal void EnableTraceLogging(OperationArguments operationArguments, string logFilePath)
|
|
=> _enableTraceLoggingFile(this, operationArguments, logFilePath);
|
|
|
|
internal bool BitbucketCredentialPrompt(string titleMessage, TargetUri targetUri, out string username, out string password)
|
|
=> _bitbucketCredentialPrompt(this, titleMessage, targetUri, out username, out password);
|
|
|
|
internal bool BitbucketOAuthPrompt(string title, TargetUri targetUri, Bitbucket.AuthenticationResultType resultType, string username)
|
|
=> _bitbucketOauthPrompt(this, title, targetUri, resultType, username);
|
|
|
|
internal string KeyTypeName(KeyType type)
|
|
{
|
|
string value = "UNKNOWN";
|
|
|
|
if (!_configurationKeys.TryGetValue(type, out value)
|
|
&& !_environmentKeys.TryGetValue(type, out value))
|
|
{
|
|
_context.Trace.WriteLine($"BUG: unknown {nameof(KeyType)}: '{type}' encountered.");
|
|
}
|
|
|
|
return value;
|
|
}
|
|
|
|
internal bool GitHubAuthCodePrompt(TargetUri targetUri, Github.GitHubAuthenticationResultType resultType, string username, out string authenticationCode)
|
|
=> _gitHubAuthCodePrompt(this, targetUri, resultType, username, out authenticationCode);
|
|
|
|
internal bool GitHubCredentialPrompt(TargetUri targetUri, out string username, out string password)
|
|
=> _gitHubCredentialPrompt(this, targetUri, out username, out password);
|
|
|
|
private void LoadAssemblyInformation()
|
|
{
|
|
Debug.Assert(Monitor.IsEntered(_syncpoint), "Expected lock not held.");
|
|
|
|
var assembly = System.Reflection.Assembly.GetEntryAssembly();
|
|
var asseName = assembly.GetName();
|
|
|
|
_executablePath = assembly.Location;
|
|
_location = Path.GetDirectoryName(_executablePath);
|
|
_name = asseName.Name;
|
|
_version = asseName.Version;
|
|
}
|
|
|
|
internal bool ModalPromptDisplayDialog(
|
|
ref NativeMethods.CredentialUiInfo credUiInfo,
|
|
ref NativeMethods.CredentialPackFlags authPackage,
|
|
IntPtr packedAuthBufferPtr,
|
|
uint packedAuthBufferSize,
|
|
IntPtr inBufferPtr,
|
|
int inBufferSize,
|
|
bool saveCredentials,
|
|
NativeMethods.CredentialUiWindowsFlags flags,
|
|
out string username,
|
|
out string password)
|
|
=> _modalPromptDisplayDialog(this,
|
|
ref credUiInfo,
|
|
ref authPackage,
|
|
packedAuthBufferPtr,
|
|
packedAuthBufferSize,
|
|
inBufferPtr,
|
|
inBufferSize,
|
|
saveCredentials,
|
|
flags,
|
|
out username,
|
|
out password);
|
|
|
|
internal Credential ModalPromptForCredentials(TargetUri targetUri, string message)
|
|
=> _modalPromptForCredentials(this, targetUri, message);
|
|
|
|
internal Credential ModalPromptForCredentials(TargetUri targetUri)
|
|
{
|
|
string message = string.Format("Enter your credentials for {0}.", targetUri.ToString(username: false, port: true, path: true));
|
|
|
|
if (!string.IsNullOrEmpty(targetUri.QueryUri.UserInfo))
|
|
{
|
|
string username = targetUri.QueryUri.UserInfo;
|
|
|
|
if (!targetUri.QueryUri.UserEscaped)
|
|
{
|
|
username = Uri.UnescapeDataString(username);
|
|
}
|
|
|
|
return ModalPromptForPassword(targetUri, message, username);
|
|
}
|
|
|
|
return ModalPromptForCredentials(targetUri, message);
|
|
}
|
|
|
|
private Credential ModalPromptForPassword(TargetUri targetUri, string message, string username)
|
|
=> _modalPromptForPassword(this, targetUri, message, username);
|
|
|
|
internal void PrintVersion()
|
|
{
|
|
#if DEBUG
|
|
WriteLine($"{Title} version {Version.ToString(4)}");
|
|
#else
|
|
WriteLine($"{Title} version {Version.ToString(3)}");
|
|
#endif
|
|
}
|
|
|
|
internal void ReadGitRemoteDetails(OperationArguments operationArguments)
|
|
=> _readGitRemoteDetails(this, operationArguments);
|
|
|
|
internal void SetError(TextWriter writer)
|
|
{
|
|
_setStandardErrorWriter(this, writer);
|
|
}
|
|
|
|
internal void SetIn(TextReader reader)
|
|
{
|
|
_setStandardInputReader(this, reader);
|
|
}
|
|
|
|
internal void SetOut(TextWriter writer)
|
|
{
|
|
_setStandardOutputWriter(this, writer);
|
|
}
|
|
|
|
internal bool StandardHandleIsTty(NativeMethods.StandardHandleType handleType)
|
|
=> _standardHandleIsTty(this, handleType);
|
|
|
|
internal bool TryReadBoolean(OperationArguments operationArguments, KeyType key, out bool? value)
|
|
=> _tryReadBoolean(this, operationArguments, key, out value);
|
|
|
|
internal bool TryReadString(OperationArguments operationArguments, KeyType key, out string value)
|
|
=> _tryReadString(this, operationArguments, key, out value);
|
|
}
|
|
}
|