Beispiel #1
0
        public async Task AzureDevOpsRestApi_CreatePersonalAccessTokenAsync_IdentSvcReturnsHttp500_ThrowsException()
        {
            var context = new TestCommandContext();
            var orgUri  = new Uri("https://dev.azure.com/org/");

            JsonWebToken         accessToken = CreateJwt();
            IEnumerable <string> scopes      = new[] { AzureDevOpsConstants.PersonalAccessTokenScopes.ReposWrite };

            var identityServiceUri = new Uri("https://identity.example.com/");

            var locSvcRequestUri = new Uri(orgUri, ExpectedLocationServicePath);
            var locSvcResponse   = CreateLocationServiceResponse(identityServiceUri);

            var identSvcRequestUri = new Uri(identityServiceUri, ExpectedIdentityServicePath);

            var httpHandler = new TestHttpMessageHandler {
                ThrowOnUnexpectedRequest = true
            };

            httpHandler.Setup(HttpMethod.Get, locSvcRequestUri, x =>
            {
                AssertAcceptJson(x);
                AssertBearerToken(x, accessToken);
                return(locSvcResponse);
            });
            httpHandler.Setup(HttpMethod.Post, identSvcRequestUri, HttpStatusCode.InternalServerError);

            context.HttpClientFactory.MessageHandler = httpHandler;
            var api = new AzureDevOpsRestApi(context);

            await Assert.ThrowsAsync <Exception>(() => api.CreatePersonalAccessTokenAsync(orgUri, accessToken, scopes));
        }
        public async Task GitHubRestApi_AcquireTokenAsync_Valid1FANoSmsAuthCode_ReturnsSms2FARequired()
        {
            const string testUserName = "******";
            const string testPassword = "******";

            string[] testScopes = { "scope1", "scope2" };

            var context = new TestCommandContext();
            var uri     = new Uri("https://github.com");

            var expectedRequestUri = new Uri("https://api.github.com/authorizations");

            var httpResponse = new HttpResponseMessage(HttpStatusCode.Unauthorized);

            httpResponse.Headers.Add(GitHubConstants.GitHubOptHeader, "sms");

            var httpHandler = new TestHttpMessageHandler {
                ThrowOnUnexpectedRequest = true
            };

            httpHandler.Setup(HttpMethod.Post, expectedRequestUri, request =>
            {
                AssertBasicAuth(request, testUserName, testPassword);
                AssertAuthCode(request, null);
                return(httpResponse);
            });

            context.HttpClientFactory.MessageHandler = httpHandler;
            var api = new GitHubRestApi(context);

            AuthenticationResult authResult = await api.AcquireTokenAsync(
                uri, testUserName, testPassword, null, testScopes);

            Assert.Equal(GitHubAuthenticationResultType.TwoFactorSms, authResult.Type);
        }
        private static async Task TestGetIsSupportedAsync(string[] wwwAuthHeaders, bool expected)
        {
            var context = new TestCommandContext();
            var uri     = new Uri("https://example.com");

            var wiaResponse = new HttpResponseMessage(HttpStatusCode.Unauthorized);

            foreach (string headerValue in wwwAuthHeaders)
            {
                wiaResponse.Headers.WwwAuthenticate.ParseAdd(headerValue);
            }

            var httpHandler = new TestHttpMessageHandler {
                ThrowOnUnexpectedRequest = true
            };

            httpHandler.Setup(HttpMethod.Head, uri, wiaResponse);

            context.HttpClientFactory.MessageHandler = httpHandler;
            var wiaAuth = new WindowsIntegratedAuthentication(context);

            bool actual = await wiaAuth.GetIsSupportedAsync(uri);

            Assert.Equal(expected, actual);
            httpHandler.AssertRequest(HttpMethod.Head, uri, expectedNumberOfCalls: 1);
        }
