예제 #1
2
 /// <summary>
 /// Retrieves a new auth token from AAD.
 /// </summary>
 /// <param name="authUrl">The root of the authority url.</param>
 /// <param name="tenantDomain">The domain name of the Azure tenant as the second part of the authority url.</param>
 /// <param name="targetServiceUrl">The url of the service that should be accessed. Be sure to check trailing slashes!</param>
 /// <param name="clientId">The unique client id as it is configured in Azure Portal.</param>
 /// <param name="appKey">This value is optional and contains the App-Key-Secret if it is configured in azure portal.</param>
 /// <param name="redirectUrl">The redirect url as it is configured in Azure Portal.</param>
 /// <returns>The authentication token.</returns>
 public static async Task<string> RetrieveTokenAsync(string authUrl, string tenantDomain, string targetServiceUrl, string clientId, Uri redirectUrl, string appKey = null)
 {
     var authenticationContext = new AuthenticationContext($"{authUrl}/{tenantDomain}");
     try
     {
         AuthenticationResult result = null;                
         if (appKey.IsNullOrEmpty())
         {
             // use user auth
             var parameters = new PlatformParameters(PromptBehavior.Auto);
             result = await authenticationContext.AcquireTokenAsync(targetServiceUrl, clientId, redirectUrl, parameters).ConfigureAwait(false);
         }
         else
         {
             // use key auth
             var clientCredential = new ClientCredential(clientId, appKey);
             result = await authenticationContext.AcquireTokenAsync(targetServiceUrl, clientCredential).ConfigureAwait(false);
         }
         if (result == null)
         {
             throw new InvalidOperationException("Failed to obtain the JWT token");
         }
         // store token for reuse
         return result.AccessToken;
     }
     catch (Exception ex)
     {
         throw new InvalidOperationException("Could not retrieve token.", ex);
     }
 }
        public override void AddPromptBehaviorQueryParameter(IPlatformParameters parameters, DictionaryRequestParameters authorizationRequestParameters)
        {
            PlatformParameters authorizationParameters = (parameters as PlatformParameters);

            if (authorizationParameters == null)
            {
                throw new ArgumentException("parameters should be of type PlatformParameters", "parameters");
            }

            PromptBehavior promptBehavior = authorizationParameters.PromptBehavior;

            switch (promptBehavior)
            {
            case PromptBehavior.Always:
                authorizationRequestParameters[OAuthParameter.Prompt] = PromptValue.Login;
                break;

            case PromptBehavior.SelectAccount:
                authorizationRequestParameters[OAuthParameter.Prompt] = PromptValue.SelectAccount;
                break;

            case PromptBehavior.RefreshSession:
                authorizationRequestParameters[OAuthParameter.Prompt] = PromptValue.RefreshSession;
                break;
            }
        }
        public override void AddPromptBehaviorQueryParameter(IPlatformParameters parameters, DictionaryRequestParameters authorizationRequestParameters)
        {
            PlatformParameters authorizationParameters = (parameters as PlatformParameters);

            if (authorizationParameters == null)
            {
                throw new ArgumentException("parameters should be of type PlatformParameters", "parameters");
            }

            PromptBehavior promptBehavior = authorizationParameters.PromptBehavior;

            // ADFS currently ignores the parameter for now.
            switch (promptBehavior)
            {
            case PromptBehavior.Always:
                authorizationRequestParameters[OAuthParameter.Prompt] = PromptValue.Login;
                break;

            case PromptBehavior.RefreshSession:
                authorizationRequestParameters[OAuthParameter.Prompt] = PromptValue.RefreshSession;
                break;

            case PromptBehavior.Never:
                authorizationRequestParameters[OAuthParameter.Prompt] = PromptValue.AttemptNone;
                break;
            }
        }
