public bool?Ping(
            string instrumentationKey,
            DateTimeOffset timestamp,
            string configurationETag,
            string authApiKey,
            out CollectionConfigurationInfo configurationInfo)
        {
            lock (this.ResponseLock)
            {
                if (this.CountersEnabled)
                {
                    lock (this.countersLock)
                    {
                        this.PingCount++;
                        this.LastPingTimestamp = timestamp;
                        this.LastAuthApiKey    = authApiKey;
                    }
                }

                if (this.AlwaysThrow)
                {
                    throw new InvalidOperationException("Mock is set to always throw");
                }

                configurationInfo = this.CollectionConfigurationInfo?.ETag == configurationETag ? null : this.CollectionConfigurationInfo;

                return(this.ReturnValueFromPing);
            }
        }
        public void CollectionConfigurationAccumulatorPreparesMetricAccumulatorsTest()
        {
            // ARRANGE
            CollectionConfigurationError[] error;
            var metricInfo = new CalculatedMetricInfo()
            {
                Id            = "Metric1",
                TelemetryType = TelemetryType.Request,
                Projection    = "Name",
                Aggregation   = AggregationType.Min,
                FilterGroups  = new FilterConjunctionGroupInfo[0]
            };

            var collectionConfigurationInfo = new CollectionConfigurationInfo()
            {
                Metrics = new[] { metricInfo }
            };
            var collectionConfiguration = new CollectionConfiguration(collectionConfigurationInfo, out error, new ClockMock());

            // ACT
            var accumulator = new CollectionConfigurationAccumulator(collectionConfiguration);

            // ASSERT
            Assert.AreSame(collectionConfiguration, accumulator.CollectionConfiguration);
            Assert.AreEqual("Metric1", accumulator.MetricAccumulators.Single().Key);
        }
        public bool?SubmitSamples(
            IEnumerable <QuickPulseDataSample> samples,
            string instrumentationKey,
            string configurationETag,
            string authApiKey,
            out CollectionConfigurationInfo configurationInfo,
            CollectionConfigurationError[] collectionConfigurationErrors)
        {
            lock (this.ResponseLock)
            {
                if (this.CountersEnabled)
                {
                    lock (this.countersLock)
                    {
                        this.batches.Add(samples.Count());
                        this.LastSampleBatchSize = samples.Count();
                        this.samples.AddRange(samples);
                        this.LastAuthApiKey = authApiKey;
                    }
                }

                if (this.AlwaysThrow)
                {
                    throw new InvalidOperationException("Mock is set to always throw");
                }

                configurationInfo = this.CollectionConfigurationInfo?.ETag == configurationETag ? null : this.CollectionConfigurationInfo;
                this.CollectionConfigurationErrors = collectionConfigurationErrors;

                return(this.ReturnValueFromSubmitSample);
            }
        }
        private void UpdateConfiguration(CollectionConfigurationInfo configurationInfo)
        {
            // we only get here if Etag in the header is different from the current one, but we still want to check if Etag in the body is also different
            if (configurationInfo != null && !string.Equals(configurationInfo.ETag, this.currentConfigurationETag, StringComparison.Ordinal))
            {
                QuickPulseEventSource.Log.CollectionConfigurationUpdating(this.currentConfigurationETag, configurationInfo.ETag, string.Empty);

                this.collectionConfigurationErrors.Clear();

                CollectionConfigurationError[] errors = null;
                try
                {
                    errors = this.onUpdatedConfiguration?.Invoke(configurationInfo);
                }
                catch (Exception e)
                {
                    QuickPulseEventSource.Log.CollectionConfigurationUpdateFailed(this.currentConfigurationETag, configurationInfo.ETag, e.ToInvariantString(), string.Empty);

                    this.collectionConfigurationErrors.Add(
                        CollectionConfigurationError.CreateError(
                            CollectionConfigurationErrorType.CollectionConfigurationFailureToCreateUnexpected,
                            string.Format(CultureInfo.InvariantCulture, "Unexpected error applying configuration. ETag: {0}", configurationInfo.ETag ?? string.Empty),
                            e,
                            Tuple.Create("ETag", configurationInfo.ETag)));
                }

                if (errors != null)
                {
                    this.collectionConfigurationErrors.AddRange(errors);
                }

                this.currentConfigurationETag = configurationInfo.ETag;
            }
        }
        private CollectionConfigurationError[] OnUpdatedConfiguration(CollectionConfigurationInfo configurationInfo)
        {
            // we need to preserve the current quota for each document stream that still exists in the new configuration
            CollectionConfigurationError[] errorsConfig;
            var newCollectionConfiguration = new CollectionConfiguration(configurationInfo, out errorsConfig, this.timeProvider, this.collectionConfiguration?.DocumentStreams);

            // the next accumulator that gets swapped in on the collection thread will be initialized with the new collection configuration
            Interlocked.Exchange(ref this.collectionConfiguration, newCollectionConfiguration);

            CollectionConfigurationError[] errorsPerformanceCounters;
            this.UpdatePerformanceCollector(newCollectionConfiguration.PerformanceCounters, out errorsPerformanceCounters);

            return(errorsConfig.Concat(errorsPerformanceCounters).ToArray());
        }
        public void CollectionConfigurationReportsInvalidFilterForDocumentStreams()
        {
            // ARRANGE
            CollectionConfigurationError[] errors;
            var documentStreamInfos = new[]
            {
                new DocumentStreamInfo()
                {
                    Id = "Stream1",
                    DocumentFilterGroups =
                        new[]
                    {
                        new DocumentFilterConjunctionGroupInfo()
                        {
                            TelemetryType = TelemetryType.Request,
                            Filters       = new FilterConjunctionGroupInfo()
                            {
                                Filters = new[] { new FilterInfo()
                                                  {
                                                      FieldName = "NonExistentFieldName"
                                                  } }
                            }
                        }
                    }
                }
            };

            var collectionConfigurationInfo = new CollectionConfigurationInfo()
            {
                DocumentStreams = documentStreamInfos, ETag = "ETag1"
            };

            // ACT
            var collectionConfiguration = new CollectionConfiguration(collectionConfigurationInfo, out errors, new ClockMock());

            // ASSERT
            Assert.AreEqual(1, collectionConfiguration.DocumentStreams.Count());

            Assert.AreEqual(CollectionConfigurationErrorType.FilterFailureToCreateUnexpected, errors.Single().ErrorType);
            Assert.AreEqual("Failed to create a filter NonExistentFieldName Equal .", errors.Single().Message);
            Assert.IsTrue(errors.Single().FullException.Contains("Comparand"));
            Assert.AreEqual(5, errors.Single().Data.Count);
            Assert.AreEqual("Stream1", errors.Single().Data["DocumentStreamId"]);
            Assert.AreEqual("ETag1", errors.Single().Data["ETag"]);
            Assert.AreEqual("NonExistentFieldName", errors.Single().Data["FilterFieldName"]);
            Assert.AreEqual(Predicate.Equal.ToString(), errors.Single().Data["FilterPredicate"]);
            Assert.AreEqual(null, errors.Single().Data["FilterComparand"]);
        }
