//Token _token;
        /// <summary>
        /// Generates a token using the username and password set for this provider.
        /// </summary>
        /// <returns>The generated token or null if not applicable</returns>
        /// <remarks>This sets the Token property for the provider. It will be auto appended to
        /// any requests sent through the gateway used by this provider.</remarks>
        public async Task <Token> CheckGenerateToken(CancellationToken ct = default(CancellationToken))
        {
            if (TokenRequest == null)
            {
                return(null);
            }

            if (_token != null && !_token.IsExpired)
            {
                return(_token);
            }

            _token     = null; // reset the Token
            _publicKey = null;

            CheckRefererHeader();

            var  url      = TokenRequest.BuildAbsoluteUrl(RootUrl).Split('?').FirstOrDefault();
            bool validUrl = Uri.TryCreate(url, UriKind.Absolute, out Uri uri);

            if (!validUrl)
            {
                throw new HttpRequestException(string.Format("Not a valid url: {0}", url));
            }
            _logger.DebugFormat("Token request {0}", uri.AbsoluteUri);

            if (CryptoProvider != null && _publicKey == null && CanAccessPublicKeyEndpoint)
            {
                var publicKey = new PublicKey();
                var encryptionInfoEndpoint = publicKey.BuildAbsoluteUrl(RootUrl) + PortalGatewayBase.AsRequestQueryString(Serializer, publicKey);
                _logger.DebugFormat("Encrypted token request {0}", encryptionInfoEndpoint);

                string publicKeyResultString = null;
                try
                {
                    if (CancelPendingRequests)
                    {
                        _httpClient.CancelPendingRequests();
                    }
                    HttpResponseMessage response = await _httpClient.GetAsync(encryptionInfoEndpoint, ct).ConfigureAwait(false);

                    response.EnsureSuccessStatusCode();
                    publicKeyResultString = await response.Content.ReadAsStringAsync().ConfigureAwait(false);
                }
                catch (TaskCanceledException tce)
                {
                    _logger.WarnException("Token request cancelled (exception swallowed)", tce);
                    return(default(Token));
                }
                catch (HttpRequestException hex)
                {
                    _logger.WarnException("Token request exception (exception swallowed)", hex);
                    CanAccessPublicKeyEndpoint = false;
                }

                if (ct.IsCancellationRequested)
                {
                    return(null);
                }

                if (CanAccessPublicKeyEndpoint)
                {
                    _publicKey = Serializer.AsPortalResponse <PublicKeyResponse>(publicKeyResultString);
                    if (_publicKey.Error != null)
                    {
                        throw new InvalidOperationException(_publicKey.Error.ToString());
                    }

                    TokenRequest = CryptoProvider.Encrypt(TokenRequest, _publicKey.Exponent, _publicKey.Modulus);
                }
            }

            if (ct.IsCancellationRequested)
            {
                return(null);
            }

            HttpContent content = new FormUrlEncodedContent(Serializer.AsDictionary(TokenRequest));

            if (CancelPendingRequests)
            {
                _httpClient.CancelPendingRequests();
            }

            string resultString = string.Empty;

            try
            {
                _logger.DebugFormat("HTTP call: {0} {1}", uri, content);
                HttpResponseMessage response = await _httpClient.PostAsync(uri, content, ct).ConfigureAwait(false);

                response.EnsureSuccessStatusCode();

                resultString = await response.Content.ReadAsStringAsync().ConfigureAwait(false);

                _logger.DebugFormat("HTTP call response: {0}", resultString);
            }
            catch (TaskCanceledException tce)
            {
                _logger.WarnException("Token request cancelled (exception swallowed)", tce);
                return(default(Token));
            }
            catch (Exception ex)
            {
                _logger.ErrorException("Token request failed", ex);
                return(default(Token));
            }
            // TODO ; add verbose logging
            Token result = null;

            try
            {
                result = Serializer.AsPortalResponse <Token>(resultString);
            }
            catch (Exception ex)
            {
                _logger.WarnException("unable to deserialize token", ex);
                return(default(Token));
            }

            if (result?.Error != null)
            {
                throw new InvalidOperationException(result.Error.ToString());
            }

            if (!string.IsNullOrWhiteSpace(TokenRequest.Referer))
            {
                result.Referer = TokenRequest.Referer;
            }

            _token = result;
            return(_token);
        }