예제 #4
0
        public async Task<string> Login(string sharePointSiteUrl, bool forceLogin = false)
        {
            var spUri = new Uri(sharePointSiteUrl);

            string resourceUri = spUri.Scheme + "://" + spUri.Authority;

            ADAL.AuthenticationResult authenticationResult;
 
            try
            {
                authenticationResult = await AuthContext.AcquireTokenSilentAsync(resourceUri, clientId);
            }
            catch (ADAL.AdalSilentTokenAcquisitionException)
            {
                //Console.WriteLine("Silent Async failed. Use prompt instead.");

                try
                {
                    // prevent flashing of login window when credentials are valid
                    var authParam = new ADAL.PlatformParameters(ADAL.PromptBehavior.Never);
                    authenticationResult = await AuthContext.AcquireTokenAsync(resourceUri, clientId, new Uri(redirectUri), authParam);
                }
                catch (ADAL.AdalException /* e */)
                {
                    //Console.WriteLine(e);

                    var authParam = new ADAL.PlatformParameters(ADAL.PromptBehavior.Auto);
                    authenticationResult = await AuthContext.AcquireTokenAsync(resourceUri, clientId, new Uri(redirectUri), authParam);

                }
            }


            return authenticationResult.CreateAuthorizationHeader();
        }
예제 #5
0
        public IWebUI CreateAuthenticationDialog(IPlatformParameters inputParameters)
        {
            this.parameters = inputParameters as PlatformParameters;
            if (this.parameters == null)
            {
                throw new ArgumentException("parameters should be of type PlatformParameters", "parameters");
            }

            switch (this.parameters.PromptBehavior)
            {
            case PromptBehavior.Auto:
                return(new InteractiveWebUI {
                    OwnerWindow = this.parameters.OwnerWindow
                });

            case PromptBehavior.Always:
            case PromptBehavior.RefreshSession:
                return(new InteractiveWebUI {
                    OwnerWindow = this.parameters.OwnerWindow
                });

            case PromptBehavior.Never:
                return(new SilentWebUI {
                    OwnerWindow = this.parameters.OwnerWindow
                });

            default:
                throw new InvalidOperationException("Unexpected PromptBehavior value");
            }
        }
예제 #6
0
 public WebUI(IPlatformParameters parameters)
 {
     this.parameters = parameters as PlatformParameters;
     if (this.parameters == null)
     {
         throw new ArgumentException("parameters should be of type PlatformParameters", "parameters");
     }
 }
예제 #7
0
 public WebUI(IPlatformParameters parameters)
 {
     this.parameters = parameters as PlatformParameters;
     if (this.parameters == null)
     {
         throw new ArgumentException("parameters should be of type PlatformParameters", "parameters");
     }
 }
		public static async Task<AuthenticationResult> GetAccessToken(string serviceResourceId, PlatformParameters param)
		{
			authContext = new AuthenticationContext(Authority);
			if (authContext.TokenCache.ReadItems ().Any ())
				authContext = new AuthenticationContext (authContext.TokenCache.ReadItems ().First ().Authority);
			var authResult = await authContext.AcquireTokenAsync(serviceResourceId, clientId, returnUri, param);
			return authResult;
		}
        public async Task <AuthorizationResult> AcquireAuthorizationAsync(Uri authorizationUri, Uri redirectUri, CallState callState)
        {
            returnedUriReady = new SemaphoreSlim(0);
            Authenticate(authorizationUri, redirectUri, callState);
            await returnedUriReady.WaitAsync().ConfigureAwait(false);

            this.parameters = null;
            return(authorizationResult);
        }
예제 #10
0
 public async Task<AuthenticationResult> Authenticate(string authority, string resource, string clientId, string returnUri)
 {
     var authContext = new AuthenticationContext(authority);
     if (authContext.TokenCache.ReadItems().Any())
         authContext = new AuthenticationContext(authContext.TokenCache.ReadItems().First().Authority);
     var uri = new Uri(returnUri);
     var platformParams = new PlatformParameters((Activity)Forms.Context);
     var authResult = await authContext.AcquireTokenAsync(resource, clientId, uri, platformParams);
     return authResult;
 }
