/// <summary>
        /// Extracts the User details accessing the service as a unique id in the form
        /// of "{authprovider}:{uniqueId}" using ProviderCrednetials for the logged
        /// in user.
        /// </summary>
        /// <param name="principal">The principal accessing the service.</param>
        /// <param name="request">The HttpRequest used to access the service.</param>
        /// <returns>The unique user id.</returns>
        public async Task<string> GetCurrentUserRegistrationReferenceAsync(ClaimsPrincipal principal, HttpRequestMessage request)
        {
            string provider = principal?.FindFirst("http://schemas.microsoft.com/identity/claims/identityprovider").Value;

            ProviderCredentials creds = null;
            if (string.Equals(provider, "facebook", StringComparison.OrdinalIgnoreCase))
            {
                creds = await principal.GetAppServiceIdentityAsync<FacebookCredentials>(request);
            }
            else if (string.Equals(provider, "google", StringComparison.OrdinalIgnoreCase))
            {
                creds = await principal.GetAppServiceIdentityAsync<GoogleCredentials>(request);
            }
            else if (string.Equals(provider, "twitter", StringComparison.OrdinalIgnoreCase))
            {
                creds = await principal.GetAppServiceIdentityAsync<TwitterCredentials>(request);
            }
            else if (string.Equals(provider, "microsoftaccount", StringComparison.OrdinalIgnoreCase))
            {
                creds = await principal.GetAppServiceIdentityAsync<MicrosoftAccountCredentials>(request);
            }

            if (creds == null)
            {
                throw ServiceExceptions.UserNullException();
            }

            // Format user details in the desired form of {authprovider}:{uniqueId}
            string authProvider = creds.Provider;
            string uniqueId = creds.UserClaims.FirstOrDefault(c => c.Type.Equals(ClaimTypes.NameIdentifier))?.Value;
            var uniqueUserName = $"{authProvider}:{uniqueId}";

            return uniqueUserName;
        }
        public async Task GetIdentityAsync_Throws_IfNoIssuer()
        {
            // Arrange
            ClaimsPrincipal user = new ClaimsPrincipal(CreateMockClaimsIdentity(new Claim[] { new Claim("notiss", "nope") }, true));
            HttpRequestMessage request = new HttpRequestMessage();
            request.Headers.Add(AuthHeaderName, "some jwt");

            // Act
            ArgumentOutOfRangeException ex = await Assert.ThrowsAsync<ArgumentOutOfRangeException>(async () => await user.GetAppServiceIdentityAsync<FacebookCredentials>(request));

            // Assert
            Assert.Equal("The IPrincipal's Claims must contain an 'iss' Claim.", ex.Message);
        }
        public async Task GetIdentityAsync_ReturnsNull_IfUserNotAuthenticated()
        {
            // Arrange
            ClaimsPrincipal user = new ClaimsPrincipal(CreateMockClaimsIdentity(Enumerable.Empty<Claim>(), false));
            HttpRequestMessage request = new HttpRequestMessage();

            // Act
            var tokenResult = await user.GetAppServiceIdentityAsync<FacebookCredentials>(request);

            // Assert
            Assert.Null(tokenResult);
        }
        public async Task GetIdentityAsync_ReturnsNull_IfMobileAppAuthenticationTokenIsNullOrEmpty(string token)
        {
            // Arrange
            ClaimsPrincipal user = new ClaimsPrincipal(CreateMockClaimsIdentity(Enumerable.Empty<Claim>(), true));
            HttpRequestMessage request = new HttpRequestMessage();
            request.RequestUri = new Uri(TestLocalhostUrl);
            request.Headers.Add(AuthHeaderName, token);

            // Act
            var tokenResult = await user.GetAppServiceIdentityAsync<FacebookCredentials>(request);

            // Assert
            Assert.Null(tokenResult);
        }
        public async Task GetIdentityAsync_Succeeds()
        {
            // Arrange
            TokenEntry tokenEntry = new TokenEntry("facebook");
            tokenEntry.UserId = "userId";
            tokenEntry.AccessToken = "accessToken";
            tokenEntry.UserClaims = new List<ClaimSlim>() { new ClaimSlim(ClaimTypes.NameIdentifier, "11111111") };

            HttpResponseMessage response = CreateOkResponseWithContent(tokenEntry);
            MockHttpMessageHandler handler = new MockHttpMessageHandler(response);

            ClaimsPrincipal user = new ClaimsPrincipal(CreateMockClaimsIdentity(new[] { new Claim(JwtRegisteredClaimNames.Iss, "http://contoso.com") }, true));
            HttpRequestMessage request = new HttpRequestMessage();
            request.Headers.Add(AuthHeaderName, "token");

            //Act
            FacebookCredentials creds = await user.GetAppServiceIdentityAsync<FacebookCredentials>(request, new HttpClient(handler));

            // Assert
            Assert.Equal(tokenEntry.UserId, creds.UserId);
            Assert.Equal(tokenEntry.AccessToken, creds.AccessToken);
            Assert.Equal("Facebook", creds.Provider);
            Assert.Equal(1, tokenEntry.UserClaims.Count());
            ClaimSlim claim = tokenEntry.UserClaims[0];
            Assert.Equal(ClaimTypes.NameIdentifier, claim.Type);
            Assert.Equal("11111111", claim.Value);

            Assert.Equal("http://contoso.com/.auth/me?provider=facebook", handler.ActualRequest.RequestUri.ToString());
            Assert.Equal("token", handler.ActualRequest.GetHeaderOrDefault(AuthHeaderName));
        }