private IEnumerable <DataSample> PopulateBucketedDataSamples(DimensionSpecification filterDims, Action <DataSample, TInternal, QuerySpecification> sampleAction, QuerySpecification querySpec) { using (SharedLock.OpenShared(this.dataLock)) { var bucketQuery = new BucketQuery(this, filterDims); foreach (var bucket in bucketQuery) { foreach (var match in (querySpec.IsCrossQuery ? bucket.GetMatchesSplitByDimension(filterDims, querySpec.CrossQueryDimension) : bucket.GetMatches(filterDims))) { if (match.DataCount == 0) { continue; } var sample = new DataSample { Name = this.Name, Dimensions = match.DimensionValues.Data, StartTime = bucket.StartTime.ToMillisecondTimestamp(), EndTime = bucket.EndTime.ToMillisecondTimestamp(), }; sampleAction(sample, match.Data, querySpec); yield return(sample); } } } Events.Write.EndQueryData(this); }
public IEnumerable <DataSample> QueryData(DimensionSpecification filterDims, QuerySpecification querySpec) { Events.Write.BeginQueryData(this, filterDims, querySpec); if (filterDims == null) { throw new ArgumentNullException("filterDims"); } // EndQueryData has to be called in the data enumerators because the enumeration does not occur // until iteration begins on the IEnumerable we return. if (querySpec.QueryType != QueryType.Normal && typeof(TInternal) != typeof(InternalHistogram)) { throw new NotSupportedException("Cannot get percentiles for non-histograms."); } switch (querySpec.QueryType) { case QueryType.Normal: { return(querySpec.Combine ? this.PopulateCombinedDataSamples(filterDims, PopulateNormalSample, querySpec) : this.PopulateBucketedDataSamples(filterDims, PopulateNormalSample, querySpec)); } case QueryType.Percentile: { CheckPercentileValue(querySpec.Percentile); return(querySpec.Combine ? this.PopulateCombinedDataSamples(filterDims, PopulatePercentileSample, querySpec) : this.PopulateBucketedDataSamples(filterDims, PopulatePercentileSample, querySpec)); } case QueryType.Average: { return(querySpec.Combine ? this.PopulateCombinedDataSamples(filterDims, PopulateAverageSample, querySpec) : this.PopulateBucketedDataSamples(filterDims, PopulateAverageSample, querySpec)); } case QueryType.Maximum: { return(querySpec.Combine ? this.PopulateCombinedDataSamples(filterDims, PopulateMaximumSample, querySpec) : this.PopulateBucketedDataSamples(filterDims, PopulateMaximumSample, querySpec)); } case QueryType.Minimum: { return(querySpec.Combine ? this.PopulateCombinedDataSamples(filterDims, PopulateMinimumSample, querySpec) : this.PopulateBucketedDataSamples(filterDims, PopulateMinimumSample, querySpec)); } default: throw new NotSupportedException("Unknown query type " + querySpec.QueryType); } }
private static void PopulateMinimumSample(DataSample sample, TInternal data, QuerySpecification querySpec) { var histogram = data as InternalHistogram; sample.SampleType = DataSampleType.Minimum; sample.SampleCount = histogram.SampleCount; sample.MinValue = histogram.Data.GetMinimumValue(); }
private static void PopulateAverageSample(DataSample sample, TInternal data, QuerySpecification querySpec) { var histogram = data as InternalHistogram; sample.SampleCount = histogram.SampleCount; sample.SampleType = DataSampleType.Average; sample.Average = histogram.Data.GetAverageValue(histogram.SampleCount); }
private static void PopulatePercentileSample(DataSample sample, TInternal data, QuerySpecification querySpec) { var histogram = data as InternalHistogram; sample.SampleCount = histogram.SampleCount; sample.SampleType = DataSampleType.Percentile; sample.Percentile = querySpec.Percentile; sample.PercentileValue = histogram.Data.GetValueAtPercentile(querySpec.Percentile, sample.SampleCount); }
internal void BeginQueryData(IDataSet dataSet, DimensionSpecification filterDimensions, QuerySpecification querySpec) { if (this.IsEnabled(EventLevel.Verbose, EventKeywords.None)) { this.BeginQueryData(dataSet.Name, string.Join("; ", (from pair in filterDimensions select pair.Key + '=' + pair.Value)), querySpec.ToString()); } }
internal static DimensionSpecification ExtractQuerySpec(DimensionSpecification queryParameters, out QuerySpecification querySpec) { var filterDimensions = new DimensionSpecification(); querySpec = new QuerySpecification(); foreach (var param in queryParameters) { if (string.Equals(param.Key, ReservedDimensions.DimensionDimension, StringComparison.OrdinalIgnoreCase)) { querySpec.CrossQueryDimension = param.Value; // Ensure that split dimension is not also sent a filter dimension if (queryParameters.ContainsKey(param.Value)) { return(null); } } else if (string.Equals(param.Key, ReservedDimensions.AggregateSamplesDimension, StringComparison.OrdinalIgnoreCase)) { querySpec.Combine = Convert.ToBoolean(param.Value); } else if (string.Equals(param.Key, ReservedDimensions.PercentileDimension, StringComparison.OrdinalIgnoreCase)) { if (string.Equals(param.Value, ReservedDimensions.PercentileDimensionValueForAverage, StringComparison.OrdinalIgnoreCase)) { querySpec.QueryType = QueryType.Average; } else if (string.Equals(param.Value, ReservedDimensions.PercentileDimensionValueForMaximum, StringComparison.OrdinalIgnoreCase)) { querySpec.QueryType = QueryType.Maximum; } else if (string.Equals(param.Value, ReservedDimensions.PercentileDimensionValueForMinimum, StringComparison.OrdinalIgnoreCase)) { querySpec.QueryType = QueryType.Minimum; } else { querySpec.QueryType = QueryType.Percentile; querySpec.Percentile = double.Parse(param.Value); } } else { filterDimensions.Add(param.Key, param.Value); } } return(filterDimensions); }
private DimensionSpecification ProcessQueryParameters(DimensionSpecification queryParameters, out QuerySpecification querySpec) { var filterDimensions = ExtractQuerySpec(queryParameters, out querySpec); if (querySpec.QueryType == QueryType.Average && !this.DataSet.SupportsAverageQuery) { querySpec.QueryType = QueryType.Normal; } else if (querySpec.QueryType == QueryType.Percentile && !this.DataSet.SupportsPercentileQuery) { querySpec.QueryType = QueryType.Normal; } return(filterDimensions); }
private static void PopulateNormalSample(DataSample sample, TInternal data, QuerySpecification querySpec) { data.UpdateDataSample(sample); }
private IEnumerable <DataSample> PopulateCombinedDataSamples(DimensionSpecification filterDims, Action <DataSample, TInternal, QuerySpecification> sampleAction, QuerySpecification querySpec) { var combinedData = new Dictionary <string, CombinedSample>(); long start = long.MaxValue; long end = long.MinValue; using (SharedLock.OpenShared(this.dataLock)) { var bucketQuery = new BucketQuery(this, filterDims); foreach (var bucket in bucketQuery) { foreach (var match in (querySpec.IsCrossQuery ? bucket.GetMatchesSplitByDimension(filterDims, querySpec.CrossQueryDimension) : bucket.GetMatches(filterDims))) { if (match.DataCount == 0) { continue; } CombinedSample value; if (!combinedData.TryGetValue(match.SplitDimensionValue, out value)) { value = new CombinedSample { Data = match.Data, Dimensions = match.DimensionValues, }; combinedData[match.SplitDimensionValue] = value; } else { value.Data.MergeFrom(match.Data); } if (bucket.StartTicks < start) { start = bucket.StartTicks; } if (bucket.EndTicks > end) { end = bucket.EndTicks; } } } } foreach (var value in combinedData.Values) { var sample = new DataSample { Name = this.Name, StartTime = new DateTime(start, DateTimeKind.Utc).ToMillisecondTimestamp(), EndTime = new DateTime(end, DateTimeKind.Utc).ToMillisecondTimestamp(), Dimensions = value.Dimensions.Data, }; sampleAction(sample, value.Data, querySpec); yield return(sample); } Events.Write.EndQueryData(this); }
internal static DimensionSpecification ExtractQuerySpec(DimensionSpecification queryParameters, out QuerySpecification querySpec) { var filterDimensions = new DimensionSpecification(); querySpec = new QuerySpecification(); foreach (var param in queryParameters) { if (string.Equals(param.Key, ReservedDimensions.DimensionDimension, StringComparison.OrdinalIgnoreCase)) { querySpec.CrossQueryDimension = param.Value; // Ensure that split dimension is not also sent a filter dimension if (queryParameters.ContainsKey(param.Value)) { return null; } } else if (string.Equals(param.Key, ReservedDimensions.AggregateSamplesDimension, StringComparison.OrdinalIgnoreCase)) { querySpec.Combine = Convert.ToBoolean(param.Value); } else if (string.Equals(param.Key, ReservedDimensions.PercentileDimension, StringComparison.OrdinalIgnoreCase)) { if (string.Equals(param.Value, ReservedDimensions.PercentileDimensionValueForAverage, StringComparison.OrdinalIgnoreCase)) { querySpec.QueryType = QueryType.Average; } else if (string.Equals(param.Value, ReservedDimensions.PercentileDimensionValueForMaximum, StringComparison.OrdinalIgnoreCase)) { querySpec.QueryType = QueryType.Maximum; } else if (string.Equals(param.Value, ReservedDimensions.PercentileDimensionValueForMinimum, StringComparison.OrdinalIgnoreCase)) { querySpec.QueryType = QueryType.Minimum; } else { querySpec.QueryType = QueryType.Percentile; querySpec.Percentile = double.Parse(param.Value); } } else { filterDimensions.Add(param.Key, param.Value); } } return filterDimensions; }
private DimensionSpecification ProcessQueryParameters(DimensionSpecification queryParameters, out QuerySpecification querySpec) { var filterDimensions = ExtractQuerySpec(queryParameters, out querySpec); if (querySpec.QueryType == QueryType.Average && !this.DataSet.SupportsAverageQuery) { querySpec.QueryType = QueryType.Normal; } else if (querySpec.QueryType == QueryType.Percentile && !this.DataSet.SupportsPercentileQuery) { querySpec.QueryType = QueryType.Normal; } return filterDimensions; }