예제 #11
0
 public async Task<AuthenticationResult> Authenticate(string authority, string resource, string clientId, string returnUri)
 {
     authContext = new AuthenticationContext(authority);
     if (authContext.TokenCache.ReadItems().Any())
         authContext = new AuthenticationContext(authContext.TokenCache.ReadItems().First().Authority);
     var controller = UIApplication.SharedApplication.KeyWindow.RootViewController;
     var uri = new Uri(returnUri);
     var platformParams = new PlatformParameters(controller);
     var authResult = await authContext.AcquireTokenAsync(resource, clientId, uri, platformParams);
     return authResult;
 }
        private bool WillUseBroker()
        {
            PlatformParameters pp = PlatformParameters as PlatformParameters;

            if (pp != null)
            {
                return(pp.UseBroker);
            }

            return(false);
        }
        public override bool GetCacheLoadPolicy(IPlatformParameters parameters)
        {
            PlatformParameters authorizationParameters = (parameters as PlatformParameters);

            if (authorizationParameters == null)
            {
                throw new ArgumentException("parameters should be of type PlatformParameters", "parameters");
            }

            PromptBehavior promptBehavior = authorizationParameters.PromptBehavior;

            return(promptBehavior != PromptBehavior.Always && promptBehavior != PromptBehavior.RefreshSession);
        }
예제 #14
0
        public async Task <IAdalResult> AcquireTokenAsync(
            string authorityHostUrl,
            string resource,
            string clientId,
            Uri redirectUri,
            string extraQueryParameters)
        {
            if (authorityHostUrl is null)
            {
                throw new ArgumentNullException(nameof(authorityHostUrl));
            }
            if (resource is null)
            {
                throw new ArgumentNullException(nameof(resource));
            }
            if (clientId is null)
            {
                throw new ArgumentNullException(nameof(clientId));
            }
            if (redirectUri is null)
            {
                throw new ArgumentNullException(nameof(redirectUri));
            }
            if (extraQueryParameters is null)
            {
                throw new ArgumentNullException(nameof(extraQueryParameters));
            }

            try
            {
                var authenticationContext = new ActiveDirectory.AuthenticationContext(authorityHostUrl, _cache);
                var platformParameters    = new ActiveDirectory.PlatformParameters(ActiveDirectory.PromptBehavior.SelectAccount);
                var userIdentifier        = ActiveDirectory.UserIdentifier.AnyUser;

                ActiveDirectory.AuthenticationResult result = await authenticationContext.AcquireTokenAsync(resource,
                                                                                                            clientId,
                                                                                                            redirectUri,
                                                                                                            platformParameters,
                                                                                                            userIdentifier,
                                                                                                            extraQueryParameters);

                return(new Result(result));
            }
            // We should just be able to catch AdalException here but due to an ADAL bug an HttpRequestException can be leaked:
            // https://github.com/AzureAD/azure-activedirectory-library-for-dotnet/issues/1285
            // Until we update to ADAL 4.x or MSAL, we should just workaround this problem.
            catch (Exception exception)
            {
                throw new AuthenticationException(exception);
            }
        }
        public async Task <IAdalResult> AcquireTokenAsync(
            string authorityHostUrl,
            string resource,
            string clientId,
            Uri redirectUri,
            string extraQueryParameters)
        {
            if (authorityHostUrl is null)
            {
                throw new ArgumentNullException(nameof(authorityHostUrl));
            }
            if (resource is null)
            {
                throw new ArgumentNullException(nameof(resource));
            }
            if (clientId is null)
            {
                throw new ArgumentNullException(nameof(clientId));
            }
            if (redirectUri is null)
            {
                throw new ArgumentNullException(nameof(redirectUri));
            }
            if (extraQueryParameters is null)
            {
                throw new ArgumentNullException(nameof(extraQueryParameters));
            }

            try
            {
                var authenticationContext = new ActiveDirectory.AuthenticationContext(authorityHostUrl, _cache);
                var platformParameters    = new ActiveDirectory.PlatformParameters(ActiveDirectory.PromptBehavior.SelectAccount);
                var userIdentifier        = ActiveDirectory.UserIdentifier.AnyUser;

                ActiveDirectory.AuthenticationResult result = await authenticationContext.AcquireTokenAsync(resource,
                                                                                                            clientId,
                                                                                                            redirectUri,
                                                                                                            platformParameters,
                                                                                                            userIdentifier,
                                                                                                            extraQueryParameters);

                return(new Result(result));
            }
            catch (ActiveDirectory.AdalException exception)
            {
                throw new AuthenticationException(exception);
            }
        }
