예제 #1
0
        /// <summary>
        /// Query a service on it's predefined 'ping' endpoint.
        /// </summary>
        private async Task <ServicePingResponse> QueryService(Service service)
        {
            var pingUrl = service.Endpoint.TrimEnd('/') + "/ping";
            var sw      = Stopwatch.StartNew();

            try
            {
                Logger.LogInformation($"{nameof(QueryService)}: Querying '{pingUrl}'...");

                var response = await _webRequest.ExecuteRequest(
                    endpoint : pingUrl,
                    method : HttpMethod.Get,
                    retries : 0);

                sw.Stop();

                Logger.LogInformation($"{nameof(QueryService)}: Service '{service.Identifier}' responded in {sw.Elapsed}");
                return(ServicePingResponse.Create(service.Identifier, sw.ElapsedTicks, IsSuccessStatusCode(response)));
            }
            catch (TaskCanceledException)
            {
                // Exception handling is managed in our IWebRequest service.
            }
            catch (Exception ex)
            {
                Logger.LogError(ex, ErrorMessage(ex));
            }

            string ErrorMessage(Exception ex) => $"{nameof(QueryService)}: Failure querying service '{service.Identifier}' at '{pingUrl}'; {ex.GetBaseException().Message}";

            return(ServicePingResponse.Create(service.Identifier, sw.ElapsedTicks, isSuccessStatusCode: false));
        }
예제 #2
0
        /// <inheritdoc/>
        public ServicePingResponse AddServicePingResponse(string identifier, ServicePingResponse servicePingResponse)
        {
            if (string.IsNullOrEmpty(identifier))
            {
                throw new ArgumentNullException(identifier, "Cannot be null");
            }

            var cacheKey = _serviceStateCacheKey(identifier);

            if (!_cache.TryGetValue(cacheKey, out Queue <ServicePingResponse> cachedResponses))
            {
                throw new Exception($"Cache entry for service '{cacheKey}' not found");
            }

            cachedResponses.Enqueue(servicePingResponse);

            if (cachedResponses.Count > PING_RESPONSE_CACHE_SIZE)
            {
                cachedResponses.TrimExcess();
            }

            return(servicePingResponse);
        }
예제 #3
0
        /// <inheritdoc/>
        public IEnumerable <ServicePingResponse> GetServiceState(params string[] identifiers)
        {
            if (identifiers == null || identifiers.Length == 0)
            {
                throw new ArgumentNullException("Service identifier cannot be null or empty");
            }

            var response = new ServicePingResponse[identifiers.Length];

            for (var i = 0; i < identifiers.Length; i++)
            {
                var serviceCacheExists = _cache.TryGetValue(_serviceStateCacheKey(identifiers[i]), out Queue <ServicePingResponse> serviceStates);

                if (!serviceCacheExists || serviceStates.Count == 0)
                {
                    continue;
                }

                // Return the last, most recent ping response.
                response[i] = serviceStates.Last();
            }

            return(response);
        }