/// <summary>
        /// Get Authorization Url
        /// </summary>
        /// <param name="scopes"></param>
        /// <returns></returns>
        public string GetAuthorizationURL(List <OidcScopes> scopes)
        {
            if (string.IsNullOrEmpty(DiscoveryDoc.AuthorizeEndpoint))
            {
                throw new System.Exception("Discovery Call failed. Authorize Endpoint is empty.");
            }

            AdvancedLoggerEnabled = true;
            //Set internal property to track only informational -intuit_tid based logs
            if (EnableAdvancedLoggerInfoMode == true)
            {
                ShowInfoLogs = true;
            }

            //Intialize Logger
            AdvancedLogger = LogHelper.GetAdvancedLogging(enableSerilogRequestResponseLoggingForDebug: this.EnableSerilogRequestResponseLoggingForDebug, enableSerilogRequestResponseLoggingForTrace: this.EnableSerilogRequestResponseLoggingForTrace, enableSerilogRequestResponseLoggingForConsole: this.EnableSerilogRequestResponseLoggingForConsole, enableSerilogRequestResponseLoggingForRollingFile: this.EnableSerilogRequestResponseLoggingForRollingFile, serviceRequestLoggingLocationForFile: this.ServiceRequestLoggingLocationForFile);



            string scopeValue = "";

            for (var index = 0; index < scopes.Count; index++)
            {
                scopeValue += scopes[index].GetStringValue() + " ";
            }
            scopeValue = scopeValue.TrimEnd();

            //creating CSRF token since client did not send one
            CSRFToken = GenerateCSRFToken();

            //builiding authorization request
            string authorizationRequest = string.Format("{0}?client_id={1}&response_type=code&scope={2}&redirect_uri={3}&state={4}",
                                                        DiscoveryDoc.AuthorizeEndpoint,
                                                        ClientID,
                                                        Uri.EscapeDataString(scopeValue),
                                                        Uri.EscapeDataString(RedirectURI),
                                                        CSRFToken);

            //Logging authorization request
            AdvancedLogger.Log("Logging AuthorizationRequest:" + authorizationRequest);

            return(authorizationRequest);
        }
        ///// <summary>
        ///// Get Authorization Url
        ///// </summary>
        ///// <param name="scopes"></param>
        ///// <param name="CSRFToken"></param>
        ///// <param name="getRealmId"></param>
        ///// <returns></returns>
        //public string GetAuthorizationURL(List<OidcScopes> scopes, string CSRFToken, bool getRealmId )
        //{
        //    string scopeValue = "";
        //    string realmIdJson = OidcConstants.AuthorizeRequest.IdToken_ReamId;
        //    string authorizationRequest = "";
        //    for (var index = 0; index < scopes.Count; index++)
        //    {
        //        scopeValue += scopes[index].GetStringValue() + " ";
        //    }
        //    scopeValue = scopeValue.TrimEnd();
        //    this.CSRFToken = CSRFToken;
        //    if (getRealmId == true)
        //    {
        //        authorizationRequest = string.Format("{0}?client_id={1}&response_type=code&scope={2}&redirect_uri={3}&state={4}&claims={5}",
        //            DiscoveryDoc.AuthorizeEndpoint,
        //            ClientID,
        //            Uri.EscapeDataString(scopeValue),
        //            Uri.EscapeDataString(RedirectURI),
        //            Uri.EscapeDataString(realmIdJson),
        //            CSRFToken);
        //    }
        //    else
        //    {
        //        authorizationRequest = string.Format("{0}?client_id={1}&response_type=code&scope={2}&redirect_uri={3}&state={4}",
        //            DiscoveryDoc.AuthorizeEndpoint,
        //            ClientID,
        //            Uri.EscapeDataString(scopeValue),
        //            Uri.EscapeDataString(RedirectURI),
        //            CSRFToken);
        //    }
        //    return authorizationRequest;
        //}

        ///// <summary>
        ///// Get Authorization Url
        ///// </summary>
        ///// <param name="scopes"></param>
        ///// <param name="CSRFToken"></param>
        ///// <param name="getRealmId"></param>
        ///// <returns></returns>
        //public string GetAuthorizationURL(List<OidcScopes> scopes, bool getRealmId)
        //{
        //    string scopeValue = "";
        //    string realmIdJson = OidcConstants.AuthorizeRequest.IdToken_ReamId;
        //    string authorizationRequest = "";
        //    for (var index = 0; index < scopes.Count; index++)
        //    {
        //        scopeValue += scopes[index].GetStringValue() + " ";
        //    }
        //    scopeValue = scopeValue.TrimEnd();
        //    this.CSRFToken = GenerateCSRFToken();
        //    if (getRealmId == true)
        //    {
        //        authorizationRequest = string.Format("{0}?client_id={1}&response_type=code&scope={2}&redirect_uri={3}&state={4}&claims={5}",
        //            DiscoveryDoc.AuthorizeEndpoint,
        //            ClientID,
        //            Uri.EscapeDataString(scopeValue),
        //            Uri.EscapeDataString(RedirectURI),
        //            Uri.EscapeDataString(realmIdJson),
        //            CSRFToken);
        //    }
        //    else
        //    {
        //        authorizationRequest = string.Format("{0}?client_id={1}&response_type=code&scope={2}&redirect_uri={3}&state={4}",
        //            DiscoveryDoc.AuthorizeEndpoint,
        //            ClientID,
        //            Uri.EscapeDataString(scopeValue),
        //            Uri.EscapeDataString(RedirectURI),
        //            CSRFToken);
        //    }
        //    return authorizationRequest;
        //}


        ///// <summary>
        ///// Validates ID token
        ///// </summary>
        ///// <param name="idToken"></param>
        ///// <returns></returns>
        //public string GetRealmIdFromIDTokenAsync(string idToken)
        //{

        //    if (idToken != null)
        //    {
        //        string[] splitValues = idToken.Split('.');


        //        if (splitValues[1] != null)
        //        {
        //            var payloadJson = Encoding.UTF8.GetString(Base64Url.Decode(splitValues[1].ToString()));
        //            IdTokenJWTClaimTypes payloadData = JsonConvert.DeserializeObject<IdTokenJWTClaimTypes>(payloadJson);

        //            if (payloadData.RealmId != null)
        //            {
        //                return payloadData.RealmId.ToString();
        //            }

        //        }

        //    }

        //    return null;

        //}

        #endregion



        /// <summary>
        /// Gets Bearer token from Authorization code
        /// </summary>
        /// <param name="code"></param>
        /// <param name="cancellationToken"></param>
        /// <returns></returns>
        public async Task <TokenResponse> GetBearerTokenAsync(string code, CancellationToken cancellationToken = default(CancellationToken))
        {
            if (string.IsNullOrEmpty(DiscoveryDoc.TokenEndpoint))
            {
                AdvancedLogger.Log("Discovery Call failed.BearerToken Endpoint is empty.");
                return(new TokenResponse(HttpStatusCode.InternalServerError, "Discovery Call failed. BearerToken Endpoint is empty."));
            }

            AdvancedLoggerEnabled = true;
            //Set internal property to track only informational -intuit_tid based logs
            if (EnableAdvancedLoggerInfoMode == true)
            {
                ShowInfoLogs = true;
            }
            //Intialize Logger
            AdvancedLogger = LogHelper.GetAdvancedLogging(enableSerilogRequestResponseLoggingForDebug: this.EnableSerilogRequestResponseLoggingForDebug, enableSerilogRequestResponseLoggingForTrace: this.EnableSerilogRequestResponseLoggingForTrace, enableSerilogRequestResponseLoggingForConsole: this.EnableSerilogRequestResponseLoggingForConsole, enableSerilogRequestResponseLoggingForRollingFile: this.EnableSerilogRequestResponseLoggingForRollingFile, serviceRequestLoggingLocationForFile: this.ServiceRequestLoggingLocationForFile);



            var tokenClient = new TokenClient(DiscoveryDoc.TokenEndpoint, ClientID, ClientSecret);

            return(await tokenClient.RequestTokenFromCodeAsync(code, RedirectURI, cancellationToken : cancellationToken).ConfigureAwait(false));
        }