예제 #16
0
        public static AuthenticationResult GetAzureAdToken(AuthenticationContext authContext, String resourceHostUri,
            string clientId, string redirectUri, UserCredential uc)
        {
            AuthenticationResult authenticationResult = null;

            Console.WriteLine("Performing GetAzureAdToken");
            try
            {
                Console.WriteLine("Passed resource host URI is " + resourceHostUri);
                if (resourceHostUri.StartsWith("http"))
                {
                    resourceHostUri = Helpers.ReduceUriToProtoAndHost(resourceHostUri);
                    Console.WriteLine("Normalized the resourceHostUri to just the protocol and hostname " + resourceHostUri);
                }

                // check if there's a user credential - i.e. a username and password

                if(uc != null)
                    {
                    authenticationResult = authContext.AcquireTokenAsync(resourceHostUri, clientId, uc).Result;

                }
                else {
                    PlatformParameters platformParams = new PlatformParameters(PromptBehavior.Auto);
                    authenticationResult = authContext.AcquireTokenAsync(resourceHostUri, clientId, new Uri(redirectUri), platformParams).Result;
                }

                //Console.WriteLine("Bearer token from Azure AD is " + authenticationResult.AccessToken);
            }
            catch (Exception ex)
            {
                Console.ForegroundColor = ConsoleColor.Red;
                Console.WriteLine("An unexpected error occurred.");
                string message = ex.Message;
                if (ex.InnerException != null)
                {
                    message += Environment.NewLine + "Inner Exception : " + ex.InnerException.Message;
                }
                Console.WriteLine("Message: {0}", message);
                Console.ForegroundColor = ConsoleColor.White;

            }

            return authenticationResult;
        }
예제 #17
0
        public async Task<AuthenticationResult> Authenticate(string authority, string resource, string clientId, string returnUri)
        {
            var authContext = new AuthenticationContext(authority);

            if (authContext.TokenCache.ReadItems().Any())
                authContext = new AuthenticationContext(authContext.TokenCache.ReadItems().First().Authority);
            
            var topController = UIApplication.SharedApplication.KeyWindow.RootViewController;

            // ensures that the currently presented viewcontroller is acquired, even a modally presented one
            while (topController.PresentedViewController != null) {
                topController = topController.PresentedViewController;
            }

            var platformParams = new PlatformParameters(topController);

            var authResult = await authContext.AcquireTokenAsync(resource, clientId, new Uri(returnUri), platformParams);

            return authResult;
        }