示例#7
0
        private bool?SendRequest(
            string requestUri,
            bool includeIdentityHeaders,
            string configurationETag,
            string authApiKey,
            out CollectionConfigurationInfo configurationInfo,
            Action <Stream> onWriteRequestBody)
        {
            try
            {
                using (HttpRequestMessage request = new HttpRequestMessage(HttpMethod.Post, requestUri))
                {
                    this.AddHeaders(request, includeIdentityHeaders, configurationETag, authApiKey);

                    using (MemoryStream stream = new MemoryStream())
                    {
                        onWriteRequestBody(stream);
                        stream.Flush();
                        ArraySegment <byte> buffer = stream.TryGetBuffer(out buffer) ? buffer : new ArraySegment <byte>();
                        request.Content = new ByteArrayContent(buffer.Array, buffer.Offset, buffer.Count);

                        using (var cancellationToken = new CancellationTokenSource(this.timeout))
                        {
                            HttpResponseMessage response = this.httpClient.SendAsync(request, cancellationToken.Token).GetAwaiter().GetResult();
                            if (response == null)
                            {
                                configurationInfo = null;
                                return(null);
                            }

                            return(this.ProcessResponse(response, configurationETag, out configurationInfo));
                        }
                    }
                }
            }
            catch (Exception e)
            {
                QuickPulseEventSource.Log.ServiceCommunicationFailedEvent(e.ToInvariantString());
            }

            configurationInfo = null;
            return(null);
        }
        public void CollectionConfigurationReportsInvalidFilterGroupForDocumentStreams()
        {
            // ARRANGE
            CollectionConfigurationError[] errors;
            var documentStreamInfos = new[]
            {
                new DocumentStreamInfo()
                {
                    Id = "Stream1",
                    DocumentFilterGroups =
                        new[]
                    {
                        new DocumentFilterConjunctionGroupInfo()
                        {
                            TelemetryType = (TelemetryType)505,
                            Filters       = new FilterConjunctionGroupInfo()
                            {
                                Filters = new FilterInfo[0]
                            }
                        }
                    }
                }
            };

            var collectionConfigurationInfo = new CollectionConfigurationInfo()
            {
                DocumentStreams = documentStreamInfos, ETag = "ETag1"
            };

            // ACT
            var collectionConfiguration = new CollectionConfiguration(collectionConfigurationInfo, out errors, new ClockMock());

            // ASSERT
            Assert.AreEqual(1, collectionConfiguration.DocumentStreams.Count());

            Assert.AreEqual(CollectionConfigurationErrorType.DocumentStreamFailureToCreateFilterUnexpected, errors.Single().ErrorType);
            Assert.AreEqual("Failed to create a document stream filter TelemetryType: '505', filters: ''.", errors.Single().Message);
            Assert.IsTrue(errors.Single().FullException.Contains("Unsupported TelemetryType: '505'"));
            Assert.AreEqual(2, errors.Single().Data.Count);
            Assert.AreEqual("Stream1", errors.Single().Data["DocumentStreamId"]);
            Assert.AreEqual("ETag1", errors.Single().Data["ETag"]);
        }
        public bool?Ping(
            string instrumentationKey,
            DateTimeOffset timestamp,
            string configurationETag,
            string authApiKey,
            out CollectionConfigurationInfo configurationInfo)
        {
            var requestUri = string.Format(
                CultureInfo.InvariantCulture,
                "{0}/ping?ikey={1}",
                this.ServiceUri.AbsoluteUri.TrimEnd('/'),
                Uri.EscapeUriString(instrumentationKey));

            return(this.SendRequest(
                       requestUri,
                       true,
                       configurationETag,
                       authApiKey,
                       out configurationInfo,
                       requestStream => this.WritePingData(timestamp, requestStream)));
        }