Beispiel #4
0
        public async Task HostProviderRegistry_GetProvider_Auto_NetworkProbe_TimeoutNegative_NoNetworkCall()
        {
            var context   = new TestCommandContext();
            var registry  = new HostProviderRegistry(context);
            var remoteUri = new Uri("https://onprem.example.com");
            var input     = new InputArguments(
                new Dictionary <string, string>
            {
                ["protocol"] = remoteUri.Scheme,
                ["host"]     = remoteUri.Host
            }
                );

            var providerMock = new Mock <IHostProvider>();

            providerMock.Setup(x => x.IsSupported(It.IsAny <InputArguments>())).Returns(false);
            providerMock.Setup(x => x.IsSupported(It.IsAny <HttpResponseMessage>())).Returns(true);

            var responseMessage = new HttpResponseMessage(HttpStatusCode.Unauthorized);
            var httpHandler     = new TestHttpMessageHandler();

            httpHandler.Setup(HttpMethod.Head, remoteUri, responseMessage);
            context.HttpClientFactory.MessageHandler = httpHandler;

            registry.Register(providerMock.Object, HostProviderPriority.Normal);

            context.Settings.AutoDetectProviderTimeout = -1;

            await Assert.ThrowsAnyAsync <Exception>(() => registry.GetProviderAsync(input));

            httpHandler.AssertRequest(HttpMethod.Head, remoteUri, 0);
        }
Beispiel #5
0
        public async Task HostProviderRegistry_GetProvider_Auto_NetworkProbe_ReturnsSupportedProvider()
        {
            var            context   = new TestCommandContext();
            var            registry  = new HostProviderRegistry(context);
            var            remoteUri = new Uri("https://provider2.onprem.example.com");
            InputArguments input     = CreateInputArguments(remoteUri);

            var provider1Mock = new Mock <IHostProvider>();

            provider1Mock.Setup(x => x.IsSupported(It.IsAny <InputArguments>())).Returns(false);
            provider1Mock.Setup(x => x.IsSupported(It.IsAny <HttpResponseMessage>())).Returns(false);

            var provider2Mock = new Mock <IHostProvider>();

            provider2Mock.Setup(x => x.IsSupported(It.IsAny <InputArguments>())).Returns(false);
            provider2Mock.Setup(x => x.IsSupported(It.IsAny <HttpResponseMessage>())).Returns(true);

            var responseMessage = new HttpResponseMessage(HttpStatusCode.Unauthorized)
            {
                Headers = { { "X-Provider2", "true" } }
            };

            var httpHandler = new TestHttpMessageHandler();

            httpHandler.Setup(HttpMethod.Head, remoteUri, responseMessage);
            context.HttpClientFactory.MessageHandler = httpHandler;

            registry.Register(provider1Mock.Object, HostProviderPriority.Normal);
            registry.Register(provider2Mock.Object, HostProviderPriority.Normal);

            IHostProvider result = await registry.GetProviderAsync(input);

            httpHandler.AssertRequest(HttpMethod.Head, remoteUri, 1);
            Assert.Same(provider2Mock.Object, result);
        }
Beispiel #6
0
        public async Task AzureDevOpsRestApi_GetAuthorityAsync_VssResourceTenantMsa_ReturnsCommonAuthority()
        {
            var context     = new TestCommandContext();
            var uri         = new Uri("https://example.com");
            var msaTenantId = Guid.Empty;

            const string expectedAuthority = CommonAuthority;

            var httpResponse = new HttpResponseMessage(HttpStatusCode.Unauthorized)
            {
                Headers = { { AzureDevOpsConstants.VssResourceTenantHeader, msaTenantId.ToString("D") } }
            };

            var httpHandler = new TestHttpMessageHandler {
                ThrowOnUnexpectedRequest = true
            };

            httpHandler.Setup(HttpMethod.Head, uri, httpResponse);

            context.HttpClientFactory.MessageHandler = httpHandler;
            var api = new AzureDevOpsRestApi(context);

            string actualAuthority = await api.GetAuthorityAsync(uri);

            Assert.Equal(expectedAuthority, actualAuthority);
        }
        public async Task HttpClientExtensions_SendAsync_Headers_SetsHeaders()
        {
            var method = HttpMethod.Get;
            var uri    = new Uri("http://example.com");

            var customHeaders = new Dictionary <string, IEnumerable <string> >
            {
                ["header0"] = new string[0],
                ["header1"] = new [] { "first-value" },
                ["header2"] = new [] { "first-value", "second-value" },
                ["header3"] = new [] { "first-value", "second-value", "third-value" },
            };

            var httpHandler = new TestHttpMessageHandler {
                ThrowOnUnexpectedRequest = true
            };

            httpHandler.Setup(method, uri, request =>
            {
                Assert.False(request.Headers.Contains("header0"));
                Assert.True(request.Headers.Contains("header1"));
                Assert.True(request.Headers.Contains("header2"));
                Assert.True(request.Headers.Contains("header3"));
                Assert.Equal(customHeaders["header1"], request.Headers.GetValues("header1"));
                Assert.Equal(customHeaders["header2"], request.Headers.GetValues("header2"));
                Assert.Equal(customHeaders["header3"], request.Headers.GetValues("header3"));

                return(new HttpResponseMessage());
            });

            var httpClient = new HttpClient(httpHandler);

            await HttpClientExtensions.SendAsync(httpClient, method, uri, customHeaders);
        }
