Exemple #1
0
        public void MultithreadedLongCounterTest()
        {
            var exportedItems = new List <Metric>();

            using var meter = new Meter(Utils.GetCurrentMethodName());
            var counterLong = meter.CreateCounter <long>("mycounter");

            using var meterProvider = Sdk.CreateMeterProviderBuilder()
                                      .AddMeter(meter.Name)
                                      .AddReader(new BaseExportingMetricReader(new InMemoryExporter <Metric>(exportedItems))
            {
                Temporality = AggregationTemporality.Cumulative,
            })
                                      .Build();

            // setup args to threads.
            var mreToBlockUpdateThreads      = new ManualResetEvent(false);
            var mreToEnsureAllThreadsStarted = new ManualResetEvent(false);

            var argToThread = new UpdateThreadArguments <long>();

            argToThread.DeltaValueUpdatedByEachCall = deltaLongValueUpdatedByEachCall;
            argToThread.Counter                    = counterLong;
            argToThread.ThreadsStartedCount        = 0;
            argToThread.MreToBlockUpdateThread     = mreToBlockUpdateThreads;
            argToThread.MreToEnsureAllThreadsStart = mreToEnsureAllThreadsStarted;

            Thread[] t = new Thread[numberOfThreads];
            for (int i = 0; i < numberOfThreads; i++)
            {
                t[i] = new Thread(CounterUpdateThread <long>);
                t[i].Start(argToThread);
            }

            // Block until all threads started.
            mreToEnsureAllThreadsStarted.WaitOne();

            Stopwatch sw = Stopwatch.StartNew();

            // unblock all the threads.
            // (i.e let them start counter.Add)
            mreToBlockUpdateThreads.Set();

            for (int i = 0; i < numberOfThreads; i++)
            {
                // wait for all threads to complete
                t[i].Join();
            }

            var timeTakenInMilliseconds = sw.ElapsedMilliseconds;

            this.output.WriteLine($"Took {timeTakenInMilliseconds} msecs. Total threads: {numberOfThreads}, each thread doing {numberOfMetricUpdateByEachThread} recordings.");

            meterProvider.ForceFlush(MaxTimeToAllowForFlush);

            var sumReceived = GetLongSum(exportedItems);
            var expectedSum = deltaLongValueUpdatedByEachCall * numberOfMetricUpdateByEachThread * numberOfThreads;

            Assert.Equal(expectedSum, sumReceived);
        }
        public void MeasureAggregatorAggregatesCorrectlyWhenMultipleThreadsUpdatesDouble()
        {
            // create an aggregator
            var aggregator = new DoubleMeasureMinMaxSumCountAggregator();
            var summary    = aggregator.ToMetricData() as SummaryData <double>;

            // we start with 0.
            Assert.Equal(0, summary.Sum);
            Assert.Equal(0, summary.Count);

            // setup args to threads.
            var mre = new ManualResetEvent(false);
            var mreToEnsureAllThreadsStart = new ManualResetEvent(false);

            var argToThread = new UpdateThreadArguments <double>
            {
                minMaxSumCountAggregator   = aggregator,
                threadsStartedCount        = 0,
                mreToBlockUpdateThread     = mre,
                mreToEnsureAllThreadsStart = mreToEnsureAllThreadsStart
            };

            Thread[] t = new Thread[10];
            for (int i = 0; i < 10; i++)
            {
                t[i] = new Thread(DoubleMetricUpdateThread);
                t[i].Start(argToThread);
            }

            // Block until all 10 threads started.
            mreToEnsureAllThreadsStart.WaitOne();

            // kick-off all the threads.
            mre.Set();

            for (int i = 0; i < 10; i++)
            {
                // wait for all threads to complete
                t[i].Join();
            }

            // check point.
            aggregator.Checkpoint();
            summary = aggregator.ToMetricData() as SummaryData <double>;

            // 1000000 times (10+50+100) by each thread. times 10 as there are 10 threads
            Assert.Equal(1600000000, summary.Sum);

            // 1000000 times 3 by each thread, times 10 as there are 10 threads.
            Assert.Equal(30000000, summary.Count);

            // Min and Max are 10 and 100
            Assert.Equal(10, summary.Min);
            Assert.Equal(100, summary.Max);
        }