示例#10
0
        private bool?SendRequest(
            string requestUri,
            bool includeIdentityHeaders,
            string configurationETag,
            string authApiKey,
            out CollectionConfigurationInfo configurationInfo,
            Action <Stream> onWriteRequestBody)
        {
            try
            {
                HttpWebRequest request = WebRequest.Create(new Uri(requestUri)) as HttpWebRequest;
                request.Method  = "POST";
                request.Timeout = (int)this.timeout.TotalMilliseconds;

                this.AddHeaders(request, includeIdentityHeaders, configurationETag, authApiKey);

                using (Stream requestStream = request.GetRequestStream())
                {
                    onWriteRequestBody(requestStream);

                    using (HttpWebResponse response = request.GetResponse() as HttpWebResponse)
                    {
                        if (response == null)
                        {
                            configurationInfo = null;
                            return(null);
                        }

                        return(this.ProcessResponse(response, configurationETag, out configurationInfo));
                    }
                }
            }
            catch (Exception e)
            {
                QuickPulseEventSource.Log.ServiceCommunicationFailedEvent(e.ToInvariantString());
            }

            configurationInfo = null;
            return(null);
        }
        public bool?SubmitSamples(
            IEnumerable <QuickPulseDataSample> samples,
            string instrumentationKey,
            string configurationETag,
            string authApiKey,
            out CollectionConfigurationInfo configurationInfo,
            CollectionConfigurationError[] collectionConfigurationErrors)
        {
            var requestUri = string.Format(
                CultureInfo.InvariantCulture,
                "{0}/post?ikey={1}",
                this.ServiceUri.AbsoluteUri.TrimEnd('/'),
                Uri.EscapeUriString(instrumentationKey));

            return(this.SendRequest(
                       requestUri,
                       false,
                       configurationETag,
                       authApiKey,
                       out configurationInfo,
                       requestStream => this.WriteSamples(samples, instrumentationKey, requestStream, collectionConfigurationErrors)));
        }
        public void CollectionConfigurationReportsDocumentStreamsWithDuplicateIds()
        {
            // ARRANGE
            CollectionConfigurationError[] errors;
            var documentStreamInfos = new[]
            {
                new DocumentStreamInfo()
                {
                    Id = "Stream1",
                    DocumentFilterGroups =
                        new[]
                    {
                        new DocumentFilterConjunctionGroupInfo()
                        {
                            TelemetryType = TelemetryType.Request,
                            Filters       = new FilterConjunctionGroupInfo()
                            {
                                Filters = new FilterInfo[0]
                            }
                        }
                    }
                },
                new DocumentStreamInfo()
                {
                    Id = "Stream1",
                    DocumentFilterGroups =
                        new[]
                    {
                        new DocumentFilterConjunctionGroupInfo()
                        {
                            TelemetryType = TelemetryType.Dependency,
                            Filters       = new FilterConjunctionGroupInfo()
                            {
                                Filters = new FilterInfo[0]
                            }
                        }
                    }
                },
                new DocumentStreamInfo()
                {
                    Id = "Stream2",
                    DocumentFilterGroups =
                        new[]
                    {
                        new DocumentFilterConjunctionGroupInfo()
                        {
                            TelemetryType = TelemetryType.Dependency,
                            Filters       = new FilterConjunctionGroupInfo()
                            {
                                Filters = new FilterInfo[0]
                            }
                        }
                    }
                }
            };

            var collectionConfigurationInfo = new CollectionConfigurationInfo()
            {
                DocumentStreams = documentStreamInfos, ETag = "ETag1"
            };

            // ACT
            var collectionConfiguration = new CollectionConfiguration(collectionConfigurationInfo, out errors, new ClockMock());

            // ASSERT
            Assert.AreEqual(2, collectionConfiguration.DocumentStreams.Count());
            Assert.AreEqual("Stream1", collectionConfiguration.DocumentStreams.First().Id);
            Assert.AreEqual("Stream2", collectionConfiguration.DocumentStreams.Last().Id);

            Assert.AreEqual(CollectionConfigurationErrorType.DocumentStreamDuplicateIds, errors.Single().ErrorType);
            Assert.AreEqual("Document stream with a duplicate id ignored: Stream1", errors.Single().Message);
            Assert.AreEqual(string.Empty, errors.Single().FullException);
            Assert.AreEqual(2, errors.Single().Data.Count);
            Assert.AreEqual("Stream1", errors.Single().Data["DocumentStreamId"]);
            Assert.AreEqual("ETag1", errors.Single().Data["ETag"]);
        }
        public void CollectionConfigurationCarriesOverQuotaWhenCreatingDocumentStreams()
        {
            // ARRANGE
            var timeProvider = new ClockMock();

            CollectionConfigurationError[] errors;
            var oldDocumentStreamInfos = new[]
            {
                new DocumentStreamInfo()
                {
                    Id = "Stream1",
                    DocumentFilterGroups =
                        new[]
                    {
                        new DocumentFilterConjunctionGroupInfo()
                        {
                            TelemetryType = TelemetryType.Request,
                            Filters       = new FilterConjunctionGroupInfo()
                            {
                                Filters = new FilterInfo[0]
                            }
                        }
                    }
                },
                new DocumentStreamInfo()
                {
                    Id = "Stream2",
                    DocumentFilterGroups =
                        new[]
                    {
                        new DocumentFilterConjunctionGroupInfo()
                        {
                            TelemetryType = TelemetryType.Dependency,
                            Filters       = new FilterConjunctionGroupInfo()
                            {
                                Filters = new FilterInfo[0]
                            }
                        }
                    }
                },
                new DocumentStreamInfo()
                {
                    Id = "Stream3",
                    DocumentFilterGroups =
                        new[]
                    {
                        new DocumentFilterConjunctionGroupInfo()
                        {
                            TelemetryType = TelemetryType.Exception,
                            Filters       = new FilterConjunctionGroupInfo()
                            {
                                Filters = new FilterInfo[0]
                            }
                        }
                    }
                }
            };

            var newDocumentStreamInfos = new[]
            {
                new DocumentStreamInfo()
                {
                    Id = "Stream1",
                    DocumentFilterGroups =
                        new[]
                    {
                        new DocumentFilterConjunctionGroupInfo()
                        {
                            TelemetryType = TelemetryType.Request,
                            Filters       = new FilterConjunctionGroupInfo()
                            {
                                Filters = new FilterInfo[0]
                            }
                        }
                    }
                },
                new DocumentStreamInfo()
                {
                    Id = "Stream2",
                    DocumentFilterGroups =
                        new[]
                    {
                        new DocumentFilterConjunctionGroupInfo()
                        {
                            TelemetryType = TelemetryType.Dependency,
                            Filters       = new FilterConjunctionGroupInfo()
                            {
                                Filters = new FilterInfo[0]
                            }
                        }
                    }
                },
                new DocumentStreamInfo()
                {
                    Id = "Stream3",
                    DocumentFilterGroups =
                        new[]
                    {
                        new DocumentFilterConjunctionGroupInfo()
                        {
                            TelemetryType = TelemetryType.Exception,
                            Filters       = new FilterConjunctionGroupInfo()
                            {
                                Filters = new FilterInfo[0]
                            }
                        }
                    }
                },
                new DocumentStreamInfo()
                {
                    Id = "Stream4",
                    DocumentFilterGroups =
                        new[]
                    {
                        new DocumentFilterConjunctionGroupInfo()
                        {
                            TelemetryType = TelemetryType.Event,
                            Filters       = new FilterConjunctionGroupInfo()
                            {
                                Filters = new FilterInfo[0]
                            }
                        }
                    }
                },
                new DocumentStreamInfo()
                {
                    Id = "Stream5",
                    DocumentFilterGroups =
                        new[]
                    {
                        new DocumentFilterConjunctionGroupInfo()
                        {
                            TelemetryType = TelemetryType.Trace,
                            Filters       = new FilterConjunctionGroupInfo()
                            {
                                Filters = new FilterInfo[0]
                            }
                        }
                    }
                }
            };

            var oldCollectionConfigurationInfo = new CollectionConfigurationInfo()
            {
                DocumentStreams = oldDocumentStreamInfos, ETag = "ETag1"
            };
            var oldCollectionConfiguration = new CollectionConfiguration(oldCollectionConfigurationInfo, out errors, timeProvider);

            // spend some quota on the old configuration
            var accumulatorManager = new QuickPulseDataAccumulatorManager(oldCollectionConfiguration);
            var telemetryProcessor = new QuickPulseTelemetryProcessor(new SimpleTelemetryProcessorSpy());

            ((IQuickPulseTelemetryProcessor)telemetryProcessor).StartCollection(
                accumulatorManager,
                new Uri("http://microsoft.com"),
                new TelemetryConfiguration()
            {
                InstrumentationKey = "some ikey"
            });

            // ACT
            // the initial quota is 3
            telemetryProcessor.Process(new RequestTelemetry()
            {
                Context = { InstrumentationKey = "some ikey" }
            });

            telemetryProcessor.Process(new DependencyTelemetry()
            {
                Context = { InstrumentationKey = "some ikey" }
            });
            telemetryProcessor.Process(new DependencyTelemetry()
            {
                Context = { InstrumentationKey = "some ikey" }
            });

            telemetryProcessor.Process(new ExceptionTelemetry()
            {
                Context = { InstrumentationKey = "some ikey" }
            });
            telemetryProcessor.Process(new ExceptionTelemetry()
            {
                Context = { InstrumentationKey = "some ikey" }
            });
            telemetryProcessor.Process(new ExceptionTelemetry()
            {
                Context = { InstrumentationKey = "some ikey" }
            });

            // ACT
            // the new configuration must carry the quotas over from the old one (only for those document streams that already existed)
            var newCollectionConfigurationInfo = new CollectionConfigurationInfo()
            {
                DocumentStreams = newDocumentStreamInfos, ETag = "ETag1"
            };
            var newCollectionConfiguration = new CollectionConfiguration(
                newCollectionConfigurationInfo,
                out errors,
                timeProvider,
                oldCollectionConfiguration.DocumentStreams);

            // ASSERT
            DocumentStream[] documentStreams = newCollectionConfiguration.DocumentStreams.ToArray();
            Assert.AreEqual(5, documentStreams.Length);

            Assert.AreEqual("Stream1", documentStreams[0].Id);
            Assert.AreEqual(2, documentStreams[0].RequestQuotaTracker.CurrentQuota);
            Assert.AreEqual(3, documentStreams[0].DependencyQuotaTracker.CurrentQuota);
            Assert.AreEqual(3, documentStreams[0].ExceptionQuotaTracker.CurrentQuota);
            Assert.AreEqual(3, documentStreams[0].EventQuotaTracker.CurrentQuota);
            Assert.AreEqual(3, documentStreams[0].EventQuotaTracker.CurrentQuota);

            Assert.AreEqual("Stream2", documentStreams[1].Id);
            Assert.AreEqual(3, documentStreams[1].RequestQuotaTracker.CurrentQuota);
            Assert.AreEqual(1, documentStreams[1].DependencyQuotaTracker.CurrentQuota);
            Assert.AreEqual(3, documentStreams[1].ExceptionQuotaTracker.CurrentQuota);
            Assert.AreEqual(3, documentStreams[1].EventQuotaTracker.CurrentQuota);
            Assert.AreEqual(3, documentStreams[1].EventQuotaTracker.CurrentQuota);

            Assert.AreEqual("Stream3", documentStreams[2].Id);
            Assert.AreEqual(3, documentStreams[2].RequestQuotaTracker.CurrentQuota);
            Assert.AreEqual(3, documentStreams[2].DependencyQuotaTracker.CurrentQuota);
            Assert.AreEqual(0, documentStreams[2].ExceptionQuotaTracker.CurrentQuota);
            Assert.AreEqual(3, documentStreams[2].EventQuotaTracker.CurrentQuota);
            Assert.AreEqual(3, documentStreams[2].EventQuotaTracker.CurrentQuota);

            Assert.AreEqual("Stream4", documentStreams[3].Id);
            Assert.AreEqual(3, documentStreams[3].RequestQuotaTracker.CurrentQuota);
            Assert.AreEqual(3, documentStreams[3].DependencyQuotaTracker.CurrentQuota);
            Assert.AreEqual(3, documentStreams[3].ExceptionQuotaTracker.CurrentQuota);
            Assert.AreEqual(3, documentStreams[3].EventQuotaTracker.CurrentQuota);
            Assert.AreEqual(3, documentStreams[3].EventQuotaTracker.CurrentQuota);
        }
        public void CollectionConfigurationCreatesDocumentStreams()
        {
            // ARRANGE
            CollectionConfigurationError[] errors;
            var documentStreamInfos = new[]
            {
                new DocumentStreamInfo()
                {
                    Id = "Stream1",
                    DocumentFilterGroups =
                        new[]
                    {
                        new DocumentFilterConjunctionGroupInfo()
                        {
                            TelemetryType = TelemetryType.Request,
                            Filters       = new FilterConjunctionGroupInfo()
                            {
                                Filters = new FilterInfo[0]
                            }
                        }
                    }
                },
                new DocumentStreamInfo()
                {
                    Id = "Stream2",
                    DocumentFilterGroups =
                        new[]
                    {
                        new DocumentFilterConjunctionGroupInfo()
                        {
                            TelemetryType = TelemetryType.Dependency,
                            Filters       = new FilterConjunctionGroupInfo()
                            {
                                Filters = new FilterInfo[0]
                            }
                        }
                    }
                },
                new DocumentStreamInfo()
                {
                    Id = "Stream3",
                    DocumentFilterGroups =
                        new[]
                    {
                        new DocumentFilterConjunctionGroupInfo()
                        {
                            TelemetryType = TelemetryType.Exception,
                            Filters       = new FilterConjunctionGroupInfo()
                            {
                                Filters = new FilterInfo[0]
                            }
                        }
                    }
                },
                new DocumentStreamInfo()
                {
                    Id = "Stream4",
                    DocumentFilterGroups =
                        new[]
                    {
                        new DocumentFilterConjunctionGroupInfo()
                        {
                            TelemetryType = TelemetryType.Event,
                            Filters       = new FilterConjunctionGroupInfo()
                            {
                                Filters = new FilterInfo[0]
                            }
                        }
                    }
                }
            };

            var collectionConfigurationInfo = new CollectionConfigurationInfo()
            {
                DocumentStreams = documentStreamInfos, ETag = "ETag1"
            };

            // ACT
            var collectionConfiguration = new CollectionConfiguration(collectionConfigurationInfo, out errors, new ClockMock());

            // ASSERT
            DocumentStream[] documentStreams = collectionConfiguration.DocumentStreams.ToArray();
            Assert.AreEqual(4, documentStreams.Length);
            Assert.AreEqual("Stream1", documentStreams[0].Id);
            Assert.AreEqual("Stream2", documentStreams[1].Id);
            Assert.AreEqual("Stream3", documentStreams[2].Id);
            Assert.AreEqual("Stream4", documentStreams[3].Id);
        }
        private bool?ProcessResponse(HttpResponseMessage response, string configurationETag, out CollectionConfigurationInfo configurationInfo)
        {
            configurationInfo = null;

            bool isSubscribed;

            if (!bool.TryParse(response.Headers.GetValuesSafe(QuickPulseConstants.XMsQpsSubscribedHeaderName).FirstOrDefault(), out isSubscribed))
            {
                // could not parse the isSubscribed value

                // read the response out to avoid issues with TCP connections not being freed up
                try
                {
                    response.Content.LoadIntoBufferAsync().GetAwaiter().GetResult();
                }
                catch (Exception)
                {
                    // we did our best, we don't care about the outcome anyway
                }

                return(null);
            }

            foreach (string headerName in QuickPulseConstants.XMsQpsAuthOpaqueHeaderNames)
            {
                this.authOpaqueHeaderValues[headerName] = response.Headers.GetValuesSafe(headerName).FirstOrDefault();
            }

            string configurationETagHeaderValue = response.Headers.GetValuesSafe(QuickPulseConstants.XMsQpsConfigurationETagHeaderName).FirstOrDefault();

            try
            {
                using (Stream responseStream = response.Content.ReadAsStreamAsync().GetAwaiter().GetResult())
                {
                    if (isSubscribed && !string.IsNullOrEmpty(configurationETagHeaderValue) &&
                        !string.Equals(configurationETagHeaderValue, configurationETag, StringComparison.Ordinal) && responseStream != null)
                    {
                        configurationInfo = this.deserializerServerResponse.ReadObject(responseStream) as CollectionConfigurationInfo;
                    }
                }
            }
            catch (Exception e)
            {
                // couldn't read or deserialize the response
                QuickPulseEventSource.Log.ServiceCommunicationFailedEvent(e.ToInvariantString());
            }

            return(isSubscribed);
        }