Beispiel #8
0
        public async Task AzureDevOpsRestApi_GetAuthorityAsync_BothWwwAuthAndVssResourceHeaders_ReturnsWwwAuthAuthority()
        {
            var context            = new TestCommandContext();
            var uri                = new Uri("https://example.com");
            var aadTenantIdWwwAuth = Guid.NewGuid();
            var aadTenantIdVssRes  = Guid.NewGuid();

            string expectedAuthority = $"https://login.microsoftonline.com/{aadTenantIdWwwAuth:D}";

            var httpResponse = new HttpResponseMessage(HttpStatusCode.Unauthorized);

            httpResponse.Headers.Add(AzureDevOpsConstants.VssResourceTenantHeader, aadTenantIdVssRes.ToString("D"));
            httpResponse.Headers.WwwAuthenticate.ParseAdd($"Bearer authorization_uri={expectedAuthority}");

            var httpHandler = new TestHttpMessageHandler {
                ThrowOnUnexpectedRequest = true
            };

            httpHandler.Setup(HttpMethod.Head, uri, httpResponse);

            context.HttpClientFactory.MessageHandler = httpHandler;
            var api = new AzureDevOpsRestApi(context);

            string actualAuthority = await api.GetAuthorityAsync(uri);

            Assert.Equal(expectedAuthority, actualAuthority);
        }
        public async Task GitHubRestApi_AcquireTokenAsync_Valid1FANoAppAuthCode_ReturnsApp2FARequired()
        {
            const string testUserName = "******";
            const string testPassword = "******"; // [SuppressMessage("Microsoft.Security", "CS001:SecretInline", Justification="Fake credential")]

            string[] testScopes = { "scope1", "scope2" };

            var context = new TestCommandContext();
            var uri     = new Uri("https://github.com");

            var expectedRequestUri = new Uri("https://api.github.com/authorizations");

            var httpResponse = new HttpResponseMessage(HttpStatusCode.Unauthorized);

            httpResponse.Headers.Add(GitHubConstants.GitHubOptHeader, "app");

            var httpHandler = new TestHttpMessageHandler {
                ThrowOnUnexpectedRequest = true
            };

            httpHandler.Setup(HttpMethod.Post, expectedRequestUri, request =>
            {
                RestTestUtilities.AssertBasicAuth(request, testUserName, testPassword);
                AssertAuthCode(request, null);
                return(httpResponse);
            });

            context.HttpClientFactory.MessageHandler = httpHandler;
            var api = new GitHubRestApi(context);

            AuthenticationResult authResult = await api.CreatePersonalAccessTokenAsync(
                uri, testUserName, testPassword, null, testScopes);

            Assert.Equal(GitHubAuthenticationResultType.TwoFactorApp, authResult.Type);
        }
Beispiel #10
0
        public async Task AzureDevOpsRestApi_GetAuthorityAsync_VssResourceTenantMsa_ReturnsOrganizationsAuthority()
        {
            var context     = new TestCommandContext();
            var uri         = new Uri("https://example.com");
            var msaTenantId = Guid.Empty;

            // This is only the case because we're using MSA pass-through.. in the future, if and when we
            // move away from MSA pass-through, this should be the common authority.
            const string expectedAuthority = OrganizationsAuthority;

            var httpResponse = new HttpResponseMessage(HttpStatusCode.Unauthorized)
            {
                Headers = { { AzureDevOpsConstants.VssResourceTenantHeader, msaTenantId.ToString("D") } }
            };

            var httpHandler = new TestHttpMessageHandler {
                ThrowOnUnexpectedRequest = true
            };

            httpHandler.Setup(HttpMethod.Head, uri, httpResponse);

            context.HttpClientFactory.MessageHandler = httpHandler;
            var api = new AzureDevOpsRestApi(context);

            string actualAuthority = await api.GetAuthorityAsync(uri);

            Assert.Equal(expectedAuthority, actualAuthority);
        }