Exemplo n.º 2
0
        //Token _token;
        /// <summary>
        /// Generates a token using the username and password set for this provider.
        /// </summary>
        /// <returns>The generated token or null if not applicable</returns>
        /// <remarks>This sets the Token property for the provider. It will be auto appended to
        /// any requests sent through the gateway used by this provider.</remarks>
        public async Task <Token> CheckGenerateToken(CancellationToken ct)
        {
            if (TokenRequest == null)
            {
                return(null);
            }

            if (_token != null && !_token.IsExpired)
            {
                return(_token);
            }

            _token     = null; // reset the Token
            _publicKey = null;

            CheckRefererHeader();

            var  url = TokenRequest.BuildAbsoluteUrl(RootUrl).Split('?').FirstOrDefault();
            Uri  uri;
            bool validUrl = Uri.TryCreate(url, UriKind.Absolute, out uri);

            if (!validUrl)
            {
                throw new HttpRequestException(String.Format("Not a valid url: {0}", url));
            }

            if (CryptoProvider != null && _publicKey == null && CanAccessPublicKeyEndpoint)
            {
                var publicKey = new PublicKey();
                var encryptionInfoEndpoint = publicKey.BuildAbsoluteUrl(RootUrl) + PortalGateway.AsRequestQueryString(Serializer, publicKey);

                String publicKeyResultString = null;
                try
                {
                    _httpClient.CancelPendingRequests();
                    HttpResponseMessage response = await _httpClient.GetAsync(encryptionInfoEndpoint, ct);

                    response.EnsureSuccessStatusCode();
                    publicKeyResultString = await response.Content.ReadAsStringAsync();
                }
                catch (TaskCanceledException cex)
                {
                    System.Diagnostics.Debug.WriteLine(cex.ToString());
                    return(null);
                }
                catch (HttpRequestException ex)
                {
                    CanAccessPublicKeyEndpoint = false;
                    System.Diagnostics.Debug.WriteLine("Public Key access failed for " + encryptionInfoEndpoint + ". " + ex.ToString());
                }

                if (ct.IsCancellationRequested)
                {
                    return(null);
                }

                if (CanAccessPublicKeyEndpoint)
                {
                    _publicKey = Serializer.AsPortalResponse <PublicKeyResponse>(publicKeyResultString);
                    if (_publicKey.Error != null)
                    {
                        throw new InvalidOperationException(_publicKey.Error.ToString());
                    }

                    TokenRequest = CryptoProvider.Encrypt(TokenRequest, _publicKey.Exponent, _publicKey.Modulus);
                }
            }

            if (ct.IsCancellationRequested)
            {
                return(null);
            }
            HttpContent content = new FormUrlEncodedContent(Serializer.AsDictionary(TokenRequest));

            _httpClient.CancelPendingRequests();

            String resultString = String.Empty;

            try
            {
                HttpResponseMessage response = await _httpClient.PostAsync(uri, content, ct);

                response.EnsureSuccessStatusCode();

                resultString = await response.Content.ReadAsStringAsync();
            }
            catch (TaskCanceledException cex)
            {
                System.Diagnostics.Debug.WriteLine(cex.ToString());
                return(null);
            }
            catch (HttpRequestException)
            {
                throw;
            }

            System.Diagnostics.Debug.WriteLine("Generate token result: " + resultString);
            var result = Serializer.AsPortalResponse <Token>(resultString);

            if (result.Error != null)
            {
                throw new InvalidOperationException(result.Error.ToString());
            }

            if (!String.IsNullOrWhiteSpace(TokenRequest.Referer))
            {
                result.Referer = TokenRequest.Referer;
            }

            _token = result;
            return(_token);
        }