예제 #18
0
        public IWebUI CreateAuthenticationDialog(IPlatformParameters inputParameters)
        {
            this.parameters = inputParameters as PlatformParameters;
            if (this.parameters == null)
            {
                throw new ArgumentException("parameters should be of type PlatformParameters", "parameters");
            }

            switch (this.parameters.PromptBehavior)
            {
                case PromptBehavior.Auto:
                    return new InteractiveWebUI { OwnerWindow = this.parameters.OwnerWindow };
                case PromptBehavior.Always:
                case PromptBehavior.RefreshSession:
                    return new InteractiveWebUI { OwnerWindow = this.parameters.OwnerWindow };
                case PromptBehavior.Never:
                    return new SilentWebUI { OwnerWindow = this.parameters.OwnerWindow };
                default:
                    throw new InvalidOperationException("Unexpected PromptBehavior value");
            }
        }  
        public void Authenticate(Uri authorizationUri, Uri redirectUri, CallState callState)
        {
            try
            {
                this.parameters.CallerViewController.InvokeOnMainThread(() =>
                {
                    var navigationController =
                        new AuthenticationAgentUINavigationController(authorizationUri.AbsoluteUri,
                                                                      redirectUri.OriginalString, CallbackMethod, this.parameters.PreferredStatusBarStyle);

                    navigationController.ModalPresentationStyle = this.parameters.ModalPresentationStyle;
                    navigationController.ModalTransitionStyle   = this.parameters.ModalTransitionStyle;
                    navigationController.TransitioningDelegate  = this.parameters.TransitioningDelegate;

                    this.parameters.CallerViewController.PresentViewController(navigationController, true, null);
                });
            }
            catch (Exception ex)
            {
                this.parameters = null;
                throw new AdalException(AdalError.AuthenticationUiFailed, ex);
            }
        }
예제 #20
0
        public async Task<bool> InitializeAsync()
        {
            var tenant      = _configurationReader["AAD_Tenant"];
            var instance    = _configurationReader["AAD_Instance"];
            var resourceId  = _configurationReader["AAD_ResourceId"];
            var clientId    = _configurationReader["AAD_ClientId"];
            var callbackUrl = _configurationReader["AAD_CallbackUri"];

            var callbackUri = new Uri(callbackUrl);
            var authority = String.Format(CultureInfo.InvariantCulture, instance, tenant);

            var redirectUri = Windows.Security.Authentication.Web.WebAuthenticationBroker.GetCurrentApplicationCallbackUri();
            var authContext = new AuthenticationContext(authority);

            var platformParameters = new PlatformParameters(PromptBehavior.Auto, false);

            _authenticationResult = await authContext.AcquireTokenAsync(resourceId, clientId, callbackUri, platformParameters);

            if (_authenticationResult == null)
                return false;

            return true;

        }