Exemple #3
0
        private void MultithreadedCounterTest <T>(T deltaValueUpdatedByEachCall)
            where T : struct, IComparable
        {
            var metricItems  = new List <Metric>();
            var metricReader = new BaseExportingMetricReader(new InMemoryExporter <Metric>(metricItems));

            using var meter         = new Meter($"{Utils.GetCurrentMethodName()}.{typeof(T).Name}.{deltaValueUpdatedByEachCall}");
            using var meterProvider = Sdk.CreateMeterProviderBuilder()
                                      .AddMeter(meter.Name)
                                      .AddReader(metricReader)
                                      .Build();

            var argToThread = new UpdateThreadArguments <T>
            {
                ValuesToRecord             = new T[] { deltaValueUpdatedByEachCall },
                Instrument                 = meter.CreateCounter <T>("counter"),
                MreToBlockUpdateThread     = new ManualResetEvent(false),
                MreToEnsureAllThreadsStart = new ManualResetEvent(false),
            };

            Thread[] t = new Thread[numberOfThreads];
            for (int i = 0; i < numberOfThreads; i++)
            {
                t[i] = new Thread(CounterUpdateThread <T>);
                t[i].Start(argToThread);
            }

            argToThread.MreToEnsureAllThreadsStart.WaitOne();
            Stopwatch sw = Stopwatch.StartNew();

            argToThread.MreToBlockUpdateThread.Set();

            for (int i = 0; i < numberOfThreads; i++)
            {
                t[i].Join();
            }

            this.output.WriteLine($"Took {sw.ElapsedMilliseconds} msecs. Total threads: {numberOfThreads}, each thread doing {numberOfMetricUpdateByEachThread} recordings.");

            metricReader.Collect();

            if (typeof(T) == typeof(long))
            {
                var sumReceived = GetLongSum(metricItems);
                var expectedSum = deltaLongValueUpdatedByEachCall * numberOfMetricUpdateByEachThread * numberOfThreads;
                Assert.Equal(expectedSum, sumReceived);
            }
            else if (typeof(T) == typeof(double))
            {
                var sumReceived = GetDoubleSum(metricItems);
                var expectedSum = deltaDoubleValueUpdatedByEachCall * numberOfMetricUpdateByEachThread * numberOfThreads;
                Assert.Equal(expectedSum, sumReceived, 2);
            }
        }