Beispiel #11
0
        public async Task AzureDevOpsRestApi_GetAuthorityAsync_WwwAuthenticateMultiple_ReturnsBearerAuthority()
        {
            var context = new TestCommandContext();
            var uri     = new Uri("https://example.com");

            const string expectedAuthority = "https://login.microsoftonline.com/test-authority";

            var httpResponse = new HttpResponseMessage(HttpStatusCode.Unauthorized);

            httpResponse.Headers.WwwAuthenticate.ParseAdd("Bearer");
            httpResponse.Headers.WwwAuthenticate.ParseAdd($"Bearer authorization_uri={expectedAuthority}");
            httpResponse.Headers.WwwAuthenticate.ParseAdd("NTLM [test-challenge-string]");

            var httpHandler = new TestHttpMessageHandler {
                ThrowOnUnexpectedRequest = true
            };

            httpHandler.Setup(HttpMethod.Head, uri, httpResponse);

            context.HttpClientFactory.MessageHandler = httpHandler;
            var api = new AzureDevOpsRestApi(context);

            string actualAuthority = await api.GetAuthorityAsync(uri);

            Assert.Equal(expectedAuthority, actualAuthority);
        }
Beispiel #12
0
        public async Task AzureDevOpsRestApi_CreatePersonalAccessTokenAsync_ReturnsPAT()
        {
            var context = new TestCommandContext();
            var orgUri  = new Uri("https://dev.azure.com/org/");

            const string         expectedPat = "PERSONAL-ACCESS-TOKEN";
            JsonWebToken         accessToken = CreateJwt();
            IEnumerable <string> scopes      = new[] { AzureDevOpsConstants.PersonalAccessTokenScopes.ReposWrite };

            var identityServiceUri = new Uri("https://identity.example.com/");

            var locSvcRequestUri = new Uri(orgUri, ExpectedLocationServicePath);
            var locSvcResponse   = CreateLocationServiceResponse(identityServiceUri);

            var identSvcRequestUri = new Uri(identityServiceUri, ExpectedIdentityServicePath);
            var identSvcResponse   = CreateIdentityServiceResponse(expectedPat);

            var httpHandler = new TestHttpMessageHandler {
                ThrowOnUnexpectedRequest = true
            };

            httpHandler.Setup(HttpMethod.Get, locSvcRequestUri, x =>
            {
                AssertAcceptJson(x);
                AssertBearerToken(x, accessToken);
                return(locSvcResponse);
            });
            httpHandler.Setup(HttpMethod.Post, identSvcRequestUri, x =>
            {
                AssertAcceptJson(x);
                AssertBearerToken(x, accessToken);
                return(identSvcResponse);
            });

            context.HttpClientFactory.MessageHandler = httpHandler;
            var api = new AzureDevOpsRestApi(context);

            string actualPat = await api.CreatePersonalAccessTokenAsync(orgUri, accessToken, scopes);

            Assert.Equal(expectedPat, actualPat);
        }
        public async Task AzureDevOpsRestApi_CreatePersonalAccessTokenAsync_IdentSvcReturnsHttp500WithError_ThrowsExceptionWithErrorMessage()
        {
            const string serverErrorMessage = "ERROR123: This is a test error.";

            var context = new TestCommandContext();
            var orgUri  = new Uri("https://dev.azure.com/org/");

            const string         accessToken = "ACCESS-TOKEN";
            IEnumerable <string> scopes      = new[] { AzureDevOpsConstants.PersonalAccessTokenScopes.ReposWrite };

            var identityServiceUri = new Uri("https://identity.example.com/");

            var locSvcRequestUri = new Uri(orgUri, ExpectedLocationServicePath);
            var locSvcResponse   = CreateLocationServiceResponse(identityServiceUri);

            var identSvcRequestUri = new Uri(identityServiceUri, ExpectedIdentityServicePath);
            var identSvcError      = CreateIdentityServiceErrorResponse(serverErrorMessage);

            var httpHandler = new TestHttpMessageHandler {
                ThrowOnUnexpectedRequest = true
            };

            httpHandler.Setup(HttpMethod.Get, locSvcRequestUri, x =>
            {
                AssertAcceptJson(x);
                AssertBearerToken(x, accessToken);
                return(locSvcResponse);
            });
            httpHandler.Setup(HttpMethod.Post, identSvcRequestUri, _ => identSvcError);

            context.HttpClientFactory.MessageHandler = httpHandler;
            var api = new AzureDevOpsRestApi(context);

            Exception exception = await Assert.ThrowsAsync <Exception>(
                () => api.CreatePersonalAccessTokenAsync(orgUri, accessToken, scopes));

            Assert.Contains(serverErrorMessage, exception.Message, StringComparison.Ordinal);
        }
        public async Task BitbucketRestApi_GetUserInformationAsync_ReturnsUserInfo_ForSuccessfulRequest(string username, string password, bool isBearerToken)
        {
            var twoFactorAuthenticationEnabled = false;
            var uuid      = Guid.NewGuid();
            var accountId = "1234";

            var context = new TestCommandContext();

            var expectedRequestUri = new Uri("https://api.bitbucket.org/2.0/user");

            var userinfoResponseJson = $"{{ \"username\": \"{username}\" , \"has_2fa_enabled\": \"{twoFactorAuthenticationEnabled}\", \"account_id\": \"{accountId}\", \"uuid\": \"{uuid}\"}}";

            var httpResponse = new HttpResponseMessage(HttpStatusCode.OK)
            {
                Content = new StringContent(userinfoResponseJson)
            };

            var httpHandler = new TestHttpMessageHandler();

            httpHandler.Setup(HttpMethod.Get, expectedRequestUri, request =>
            {
                if (isBearerToken)
                {
                    RestTestUtilities.AssertBearerAuth(request, password);
                }
                else
                {
                    RestTestUtilities.AssertBasicAuth(request, username, password);
                }

                return(httpResponse);
            });
            context.HttpClientFactory.MessageHandler = httpHandler;

            var api    = new BitbucketRestApi(context);
            var result = await api.GetUserInformationAsync(username, password, isBearerToken);

            Assert.NotNull(result);
            Assert.Equal(username, result.Response.UserName);
            Assert.Equal(accountId, result.Response.AccountId);
            Assert.Equal(uuid, result.Response.Uuid);
            Assert.Equal(twoFactorAuthenticationEnabled, result.Response.IsTwoFactorAuthenticationEnabled);

            httpHandler.AssertRequest(HttpMethod.Get, expectedRequestUri, 1);
        }
        public async Task GitHubRestApi_AcquireTokenAsync_ValidRequestOK_ReturnsToken()
        {
            const string testUserName = "******";
            const string testPassword = "******";
            const string testAuthCode = "1234";

            string[] testScopes = { "scope1", "scope2" };

            var context = new TestCommandContext();
            var uri     = new Uri("https://github.com");

            var expectedRequestUri = new Uri("https://api.github.com/authorizations");

            const string expectedTokenValue = "GITHUB_TOKEN_VALUE";
            string       tokenResponseJson  = $"{{ \"token\": \"{expectedTokenValue}\" }}";

            var httpResponse = new HttpResponseMessage(HttpStatusCode.OK)
            {
                Content = new StringContent(tokenResponseJson)
            };

            var httpHandler = new TestHttpMessageHandler {
                ThrowOnUnexpectedRequest = true
            };

            httpHandler.Setup(HttpMethod.Post, expectedRequestUri, request =>
            {
                AssertBasicAuth(request, testUserName, testPassword);
                AssertAuthCode(request, testAuthCode);
                return(httpResponse);
            });

            context.HttpClientFactory.MessageHandler = httpHandler;
            var api = new GitHubRestApi(context);

            AuthenticationResult authResult = await api.AcquireTokenAsync(
                uri, testUserName, testPassword, testAuthCode, testScopes);

            Assert.Equal(GitHubAuthenticationResultType.Success, authResult.Type);
            Assert.NotNull(authResult.Token);
            Assert.Equal(expectedTokenValue, authResult.Token.Password);
        }