예제 #21
0
        public async Task<bool> EnsureAuthenticationContext(string authority, bool show)
        {
            if (this.AuthenticationContext == null)
            {
                var cache = _cachePersist.Read();

                if (cache != null)
                {
                    var t = new TokenCache(cache);
                    this.AuthenticationContext = new AuthenticationContext(authority, t);
                }
                else
                {
                    this.AuthenticationContext = new AuthenticationContext(authority);
                }
            }
           
            var p = new PlatformParameters(show ? PromptBehavior.Always : PromptBehavior.Never, _deviceService.WindowHandle);
            this.AuthenticationResult =
                await this.AuthenticationContext.AcquireTokenAsync(
                    Office365ServicesUris.AADGraphAPIResourceId,
                    ClientId,
                    new Uri(RedirectUri),
                    p);

            var tokenCache = AuthenticationContext.TokenCache.Serialize();
            
            _cachePersist.Write(tokenCache);

            return !string.IsNullOrWhiteSpace(this.AuthenticationResult.AccessToken);
        }
        public static async Task ForcePromptTestAsync(Sts sts)
        {
            SetCredential(sts);
            var context = new AuthenticationContextProxy(sts.Authority, sts.ValidateAuthority);
            AuthenticationResultProxy result = await context.AcquireTokenAsync(sts.ValidResource, sts.ValidClientId, sts.ValidDefaultRedirectUri, PlatformParameters, sts.ValidUserId);
            VerifySuccessResult(sts, result);

            AuthenticationContextProxy.SetCredentials(null, null);
            AuthenticationResultProxy result2 = await context.AcquireTokenAsync(sts.ValidResource, sts.ValidClientId, sts.ValidDefaultRedirectUri, PlatformParameters,
                (sts.Type == StsType.ADFS) ? null : sts.ValidUserId);
            VerifySuccessResult(sts, result2);
            Verify.AreEqual(result2.AccessToken, result.AccessToken);

            AuthenticationContextProxy.SetCredentials(sts.ValidUserName, sts.ValidPassword);
            var neverAuthorizationParameters = new PlatformParameters(PromptBehavior.Always, null);
            result = await context.AcquireTokenAsync(sts.ValidResource, sts.ValidClientId, sts.ValidDefaultRedirectUri, neverAuthorizationParameters);
            VerifySuccessResult(sts, result);
            Verify.AreNotEqual(result2.AccessToken, result.AccessToken);
        }
        public static async Task AcquireTokenAndRefreshSessionTestAsync(Sts sts)
        {
            var userId = sts.ValidUserId;

            AuthenticationContextProxy.SetCredentials(userId.Id, sts.ValidPassword);
            var context = new AuthenticationContextProxy(sts.Authority, false, TokenCacheType.InMemory);
            AuthenticationResultProxy result = await context.AcquireTokenAsync(sts.ValidResource, sts.ValidClientId, sts.ValidDefaultRedirectUri, PlatformParameters, userId);
            VerifySuccessResult(sts, result);
            AuthenticationContextProxy.Delay(2000);
            var refreshSessionAuthorizationParameters = new PlatformParameters(PromptBehavior.RefreshSession, null);
            AuthenticationResultProxy result2 = await context.AcquireTokenAsync(sts.ValidResource, sts.ValidClientId, sts.ValidDefaultRedirectUri, refreshSessionAuthorizationParameters, userId);
            VerifySuccessResult(sts, result2);
            Verify.AreNotEqual(result.AccessToken, result2.AccessToken);
        }
        // Get an access token for the given context and resourceId. An attempt is first made to 
        // acquire the token silently. If that fails, then we try to acquire the token by prompting the user.
        private static async Task<string> GetTokenHelperAsync(AuthenticationContext context, string resourceId)
        {
            string accessToken = null;
            AuthenticationResult result = null;

            try
            {
                // can use this app inside a corporate intranet. If the value of UseCorporateNetwork 
                // is true, you also need to add the Enterprise Authentication, Private Networks, and
                // Shared User Certificates capabilities in the Package.appxmanifest file.
                var platformParameters = new PlatformParameters(PromptBehavior.Auto, true);

                result = await context.AcquireTokenAsync(resourceId, ClientID, redirectUri, platformParameters);
                accessToken = result.AccessToken;
                //Store values for logged-in user, tenant id, and authority, so that
                //they can be re-used if the user re-opens the app without disconnecting.
                _settings.Values["LoggedInUser"] = result.UserInfo.GivenName;
                _settings.Values["LoggedInUserEmail"] = result.UserInfo.DisplayableId;
                _settings.Values["TenantId"] = result.TenantId;
                _settings.Values["LastAuthority"] = context.Authority;

                AccessToken = accessToken;
                return accessToken;
            }
            catch
            {
                return null;
            }
        }
        internal static async Task AcquireTokenWithPromptBehaviorNeverTestAsync(Sts sts)
        {
            // Should not be able to get a token silently on first try.
            var context = new AuthenticationContextProxy(sts.Authority, sts.ValidateAuthority);
            var neverAuthorizationParameters = new PlatformParameters(PromptBehavior.Never, null);
            AuthenticationResultProxy result = await context.AcquireTokenAsync(sts.ValidResource, sts.ValidClientId, sts.ValidDefaultRedirectUri, neverAuthorizationParameters);
            VerifyErrorResult(result, Sts.UserInteractionRequired, null);

            AuthenticationContextProxy.SetCredentials(sts.ValidUserName, sts.ValidPassword);
            // Obtain a token interactively.
            result = await context.AcquireTokenAsync(sts.ValidResource, sts.ValidClientId, sts.ValidDefaultRedirectUri, PlatformParameters, sts.ValidUserId);
            VerifySuccessResult(sts, result);

            AuthenticationContextProxy.SetCredentials(null, null);
            // Now there should be a token available in the cache so token should be available silently.
            result = await context.AcquireTokenAsync(sts.ValidResource, sts.ValidClientId, sts.ValidDefaultRedirectUri, neverAuthorizationParameters);
            VerifySuccessResult(sts, result);

            // Clear the cache and silent auth should work via session cookies.
            AuthenticationContextProxy.ClearDefaultCache();
            result = await context.AcquireTokenAsync(sts.ValidResource, sts.ValidClientId, sts.ValidDefaultRedirectUri, neverAuthorizationParameters);
            VerifySuccessResult(sts, result);

            // Clear the cache and cookies and silent auth should fail.
            AuthenticationContextProxy.ClearDefaultCache();
            EndBrowserDialogSession();
            result = await context.AcquireTokenAsync(sts.ValidResource, sts.ValidClientId, sts.ValidDefaultRedirectUri, neverAuthorizationParameters);
            VerifyErrorResult(result, Sts.UserInteractionRequired, null);
        }
        internal static async Task SwitchUserTestAsync(Sts sts)
        {
            Log.Comment("Acquire token for user1 interactively");
            AuthenticationContextProxy.SetCredentials(null, sts.ValidPassword);
            var context = new AuthenticationContextProxy(sts.Authority, sts.ValidateAuthority);
            AuthenticationResultProxy result = await context.AcquireTokenAsync(sts.ValidResource, sts.ValidClientId, sts.ValidDefaultRedirectUri, PlatformParameters, sts.ValidUserId);
            VerifySuccessResultAndTokenContent(sts, result);
            Verify.AreEqual(sts.ValidUserName, result.UserInfo.DisplayableId);

            Log.Comment("Acquire token via cookie for user1 without user");
            AuthenticationResultProxy result2 = await context.AcquireTokenAsync(sts.ValidResource, sts.ValidClientId, sts.ValidDefaultRedirectUri, PlatformParameters);
            VerifySuccessResultAndTokenContent(sts, result2);
            Verify.AreEqual(sts.ValidUserName, result2.UserInfo.DisplayableId);

            Log.Comment("Acquire token for user2 via force prompt and user");
            AuthenticationContextProxy.SetCredentials(sts.ValidUserName2, sts.ValidPassword2);
            var alwaysAuthorizationParameters = new PlatformParameters(PromptBehavior.Always, null);
            result2 = await context.AcquireTokenAsync(sts.ValidResource, sts.ValidClientId, sts.ValidDefaultRedirectUri, alwaysAuthorizationParameters, sts.ValidRequiredUserId2);
            VerifySuccessResultAndTokenContent(sts, result2);
            Verify.AreEqual(sts.ValidUserName2, result2.UserInfo.DisplayableId);

            Log.Comment("Acquire token for user2 via force prompt");
            AuthenticationContextProxy.SetCredentials(sts.ValidUserName2, sts.ValidPassword2);
            result2 = await context.AcquireTokenAsync(sts.ValidResource, sts.ValidClientId, sts.ValidDefaultRedirectUri, alwaysAuthorizationParameters);
            VerifySuccessResultAndTokenContent(sts, result2);
            Verify.AreEqual(sts.ValidUserName2, result2.UserInfo.DisplayableId);

            Log.Comment("Fail to acquire token without user while tokens for two users in the cache");
            result2 = await context.AcquireTokenAsync(sts.ValidResource, sts.ValidClientId, sts.ValidDefaultRedirectUri, PlatformParameters);
            VerifyErrorResult(result2, "multiple_matching_tokens_detected", null);
        }
        public void AcquireToken(IDictionary <string, string> brokerPayload)
        {
            if (brokerPayload.ContainsKey("broker_install_url"))
            {
                string url   = brokerPayload["broker_install_url"];
                Uri    uri   = new Uri(url);
                string query = uri.Query;
                if (query.StartsWith("?"))
                {
                    query = query.Substring(1);
                }

                Dictionary <string, string> keyPair = EncodingHelper.ParseKeyValueList(query, '&', true, false, null);

                PlatformParameters pp = PlatformParameters as PlatformParameters;
                pp.CallerActivity.StartActivity(new Intent(Intent.ActionView, Android.Net.Uri.Parse(keyPair["app_link"])));

                throw new AdalException(AdalErrorAndroidEx.BrokerApplicationRequired, AdalErrorMessageAndroidEx.BrokerApplicationRequired);
            }

            Context mContext = Application.Context;
            AuthenticationRequest request        = new AuthenticationRequest(brokerPayload);
            PlatformParameters    platformParams = PlatformParameters as PlatformParameters;

            // BROKER flow intercepts here
            // cache and refresh call happens through the authenticator service
            if (mBrokerProxy.VerifyUser(request.LoginHint,
                                        request.UserId))
            {
                CallState.Logger.Verbose(null, "It switched to broker for context: " + mContext.PackageName);
                request.BrokerAccountName = request.LoginHint;

                // Don't send background request, if prompt flag is always or
                // refresh_session
                bool hasAccountNameOrUserId = !string.IsNullOrEmpty(request.BrokerAccountName) || !string.IsNullOrEmpty(request.UserId);
                if (string.IsNullOrEmpty(request.Claims) && hasAccountNameOrUserId)
                {
                    CallState.Logger.Verbose(null, "User is specified for background token request");
                    resultEx = mBrokerProxy.GetAuthTokenInBackground(request, platformParams.CallerActivity);
                }
                else
                {
                    CallState.Logger.Verbose(null, "User is not specified for background token request");
                }

                if (resultEx != null && resultEx.Result != null && !string.IsNullOrEmpty(resultEx.Result.AccessToken))
                {
                    CallState.Logger.Verbose(null, "Token is returned from background call ");
                    readyForResponse.Release();
                    return;
                }

                // Launch broker activity
                // if cache and refresh request is not handled.
                // Initial request to authenticator needs to launch activity to
                // record calling uid for the account. This happens for Prompt auto
                // or always behavior.
                CallState.Logger.Verbose(null, "Token is not returned from backgroud call");

                // Only happens with callback since silent call does not show UI
                CallState.Logger.Verbose(null, "Launch activity for Authenticator");
                CallState.Logger.Verbose(null, "Starting Authentication Activity");
                if (resultEx == null)
                {
                    CallState.Logger.Verbose(null, "Initial request to authenticator");
                    // Log the initial request but not force a prompt
                }

                if (brokerPayload.ContainsKey("silent_broker_flow"))
                {
                    throw new AdalSilentTokenAcquisitionException();
                }

                // onActivityResult will receive the response
                // Activity needs to launch to record calling app for this
                // account
                Intent brokerIntent = mBrokerProxy.GetIntentForBrokerActivity(request, platformParams.CallerActivity);
                if (brokerIntent != null)
                {
                    try
                    {
                        CallState.Logger.Verbose(null, "Calling activity pid:" + Android.OS.Process.MyPid()
                                                 + " tid:" + Android.OS.Process.MyTid() + "uid:"
                                                 + Android.OS.Process.MyUid());
                        platformParams.CallerActivity.StartActivityForResult(brokerIntent, 1001);
                    }
                    catch (ActivityNotFoundException e)
                    {
                        CallState.Logger.Error(null, e);
                    }
                }
            }
            else
            {
                throw new AdalException(AdalErrorAndroidEx.NoBrokerAccountFound, "Add requested account as a Workplace account via Settings->Accounts or set UseBroker=true.");
            }
        }