Esempio n. 1
0
        internal async Task <AuthenticationModes> GetSupportedAuthenticationModesAsync(Uri targetUri)
        {
            // Check for an explicit override for supported authentication modes
            if (Context.Settings.TryGetSetting(
                    GitHubConstants.EnvironmentVariables.AuthenticationModes,
                    Constants.GitConfiguration.Credential.SectionName, GitHubConstants.GitConfiguration.Credential.AuthenticationModes,
                    out string authModesStr))
            {
                if (Enum.TryParse(authModesStr, true, out AuthenticationModes authModes) && authModes != AuthenticationModes.None)
                {
                    Context.Trace.WriteLine($"Supported authentication modes override present: {authModes}");
                    return(authModes);
                }
                else
                {
                    Context.Trace.WriteLine($"Invalid value for supported authentication modes override setting: '{authModesStr}'");
                }
            }

            // GitHub.com should use OAuth or manual PAT based authentication only, never basic auth as of 13th November 2020
            // https://developer.github.com/changes/2020-02-14-deprecating-oauth-auth-endpoint
            if (IsGitHubDotCom(targetUri))
            {
                Context.Trace.WriteLine($"{targetUri} is github.com - authentication schemes: '{GitHubConstants.DotComAuthenticationModes}'");
                return(GitHubConstants.DotComAuthenticationModes);
            }

            // For GitHub Enterprise we must do some detection of supported modes
            Context.Trace.WriteLine($"{targetUri} is GitHub Enterprise - checking for supported authentication schemes...");

            try
            {
                GitHubMetaInfo metaInfo = await _gitHubApi.GetMetaInfoAsync(targetUri);

                var modes = AuthenticationModes.None;
                if (metaInfo.VerifiablePasswordAuthentication)
                {
                    modes |= AuthenticationModes.Basic;
                }
                if (Version.TryParse(metaInfo.InstalledVersion, out var version) && version >= GitHubConstants.MinimumEnterpriseOAuthVersion)
                {
                    modes |= AuthenticationModes.OAuth;
                }

                Context.Trace.WriteLine($"GitHub Enterprise instance has version '{metaInfo.InstalledVersion}' and supports authentication schemes: {modes}");
                return(modes);
            }
            catch (Exception ex)
            {
                Context.Trace.WriteLine($"Failed to query '{targetUri}' for supported authentication schemes.");
                Context.Trace.WriteException(ex);

                Context.Terminal.WriteLine($"warning: failed to query '{targetUri}' for supported authentication schemes.");

                // Fall-back to offering all modes so the user is never blocked from authenticating by at least one mode
                return(AuthenticationModes.All);
            }
        }
        internal async Task <AuthenticationModes> GetSupportedAuthenticationModesAsync(Uri targetUri)
        {
            // Check for an explicit override for supported authentication modes
            if (Context.Settings.TryGetSetting(
                    GitHubConstants.EnvironmentVariables.AuthenticationModes,
                    Constants.GitConfiguration.Credential.SectionName, GitHubConstants.GitConfiguration.Credential.AuthenticationModes,
                    out string authModesStr))
            {
                if (Enum.TryParse(authModesStr, true, out AuthenticationModes authModes) && authModes != AuthenticationModes.None)
                {
                    Context.Trace.WriteLine($"Supported authentication modes override present: {authModes}");
                    return(authModes);
                }
                else
                {
                    Context.Trace.WriteLine($"Invalid value for supported authentication modes override setting: '{authModesStr}'");
                }
            }

            // GitHub.com should use OAuth authentication only
            if (IsGitHubDotCom(targetUri))
            {
                Context.Trace.WriteLine($"{targetUri} is github.com - authentication schemes: '{GitHubConstants.DotDomAuthenticationModes}'");
                return(GitHubConstants.DotDomAuthenticationModes);
            }

            // For GitHub Enterprise we must do some detection of supported modes
            Context.Trace.WriteLine($"{targetUri} is GitHub Enterprise - checking for supporting authentication schemes...");

            try
            {
                GitHubMetaInfo metaInfo = await _gitHubApi.GetMetaInfoAsync(targetUri);

                var modes = AuthenticationModes.None;
                if (metaInfo.VerifiablePasswordAuthentication)
                {
                    modes |= AuthenticationModes.Basic;
                }
                if (Version.TryParse(metaInfo.InstalledVersion, out var version) && version >= GitHubConstants.MinimumEnterpriseOAuthVersion)
                {
                    modes |= AuthenticationModes.OAuth;
                }

                Context.Trace.WriteLine($"GitHub Enterprise instance has version '{metaInfo.InstalledVersion}' and supports authentication schemes: {modes}");
                return(modes);
            }
            catch (Exception ex)
            {
                Context.Trace.WriteLine($"Failed to query '{targetUri}' for supported authentication schemes.");
                Context.Trace.WriteException(ex);

                Context.Terminal.WriteLine($"warning: failed to query '{targetUri}' for supported authentication schemes.");
                return(AuthenticationModes.Basic | AuthenticationModes.OAuth);
            }
        }