Beispiel #16
0
        public async Task HostProviderRegistry_GetProvider_Auto_NetworkProbe_NoNetwork_ReturnsLastProvider()
        {
            var context   = new TestCommandContext();
            var registry  = new HostProviderRegistry(context);
            var remoteUri = new Uri("https://provider2.onprem.example.com");
            var input     = new InputArguments(
                new Dictionary <string, string>
            {
                ["protocol"] = remoteUri.Scheme,
                ["host"]     = remoteUri.Host
            }
                );

            var highProviderMock = new Mock <IHostProvider>();

            highProviderMock.Setup(x => x.IsSupported(It.IsAny <InputArguments>())).Returns(false);
            highProviderMock.Setup(x => x.IsSupported(It.IsAny <HttpResponseMessage>())).Returns(false);
            registry.Register(highProviderMock.Object, HostProviderPriority.Normal);

            var lowProviderMock = new Mock <IHostProvider>();

            lowProviderMock.Setup(x => x.IsSupported(It.IsAny <InputArguments>())).Returns(true);
            registry.Register(lowProviderMock.Object, HostProviderPriority.Low);

            var responseMessage = new HttpResponseMessage(HttpStatusCode.Unauthorized)
            {
                Headers = { { "X-Provider2", "true" } }
            };

            var httpHandler = new TestHttpMessageHandler
            {
                SimulateNoNetwork = true,
            };

            httpHandler.Setup(HttpMethod.Head, remoteUri, responseMessage);
            context.HttpClientFactory.MessageHandler = httpHandler;

            IHostProvider result = await registry.GetProviderAsync(input);

            httpHandler.AssertRequest(HttpMethod.Head, remoteUri, 1);
            Assert.Same(lowProviderMock.Object, result);
        }
        public async Task HttpClientExtensions_SendAsync_SendsRequestMessage()
        {
            var method = HttpMethod.Get;
            var uri    = new Uri("http://example.com");

            var httpHandler = new TestHttpMessageHandler {
                ThrowOnUnexpectedRequest = true
            };

            httpHandler.Setup(method, uri, request =>
            {
                Assert.Equal(method, request.Method);
                Assert.Equal(uri, request.RequestUri);

                return(new HttpResponseMessage());
            });

            var httpClient = new HttpClient(httpHandler);

            await HttpClientExtensions.SendAsync(httpClient, method, uri);
        }
        public async Task AzureDevOpsRestApi_CreatePersonalAccessTokenAsync_LocSvcReturnsHttp500_ThrowsException()
        {
            var context = new TestCommandContext();
            var orgUri  = new Uri("https://dev.azure.com/org/");

            const string         accessToken = "ACCESS-TOKEN";
            IEnumerable <string> scopes      = new[] { AzureDevOpsConstants.PersonalAccessTokenScopes.ReposWrite };

            var locSvcRequestUri = new Uri(orgUri, ExpectedLocationServicePath);

            var httpHandler = new TestHttpMessageHandler {
                ThrowOnUnexpectedRequest = true
            };

            httpHandler.Setup(HttpMethod.Get, locSvcRequestUri, HttpStatusCode.InternalServerError);

            context.HttpClientFactory.MessageHandler = httpHandler;
            var api = new AzureDevOpsRestApi(context);

            await Assert.ThrowsAsync <Exception>(() => api.CreatePersonalAccessTokenAsync(orgUri, accessToken, scopes));
        }
        public async Task GitHubRestApi_AcquireTokenAsync_ValidRequestOKBadJson_ReturnsFailure()
        {
            const string testUserName = "******";
            const string testPassword = "******"; // [SuppressMessage("Microsoft.Security", "CS001:SecretInline", Justification="Fake credential")]
            const string testAuthCode = "1234";

            string[] testScopes = { "scope1", "scope2" };

            var context = new TestCommandContext();
            var uri     = new Uri("https://github.com");

            var expectedRequestUri = new Uri("https://api.github.com/authorizations");

            const string tokenResponseJson = "ThisIsBadJSON";

            var httpResponse = new HttpResponseMessage(HttpStatusCode.OK)
            {
                Content = new StringContent(tokenResponseJson)
            };

            var httpHandler = new TestHttpMessageHandler {
                ThrowOnUnexpectedRequest = true
            };

            httpHandler.Setup(HttpMethod.Post, expectedRequestUri, request =>
            {
                RestTestUtilities.AssertBasicAuth(request, testUserName, testPassword);
                AssertAuthCode(request, testAuthCode);
                return(httpResponse);
            });

            context.HttpClientFactory.MessageHandler = httpHandler;
            var api = new GitHubRestApi(context);

            AuthenticationResult authResult = await api.CreatePersonalAccessTokenAsync(
                uri, testUserName, testPassword, testAuthCode, testScopes);

            Assert.Equal(GitHubAuthenticationResultType.Failure, authResult.Type);
        }
        public async Task HttpClientExtensions_SendAsync_Content_SetsContent()
        {
            var method = HttpMethod.Get;
            var uri    = new Uri("http://example.com");

            var expectedContent = new StringContent("foobar");

            var httpHandler = new TestHttpMessageHandler {
                ThrowOnUnexpectedRequest = true
            };

            httpHandler.Setup(method, uri, request =>
            {
                Assert.Same(expectedContent, request.Content);

                return(new HttpResponseMessage());
            });

            var httpClient = new HttpClient(httpHandler);

            await HttpClientExtensions.SendAsync(httpClient, method, uri, null, expectedContent);
        }
        public async Task GitHubRestApi_AcquireTokenAsync_UnknownResponse_ReturnsFailure()
        {
            const string testUserName = "******";
            const string testPassword = "******";
            const string testAuthCode = "1234";

            string[] testScopes = { "scope1", "scope2" };

            var context = new TestCommandContext();
            var uri     = new Uri("https://github.com");

            var expectedRequestUri = new Uri("https://api.github.com/authorizations");

            // https://tools.ietf.org/html/rfc2324#section-2.3.2
            const HttpStatusCode httpIAmATeaPot = (HttpStatusCode)418;
            var httpResponse = new HttpResponseMessage(httpIAmATeaPot)
            {
                Content = new StringContent("I am a tea pot (short and stout).")
            };

            var httpHandler = new TestHttpMessageHandler {
                ThrowOnUnexpectedRequest = true
            };

            httpHandler.Setup(HttpMethod.Post, expectedRequestUri, request =>
            {
                AssertBasicAuth(request, testUserName, testPassword);
                AssertAuthCode(request, testAuthCode);
                return(httpResponse);
            });

            context.HttpClientFactory.MessageHandler = httpHandler;
            var api = new GitHubRestApi(context);

            AuthenticationResult authResult = await api.AcquireTokenAsync(
                uri, testUserName, testPassword, testAuthCode, testScopes);

            Assert.Equal(GitHubAuthenticationResultType.Failure, authResult.Type);
        }
        public async Task GitHubRestApi_AcquireTokenAsync_ValidOAuthToken_ReturnsOAuthToken()
        {
            const string testUserName   = "******";
            const string testOAuthToken = "TestOAuthToken";

            string[] testScopes = { "scope1", "scope2" };

            var context = new TestCommandContext();
            var uri     = new Uri("https://github.com");

            var expectedRequestUri = new Uri("https://api.github.com/authorizations");

            var httpResponse = new HttpResponseMessage(HttpStatusCode.Forbidden)
            {
                Content = new StringContent("This API can only be accessed with username and password Basic Auth")
            };

            var httpHandler = new TestHttpMessageHandler {
                ThrowOnUnexpectedRequest = true
            };

            httpHandler.Setup(HttpMethod.Post, expectedRequestUri, request =>
            {
                AssertBasicAuth(request, testUserName, testOAuthToken);
                AssertAuthCode(request, null);
                return(httpResponse);
            });

            context.HttpClientFactory.MessageHandler = httpHandler;
            var api = new GitHubRestApi(context);

            AuthenticationResult authResult = await api.AcquireTokenAsync(
                uri, testUserName, testOAuthToken, null, testScopes);

            Assert.Equal(GitHubAuthenticationResultType.Success, authResult.Type);
            Assert.NotNull(authResult.Token);
            Assert.Equal(testOAuthToken, authResult.Token.Password);
        }
        public async Task GitHubRestApi_AcquireTokenAsync_Forbidden_ReturnsFailure()
        {
            const string testUserName = "******";
            const string testPassword = "******";
            const string testAuthCode = "1234";

            string[] testScopes = { "scope1", "scope2" };

            var context = new TestCommandContext();
            var uri     = new Uri("https://github.com");

            var expectedRequestUri = new Uri("https://api.github.com/authorizations");

            var httpResponse = new HttpResponseMessage(HttpStatusCode.Forbidden)
            {
                Content = new StringContent(string.Empty)
            };

            var httpHandler = new TestHttpMessageHandler {
                ThrowOnUnexpectedRequest = true
            };

            httpHandler.Setup(HttpMethod.Post, expectedRequestUri, request =>
            {
                AssertBasicAuth(request, testUserName, testPassword);
                AssertAuthCode(request, testAuthCode);
                return(httpResponse);
            });

            context.HttpClientFactory.MessageHandler = httpHandler;
            var api = new GitHubRestApi(context);

            AuthenticationResult authResult = await api.AcquireTokenAsync(
                uri, testUserName, testPassword, testAuthCode, testScopes);

            Assert.Equal(GitHubAuthenticationResultType.Failure, authResult.Type);
        }