示例#16
0
        private void WriteCollectionConfiguration(Stream stream)
        {
            var collectionConfigurationInfo = new CollectionConfigurationInfo()
            {
                ETag    = "Etag1",
                Metrics =
                    new[]
                {
                    new CalculatedMetricInfo()
                    {
                        Id           = "Metric1",
                        Aggregation  = AggregationType.Sum,
                        Projection   = "Count()",
                        FilterGroups =
                            new[]
                        {
                            new FilterConjunctionGroupInfo()
                            {
                                Filters =
                                    new[] { new FilterInfo()
                                            {
                                                FieldName = "Success", Predicate = Predicate.Equal, Comparand = "True"
                                            } }
                            }
                        }
                    }
                },
                DocumentStreams =
                    new[]
                {
                    new DocumentStreamInfo()
                    {
                        Id = "Stream1",
                        DocumentFilterGroups =
                            new[]
                        {
                            new DocumentFilterConjunctionGroupInfo()
                            {
                                TelemetryType = TelemetryType.Request,
                                Filters       = new FilterConjunctionGroupInfo()
                                {
                                    Filters = new FilterInfo[0]
                                }
                            },
                            new DocumentFilterConjunctionGroupInfo()
                            {
                                TelemetryType = TelemetryType.Dependency,
                                Filters       = new FilterConjunctionGroupInfo()
                                {
                                    Filters = new FilterInfo[0]
                                }
                            },
                            new DocumentFilterConjunctionGroupInfo()
                            {
                                TelemetryType = TelemetryType.Exception,
                                Filters       = new FilterConjunctionGroupInfo()
                                {
                                    Filters = new FilterInfo[0]
                                }
                            },
                            new DocumentFilterConjunctionGroupInfo()
                            {
                                TelemetryType = TelemetryType.Event,
                                Filters       = new FilterConjunctionGroupInfo()
                                {
                                    Filters = new FilterInfo[0]
                                }
                            },
                            new DocumentFilterConjunctionGroupInfo()
                            {
                                TelemetryType = TelemetryType.Trace,
                                Filters       = new FilterConjunctionGroupInfo()
                                {
                                    Filters = new FilterInfo[0]
                                }
                            }
                        }
                    }
                }
            };

            var serializerCollectionConfigurationInfo = new DataContractJsonSerializer(typeof(CollectionConfigurationInfo));

            serializerCollectionConfigurationInfo.WriteObject(stream, collectionConfigurationInfo);
        }
        public void CollectionConfigurationReportsMultipleInvalidFiltersAndDocumentStreams()
        {
            // ARRANGE
            CollectionConfigurationError[] errors;
            var documentStreamInfos = new[]
            {
                new DocumentStreamInfo()
                {
                    Id = "Stream1",
                    DocumentFilterGroups =
                        new[]
                    {
                        new DocumentFilterConjunctionGroupInfo()
                        {
                            TelemetryType = (TelemetryType)505,
                            Filters       =
                                new FilterConjunctionGroupInfo()
                            {
                                Filters =
                                    new[]
                                {
                                    new FilterInfo()
                                    {
                                        FieldName = "NonExistentFilterFieldName1"
                                    },
                                    new FilterInfo()
                                    {
                                        FieldName = "NonExistentFilterFieldName2"
                                    }
                                }
                            }
                        }
                    }
                },
                new DocumentStreamInfo()
                {
                    Id = "Stream2",
                    DocumentFilterGroups =
                        new[]
                    {
                        new DocumentFilterConjunctionGroupInfo()
                        {
                            TelemetryType = TelemetryType.Request,
                            Filters       =
                                new FilterConjunctionGroupInfo()
                            {
                                Filters =
                                    new[]
                                {
                                    new FilterInfo()
                                    {
                                        FieldName = "NonExistentFilterFieldName3"
                                    },
                                    new FilterInfo()
                                    {
                                        FieldName = "NonExistentFilterFieldName4"
                                    }
                                }
                            }
                        }
                    }
                }
            };

            var collectionConfigurationInfo = new CollectionConfigurationInfo()
            {
                DocumentStreams = documentStreamInfos, ETag = "ETag1"
            };

            // ACT
            var collectionConfiguration = new CollectionConfiguration(collectionConfigurationInfo, out errors, new ClockMock());

            // ASSERT
            Assert.AreEqual(2, collectionConfiguration.DocumentStreams.Count());
            Assert.AreEqual("Stream1", collectionConfiguration.DocumentStreams.First().Id);
            Assert.AreEqual("Stream2", collectionConfiguration.DocumentStreams.Last().Id);

            Assert.AreEqual(3, errors.Length);

            Assert.AreEqual(CollectionConfigurationErrorType.DocumentStreamFailureToCreateFilterUnexpected, errors[0].ErrorType);
            Assert.AreEqual(
                "Failed to create a document stream filter TelemetryType: '505', filters: 'NonExistentFilterFieldName1 Equal , NonExistentFilterFieldName2 Equal '.",
                errors[0].Message);
            Assert.IsTrue(errors[0].FullException.Contains("Unsupported TelemetryType: '505'"));
            Assert.AreEqual(2, errors[0].Data.Count);
            Assert.AreEqual("Stream1", errors[0].Data["DocumentStreamId"]);
            Assert.AreEqual("ETag1", errors[0].Data["ETag"]);

            Assert.AreEqual(CollectionConfigurationErrorType.FilterFailureToCreateUnexpected, errors[1].ErrorType);
            Assert.AreEqual("Failed to create a filter NonExistentFilterFieldName3 Equal .", errors[1].Message);
            Assert.IsTrue(errors[1].FullException.Contains("Comparand"));
            Assert.AreEqual(5, errors[1].Data.Count);
            Assert.AreEqual("Stream2", errors[1].Data["DocumentStreamId"]);
            Assert.AreEqual("ETag1", errors[1].Data["ETag"]);
            Assert.AreEqual("NonExistentFilterFieldName3", errors[1].Data["FilterFieldName"]);
            Assert.AreEqual(Predicate.Equal.ToString(), errors[1].Data["FilterPredicate"]);
            Assert.AreEqual(null, errors[1].Data["FilterComparand"]);

            Assert.AreEqual(CollectionConfigurationErrorType.FilterFailureToCreateUnexpected, errors[2].ErrorType);
            Assert.AreEqual("Failed to create a filter NonExistentFilterFieldName4 Equal .", errors[2].Message);
            Assert.IsTrue(errors[2].FullException.Contains("Comparand"));
            Assert.AreEqual(5, errors[2].Data.Count);
            Assert.AreEqual("Stream2", errors[2].Data["DocumentStreamId"]);
            Assert.AreEqual("ETag1", errors[2].Data["ETag"]);
            Assert.AreEqual("NonExistentFilterFieldName4", errors[2].Data["FilterFieldName"]);
            Assert.AreEqual(Predicate.Equal.ToString(), errors[2].Data["FilterPredicate"]);
            Assert.AreEqual(null, errors[2].Data["FilterComparand"]);
        }
        public void QuickPulseCollectionStateManagerUpdatesCollectionConfigurationWhenETagChanges()
        {
            // ARRANGE
            var serviceClient = new QuickPulseServiceClientMock {
                ReturnValueFromPing = true, ReturnValueFromSubmitSample = true
            };

            var actions = new List <string>();
            var collectionConfigurationInfos = new List <CollectionConfigurationInfo>();
            var manager = CreateManager(serviceClient, new Clock(), actions, collectionConfigurationInfos: collectionConfigurationInfos);

            var filters = new[]
            {
                new FilterConjunctionGroupInfo()
                {
                    Filters = new[] { new FilterInfo()
                                      {
                                          FieldName = "Name", Predicate = Predicate.Equal, Comparand = "Request1"
                                      } }
                }
            };
            var metrics = new[]
            {
                new CalculatedMetricInfo()
                {
                    Id            = "Metric0",
                    TelemetryType = TelemetryType.Request,
                    Projection    = "Name",
                    Aggregation   = AggregationType.Avg,
                    FilterGroups  = filters
                },
                new CalculatedMetricInfo()
                {
                    Id            = "Metric1",
                    TelemetryType = TelemetryType.Request,
                    Projection    = "Id",
                    Aggregation   = AggregationType.Sum,
                    FilterGroups  = filters
                }
            };

            serviceClient.CollectionConfigurationInfo = new CollectionConfigurationInfo()
            {
                ETag = "1", Metrics = metrics
            };

            manager.UpdateState("empty iKey", string.Empty);
            collectionConfigurationInfos.Clear();

            // ACT
            serviceClient.CollectionConfigurationInfo = new CollectionConfigurationInfo()
            {
                ETag = "2", Metrics = metrics
            };
            manager.UpdateState("empty iKey", string.Empty);

            // ASSERT
            CollectionConfigurationInfo receivedCollectionConfigurationInfo = collectionConfigurationInfos.Single();

            Assert.AreEqual("2", receivedCollectionConfigurationInfo.ETag);
            Assert.AreEqual(2, receivedCollectionConfigurationInfo.Metrics.Length);

            Assert.AreEqual(metrics[0].ToString(), receivedCollectionConfigurationInfo.Metrics[0].ToString());
            Assert.AreEqual(metrics[0].Id, receivedCollectionConfigurationInfo.Metrics[0].Id);

            Assert.AreEqual(metrics[1].ToString(), receivedCollectionConfigurationInfo.Metrics[1].ToString());
            Assert.AreEqual(metrics[1].Id, receivedCollectionConfigurationInfo.Metrics[1].Id);
        }