示例#1
0
        public void SetUp()
        {
            _configuration = Mock.Create <IConfiguration>();
            var configurationService = Mock.Create <IConfigurationService>();

            Mock.Arrange(() => configurationService.Configuration).Returns(_configuration);

            _databaseService = new DatabaseService(Mock.Create <ICacheStatsReporter>());
            _errorService    = new ErrorService(configurationService);
            _distributedTracePayloadHandler = Mock.Create <IDistributedTracePayloadHandler>();
            _attribDefSvc      = new AttributeDefinitionService((f) => new AttributeDefinitions(f));
            _transaction       = new Transaction(_configuration, Mock.Create <ITransactionName>(), Mock.Create <ITimer>(), DateTime.UtcNow, Mock.Create <ICallStackManager>(), _databaseService, Priority, Mock.Create <IDatabaseStatementParser>(), _distributedTracePayloadHandler, _errorService, _attribDefs);
            _publishedEvent    = null;
            _eventSubscription = new EventSubscription <TransactionFinalizedEvent>(e => _publishedEvent = e);
            _wrapperToken      = new object();
        }
        private void OnTransactionFinalized(TransactionFinalizedEvent eventData)
        {
            var internalTransaction = eventData.Transaction;

            // When a transaction gets finalized it means it never ended cleanly, so we should try to estimate when it ended based on its last finished segment
            var immutableTransaction = internalTransaction.ConvertToImmutableTransaction();
            var lastStartedSegment   = TryGetLastStartedSegment(immutableTransaction);
            var lastFinishedSegment  = TryGetLastFinishedSegment(immutableTransaction);
            var estimatedDuration    = GetEstimatedTransactionDuration(internalTransaction, lastStartedSegment, lastFinishedSegment);
            var finishedTransaction  = false;

            try
            {
                internalTransaction.ForceChangeDuration(estimatedDuration);

                // Then we should mark the transaction as cleanly finished so it won't get finalized again
                finishedTransaction = Finish(internalTransaction);

                if (finishedTransaction)
                {
                    // Then we send it off to be transformed as with normal transactions
                    _transactionTransformer.Transform(internalTransaction);
                }
            }
            finally
            {
                if (finishedTransaction)
                {
                    // Finally, we announce the event to our agent health reporter
                    var transactionMetricName   = _transactionMetricNameMaker.GetTransactionMetricName(immutableTransaction.TransactionName);
                    var lastFinishedSegmentName = lastFinishedSegment != null
                        ? lastFinishedSegment.GetTransactionTraceName()
                        : "<unknown>";

                    var lastStartedSegmentName = lastStartedSegment != null
                        ? lastStartedSegment.GetTransactionTraceName()
                        : "<unknown>";

                    _agentHealthReporter.ReportTransactionGarbageCollected(transactionMetricName, lastStartedSegmentName, lastFinishedSegmentName);
                }
            }
        }
示例#3
0
        public void TransactionFinalizedEvent_IsNotPublishedASecondTime_IfBuilderGoesOutOfScopeAgain()
        {
            Assert.NotNull(_transaction);

            _transaction = null;

            GC.Collect();
            GC.WaitForFullGCComplete();
            GC.WaitForPendingFinalizers();

            Assert.NotNull(_publishedEvent);

            // The builder is now pinned to the event, but we can unpin it by unpinning the event
            _publishedEvent = null;

            GC.Collect();
            GC.WaitForFullGCComplete();
            GC.WaitForPendingFinalizers();

            Assert.Null(_publishedEvent);
        }