Exemple #4
0
        private void MultithreadedHistogramTest <T>(long[] expected, T[] values)
            where T : struct, IComparable
        {
            var bucketCounts = new long[11];
            var metricReader = new BaseExportingMetricReader(new TestExporter <Metric>(batch =>
            {
                foreach (var metric in batch)
                {
                    foreach (var metricPoint in metric.GetMetricPoints())
                    {
                        bucketCounts = metricPoint.GetHistogramBuckets().RunningBucketCounts;
                    }
                }
            }));

            using var meter         = new Meter($"{Utils.GetCurrentMethodName()}.{typeof(T).Name}");
            using var meterProvider = Sdk.CreateMeterProviderBuilder()
                                      .AddMeter(meter.Name)
                                      .AddReader(metricReader)
                                      .Build();

            var argsToThread = new UpdateThreadArguments <T>
            {
                Instrument                 = meter.CreateHistogram <T>("histogram"),
                MreToBlockUpdateThread     = new ManualResetEvent(false),
                MreToEnsureAllThreadsStart = new ManualResetEvent(false),
                ValuesToRecord             = values,
            };

            Thread[] t = new Thread[numberOfThreads];
            for (int i = 0; i < numberOfThreads; i++)
            {
                t[i] = new Thread(HistogramUpdateThread <T>);
                t[i].Start(argsToThread);
            }

            argsToThread.MreToEnsureAllThreadsStart.WaitOne();
            Stopwatch sw = Stopwatch.StartNew();

            argsToThread.MreToBlockUpdateThread.Set();

            for (int i = 0; i < numberOfThreads; i++)
            {
                t[i].Join();
            }

            this.output.WriteLine($"Took {sw.ElapsedMilliseconds} msecs. Total threads: {numberOfThreads}, each thread doing {numberOfMetricUpdateByEachThread * values.Length} recordings.");

            metricReader.Collect();

            Assert.Equal(expected, bucketCounts);
        }
        public void CounterAggregatorAggregatesCorrectlyWhenMultipleThreadsUpdatesDouble()
        {
            // create an aggregator
            var aggregator = new DoubleCounterSumAggregator();
            var sum        = aggregator.ToMetricData() as DoubleSumData;

            // we start with 0.0
            Assert.Equal(0.0, sum.Sum);

            // setup args to threads.
            var mre = new ManualResetEvent(false);
            var mreToEnsureAllThreadsStart = new ManualResetEvent(false);

            var argToThread =
                new UpdateThreadArguments <double>
            {
                CounterSumAggregator       = aggregator,
                ThreadsStartedCount        = 0,
                MreToBlockUpdateThread     = mre,
                MreToEnsureAllThreadsStart = mreToEnsureAllThreadsStart,
            };

            Thread[] t = new Thread[10];
            for (int i = 0; i < 10; i++)
            {
                t[i] = new Thread(DoubleMetricUpdateThread);
                t[i].Start(argToThread);
            }

            // Block until all 10 threads started.
            mreToEnsureAllThreadsStart.WaitOne();

            // kick-off all the threads.
            mre.Set();

            for (int i = 0; i < 10; i++)
            {
                // wait for all threads to complete
                t[i].Join();
            }

            // check point.
            aggregator.Checkpoint();
            sum = aggregator.ToMetricData() as DoubleSumData;

            // 1000000 times 10.5 by each thread. times 10 as there are 10 threads
            Assert.Equal(105000000, sum.Sum);
        }
        public void CounterAggregatorAggregatesCorrectlyWhenMultipleThreadsUpdatesLong()
        {
            // create an aggregator
            CounterSumAggregator <long> aggregator = new CounterSumAggregator <long>();
            var sum = aggregator.ValueFromLastCheckpoint();

            // we start with 0.
            Assert.Equal(0, sum);

            // setup args to threads.
            var mre = new ManualResetEvent(false);
            var mreToEnsureAllThreadsStart = new ManualResetEvent(false);

            var argToThread = new UpdateThreadArguments <long>();

            argToThread.counterSumAggregator       = aggregator;
            argToThread.threadsStartedCount        = 0;
            argToThread.mreToBlockUpdateThread     = mre;
            argToThread.mreToEnsureAllThreadsStart = mreToEnsureAllThreadsStart;

            Thread[] t = new Thread[10];
            for (int i = 0; i < 10; i++)
            {
                t[i] = new Thread(LongMetricUpdateThread);
                t[i].Start(argToThread);
            }

            // Block until all 10 threads started.
            mreToEnsureAllThreadsStart.WaitOne();

            // kick-off all the threads.
            mre.Set();

            for (int i = 0; i < 10; i++)
            {
                // wait for all threads to complete
                t[i].Join();
            }

            // check point.
            aggregator.Checkpoint();
            sum = aggregator.ValueFromLastCheckpoint();

            // 1000000 times 10 by each thread. times 10 as there are 10 threads
            Assert.Equal(100000000, sum);
        }
        public void MultithreadedDoubleCounterTest()
        {
            var metricItems    = new List <Metric>();
            var metricExporter = new TestExporter <Metric>(ProcessExport);

            void ProcessExport(Batch <Metric> batch)
            {
                foreach (var metricItem in batch)
                {
                    metricItems.Add(metricItem);
                }
            }

            var metricReader = new BaseExportingMetricReader(metricExporter)
            {
                PreferredAggregationTemporality = AggregationTemporality.Cumulative,
            };

            using var meter = new Meter("TestDoubleCounterMeter");
            var counterDouble = meter.CreateCounter <double>("mycounter");

            using var meterProvider = Sdk.CreateMeterProviderBuilder()
                                      .AddMeter("TestDoubleCounterMeter")
                                      .AddReader(metricReader)
                                      .Build();

            // setup args to threads.
            var mreToBlockUpdateThreads      = new ManualResetEvent(false);
            var mreToEnsureAllThreadsStarted = new ManualResetEvent(false);

            var argToThread = new UpdateThreadArguments <double>();

            argToThread.DeltaValueUpdatedByEachCall = deltaDoubleValueUpdatedByEachCall;
            argToThread.Counter                    = counterDouble;
            argToThread.ThreadsStartedCount        = 0;
            argToThread.MreToBlockUpdateThread     = mreToBlockUpdateThreads;
            argToThread.MreToEnsureAllThreadsStart = mreToEnsureAllThreadsStarted;

            Thread[] t = new Thread[numberOfThreads];
            for (int i = 0; i < numberOfThreads; i++)
            {
                t[i] = new Thread(CounterUpdateThread <double>);
                t[i].Start(argToThread);
            }

            // Block until all threads started.
            mreToEnsureAllThreadsStarted.WaitOne();

            Stopwatch sw = Stopwatch.StartNew();

            // unblock all the threads.
            // (i.e let them start counter.Add)
            mreToBlockUpdateThreads.Set();

            for (int i = 0; i < numberOfThreads; i++)
            {
                // wait for all threads to complete
                t[i].Join();
            }

            var timeTakenInMilliseconds = sw.ElapsedMilliseconds;

            this.output.WriteLine($"Took {timeTakenInMilliseconds} msecs. Total threads: {numberOfThreads}, each thread doing {numberOfMetricUpdateByEachThread} recordings.");

            metricReader.Collect();

            var sumReceived = GetDoubleSum(metricItems);
            var expectedSum = deltaDoubleValueUpdatedByEachCall * numberOfMetricUpdateByEachThread * numberOfThreads;
            var difference  = Math.Abs(sumReceived - expectedSum);

            Assert.True(difference <= 0.0001);
        }
        public void SimpleTest()
        {
            var metricItems    = new List <MetricItem>();
            var metricExporter = new TestExporter <MetricItem>(ProcessExport);

            void ProcessExport(Batch <MetricItem> batch)
            {
                foreach (var metricItem in batch)
                {
                    metricItems.Add(metricItem);
                }
            }

            var pullProcessor = new PullMetricProcessor(metricExporter, true);

            var meter         = new Meter("TestMeter");
            var counterLong   = meter.CreateCounter <long>("mycounter");
            var meterProvider = Sdk.CreateMeterProviderBuilder()
                                .AddSource("TestMeter")
                                .AddMetricProcessor(pullProcessor)
                                .Build();

            // setup args to threads.
            var mreToBlockUpdateThreads      = new ManualResetEvent(false);
            var mreToEnsureAllThreadsStarted = new ManualResetEvent(false);

            var argToThread = new UpdateThreadArguments();

            argToThread.Counter                    = counterLong;
            argToThread.ThreadsStartedCount        = 0;
            argToThread.MreToBlockUpdateThread     = mreToBlockUpdateThreads;
            argToThread.MreToEnsureAllThreadsStart = mreToEnsureAllThreadsStarted;

            Thread[] t = new Thread[numberOfThreads];
            for (int i = 0; i < numberOfThreads; i++)
            {
                t[i] = new Thread(CounterUpdateThread);
                t[i].Start(argToThread);
            }

            // Block until all threads started.
            mreToEnsureAllThreadsStarted.WaitOne();

            Stopwatch sw = new Stopwatch();

            sw.Start();

            // unblock all the threads.
            // (i.e let them start counter.Add)
            mreToBlockUpdateThreads.Set();

            for (int i = 0; i < numberOfThreads; i++)
            {
                // wait for all threads to complete
                t[i].Join();
            }

            var timeTakenInMilliseconds = sw.ElapsedMilliseconds;

            this.output.WriteLine($"Took {timeTakenInMilliseconds} msecs. Total threads: {numberOfThreads}, each thread doing {numberOfMetricUpdateByEachThread} recordings.");

            meterProvider.Dispose();
            pullProcessor.PullRequest();

            long sumReceived = 0;

            foreach (var metricItem in metricItems)
            {
                var metrics = metricItem.Metrics;
                foreach (var metric in metrics)
                {
                    sumReceived += (metric as ISumMetricLong).LongSum;
                }
            }

            var expectedSum = deltaValueUpdatedByEachCall * numberOfMetricUpdateByEachThread * numberOfThreads;

            Assert.Equal(expectedSum, sumReceived);
        }