internal void Clear() { var args = Settings.GetCommandLineArgs(); string url = null; bool forced = false; if (args.Length <= 2) { if (!StandardInputIsTty) { _context.Trace.WriteLine("standard input is not TTY, abandoning prompt."); return; } _context.Trace.WriteLine("prompting user for url."); WriteLine(" Target Url:"); url = In.ReadLine(); } else { url = args[2]; if (args.Length > 3) { bool.TryParse(args[3], out forced); } } Uri uri; if (Uri.TryCreate(url, UriKind.Absolute, out uri)) { _context.Trace.WriteLine($"converted '{url}' to '{uri.AbsoluteUri}'."); var operationArguments = new OperationArguments(_context); operationArguments.SetTargetUri(uri); if (operationArguments.TargetUri is null) { var inner = new ArgumentNullException(nameof(operationArguments.TargetUri)); throw new ArgumentException(inner.Message, nameof(operationArguments), inner); } Task.Run(async() => { await LoadOperationArguments(operationArguments); EnableTraceLogging(operationArguments); if (operationArguments.PreserveCredentials && !forced) { _context.Trace.WriteLine("attempting to delete preserved credentials without force, prompting user for interactivity."); if (!StandardInputIsTty || !StandardErrorIsTty) { _context.Trace.WriteLine("standard input is not TTY, abandoning prompt."); return; } WriteLine(" credentials are protected by preserve flag, clear anyways? [Y]es, [N]o."); ConsoleKeyInfo key; while ((key = ReadKey(true)).Key != ConsoleKey.Escape) { if (key.KeyChar == 'N' || key.KeyChar == 'n') { return; } if (key.KeyChar == 'Y' || key.KeyChar == 'y') { break; } } } await DeleteCredentials(operationArguments); }).Wait(); } else { _context.Trace.WriteLine($"unable to parse input '{url}'."); } }
internal void Delete() { string[] args = Settings.GetCommandLineArgs(); if (args.Length < 3) { goto error_parse; } string url = args[2]; Uri uri = null; if (Uri.IsWellFormedUriString(url, UriKind.Absolute)) { if (!Uri.TryCreate(url, UriKind.Absolute, out uri)) { goto error_parse; } } else { url = string.Format("{0}://{1}", Uri.UriSchemeHttps, url); if (!Uri.TryCreate(url, UriKind.Absolute, out uri)) { goto error_parse; } } var operationArguments = new OperationArguments(_context); operationArguments.SetTargetUri(uri); if (operationArguments.TargetUri is null) { var inner = new ArgumentNullException(nameof(operationArguments.TargetUri)); throw new ArgumentException(inner.Message, nameof(operationArguments), inner); } Task.Run(async() => { // Load operation arguments. await LoadOperationArguments(operationArguments); EnableTraceLogging(operationArguments); // Set the parent window handle. ParentHwnd = operationArguments.ParentHwnd; BaseAuthentication authentication = await CreateAuthentication(operationArguments); switch (operationArguments.Authority) { default: case AuthorityType.Basic: _context.Trace.WriteLine($"deleting basic credentials for '{operationArguments.TargetUri}'."); break; case AuthorityType.AzureDirectory: case AuthorityType.MicrosoftAccount: _context.Trace.WriteLine($"deleting VSTS credentials for '{operationArguments.TargetUri}'."); break; case AuthorityType.GitHub: _context.Trace.WriteLine($"deleting GitHub credentials for '{operationArguments.TargetUri}'."); break; case AuthorityType.Ntlm: _context.Trace.WriteLine($"deleting NTLM credentials for '{operationArguments.TargetUri}'."); break; case AuthorityType.Bitbucket: _context.Trace.WriteLine($"deleting Bitbucket credentials for '{operationArguments.Username}@{operationArguments.TargetUri}'."); break; } await authentication.DeleteCredentials(operationArguments.TargetUri, operationArguments.Username); }).Wait(); return; error_parse: Die("Unable to parse target URI."); }
internal void Config() { string[] args = Settings.GetCommandLineArgs(); // Attempt to parse a target URI from the command line arguments. if (args.Length < 3 || !Uri.TryCreate(args[2], UriKind.Absolute, out Uri targetUri)) { targetUri = new Uri("file://localhost"); } // Create operation arguments, and load configuration data. var operationArguments = new OperationArguments(_context); operationArguments.SetTargetUri(targetUri); if (operationArguments.TargetUri is null) { var inner = new ArgumentNullException(nameof(operationArguments.TargetUri)); throw new ArgumentException(inner.Message, nameof(operationArguments), inner); } Task.Run(async() => { await LoadOperationArguments(operationArguments); EnableTraceLogging(operationArguments); // Create a set of irrelevant environment variable entries. var irrelevantEntries = new HashSet <string>(StringComparer.OrdinalIgnoreCase) { "ToastSettings" }; // Write out the environment variables. WriteLine("Environment Variables:"); foreach (var entry in operationArguments.EnvironmentVariables) { // Skip well-known, irrelevant entries. if (irrelevantEntries.Contains(entry.Key)) { continue; } WriteLine($" {entry.Key} = {entry.Value}"); } WriteLine(); // Write out the Git configuration. WriteLine("Git Configuration:"); foreach (var entry in operationArguments.GitConfiguration) { WriteLine($" [{entry.Level}] {entry.Key} = {entry.Value}"); } WriteLine(); // Write out the effective settings for GCM. WriteLine($"Effective Manager Configuration for {operationArguments.QueryUri.ToString()}:"); WriteLine($" Executable = {AssemblyTitle} v{Version.ToString(4)} ({ExecutablePath})"); WriteLine($" Authority = {operationArguments.Authority}"); WriteLine($" CustomNamespace = {operationArguments.CustomNamespace}"); WriteLine($" Interactivity = {operationArguments.Interactivity}"); WriteLine($" PreserveCredentials = {operationArguments.PreserveCredentials}"); WriteLine($" QueryUri = {operationArguments.QueryUri}"); WriteLine($" TargetUri = {operationArguments.TargetUri}"); WriteLine($" TokenDuration = {operationArguments.TokenDuration}"); WriteLine($" UseConfigLocal = {operationArguments.UseConfigLocal}"); WriteLine($" UseConfigSystem = {operationArguments.UseConfigSystem}"); WriteLine($" UseHttpPath = {operationArguments.UseHttpPath}"); WriteLine($" UseModalUi = {operationArguments.UseModalUi}"); WriteLine($" ValidateCredentials = {operationArguments.ValidateCredentials}"); WriteLine($" VstsTokenScope = {operationArguments.VstsTokenScope}"); WriteLine($" WriteLog = {operationArguments.WriteLog}"); }).Wait(); }
internal void Askpass(string[] args) { if (args == null || args.Length == 0) { throw new ArgumentException("Arguments cannot be empty."); } Gui.UserPromptKind promptKind = Gui.UserPromptKind.SshPassphrase; Match match; if ((match = AskPasswordRegex.Match(args[0])).Success) { promptKind = Gui.UserPromptKind.CredentialsPassword; } else if ((match = AskPassphraseRegex.Match(args[0])).Success) { promptKind = Gui.UserPromptKind.SshPassphrase; } if (match.Success) { _context.Trace.WriteLine("querying for passphrase key."); if (match.Groups.Count < 2) { throw new ArgumentException("Unable to understand command."); } // string request = match.Groups[0].Value; string resource = match.Groups[1].Value; _context.Trace.WriteLine($"open dialog for '{resource}'."); // Load operation arguments. OperationArguments operationArguments = new OperationArguments(_context); Task.Run(async() => await operationArguments.LoadConfiguration()).Wait(); // Set the parent window handle. ParentHwnd = operationArguments.ParentHwnd; System.Windows.Application application = new System.Windows.Application(); Gui.UserPromptDialog prompt = new Gui.UserPromptDialog(promptKind, resource, operationArguments.ParentHwnd); application.Run(prompt); if (!prompt.Failed && !string.IsNullOrEmpty(prompt.Response)) { string passphase = prompt.Response; _context.Trace.WriteLine("passphase acquired."); Out.Write(passphase + "\n"); return; } Die("failed to interactively acquire credentials."); } if ((match = AskCredentialRegex.Match(args[0])).Success) { _context.Trace.WriteLine("querying for basic credentials."); if (match.Groups.Count < 3) { throw new ArgumentException("Unable to understand command."); } string seeking = match.Groups[1].Value; string targetUrl = match.Groups[2].Value; string username = string.Empty; string password = string.Empty; Uri targetUri = null; // Since we're looking for HTTP(s) credentials, we can use NetFx `Uri` class. if (Uri.TryCreate(targetUrl, UriKind.Absolute, out targetUri)) { _context.Trace.WriteLine($"success parsing URL, targetUri = '{targetUri}'."); if (TryParseUrlCredentials(targetUrl, out username, out password)) { if (password != null && seeking.Equals("Password", StringComparison.OrdinalIgnoreCase)) { Out.Write(password + '\n'); return; } // print the username if it sought if (seeking.Equals("Username", StringComparison.OrdinalIgnoreCase)) { Out.Write(username + '\n'); return; } } // create a target Url with the credential portion stripped, because Git doesn't // report hosts with credentials targetUrl = targetUri.Scheme + "://"; // Add the username@ portion of the url if it exists if (username != null) { targetUrl += Uri.EscapeDataString(username); targetUrl += '@'; } targetUrl += targetUri.Host; // Retain the port if specified. if (!targetUri.IsDefaultPort) { targetUrl += $":{targetUri.Port}"; } // Retain the path if specified. if (!string.IsNullOrWhiteSpace(targetUri.LocalPath)) { targetUrl += targetUri.LocalPath; } if (Uri.TryCreate(targetUrl, UriKind.Absolute, out targetUri)) { _context.Trace.WriteLine($"success parsing URL, targetUri = '{targetUri}'."); var operationArguments = new OperationArguments(_context); operationArguments.SetTargetUri(targetUri); operationArguments.SetCredentials(username ?? string.Empty, password ?? string.Empty); // Load up the operation arguments, enable tracing, and query for credentials. Task.Run(async() => { await LoadOperationArguments(operationArguments); EnableTraceLogging(operationArguments); Credential credentials; if ((credentials = await QueryCredentials(operationArguments)) != null) { if (seeking.Equals("Username", StringComparison.OrdinalIgnoreCase)) { _context.Trace.WriteLine($"username for '{targetUrl}' asked for and found."); Out.Write(credentials.Username + '\n'); return; } if (seeking.Equals("Password", StringComparison.OrdinalIgnoreCase)) { _context.Trace.WriteLine($"password for '{targetUrl}' asked for and found."); Out.Write(credentials.Password + '\n'); return; } } else { _context.Trace.WriteLine($"user cancelled credential dialog."); return; } }).Wait(); } else { _context.Trace.WriteLine("error: unable to parse target URL."); } } else { _context.Trace.WriteLine("error: unable to parse supplied URL."); } Die($"failed to detect {seeking} in target URL."); } if ((match = AskAuthenticityRegex.Match(args[0])).Success) { string host = match.Groups[1].Value; string fingerprint = match.Groups[2].Value; _context.Trace.WriteLine($"requesting authorization to add {host} ({fingerprint}) to known hosts."); // Load operation arguments. OperationArguments operationArguments = new OperationArguments(_context); Task.Run(async() => await operationArguments.LoadConfiguration()).Wait(); // Set the parent window handle. ParentHwnd = operationArguments.ParentHwnd; System.Windows.Application application = new System.Windows.Application(); Gui.UserPromptDialog prompt = new Gui.UserPromptDialog(host, fingerprint, operationArguments.ParentHwnd); application.Run(prompt); if (prompt.Failed) { _context.Trace.WriteLine("denied authorization of host."); Out.Write("no\n"); } else { _context.Trace.WriteLine("approved authorization of host."); Out.Write("yes\n"); } return; } Die("failed to acquire credentials."); }