Пример #1
0
 OperationTelemetry SetIdAndParentId(OperationTelemetry telemetry, string id, string parentId, DateTimeOffset timeStamp)
 {
     telemetry.Id = id;
     telemetry.Context.Operation.ParentId = parentId;
     telemetry.Timestamp = timeStamp;
     return(telemetry);
 }
Пример #2
0
        /// <summary>
        /// Set the duration given a timestamp from a high-resolution <see cref="Stopwatch"/>.
        /// </summary>
        /// <param name="telemetry">Telemetry item object to update.</param>
        /// <param name="timestamp">The high resolution timestamp.</param>
        private static void StopImpl(OperationTelemetry telemetry, long timestamp)
        {
            long   stopWatchTicksDiff = timestamp - telemetry.BeginTimeInTicks;
            double durationInTicks    = stopWatchTicksDiff * StopwatchTicksToTimeSpanTicks;

            StopImpl(telemetry, TimeSpan.FromTicks((long)Math.Round(durationInTicks)));
        }
        /// <summary>
        /// An extension to telemetry item that starts the timer for the the respective telemetry.
        /// </summary>
        /// <param name="telemetry">Telemetry item object that calls this extension method.</param>
        public static void Start(this OperationTelemetry telemetry)
        {
            var startTime = Clock.Instance.Time;

            telemetry.StartTime = startTime;
            telemetry.Timestamp = startTime;
        }
Пример #4
0
        internal static void UpdateTelemetryHttpCorrelationProtocol(ITelemetry telemetry, HttpCorrelationProtocolTraceContext context)
        {
            OperationTelemetry opTelemetry = telemetry as OperationTelemetry;

            bool initializeFromCurrent = opTelemetry != null;

            if (initializeFromCurrent)
            {
                initializeFromCurrent &= !(opTelemetry is DependencyTelemetry dependency &&
                                           dependency.Type == SqlRemoteDependencyType &&
                                           dependency.Context.GetInternalContext().SdkVersion
                                           .StartsWith(RddDiagnosticSourcePrefix, StringComparison.Ordinal));
            }

            if (initializeFromCurrent)
            {
                opTelemetry.Id = !string.IsNullOrEmpty(opTelemetry.Id) ? opTelemetry.Id : context.TelemetryId;
                telemetry.Context.Operation.ParentId = !string.IsNullOrEmpty(telemetry.Context.Operation.ParentId) ? telemetry.Context.Operation.ParentId : context.TelemetryContextOperationParentId;
            }
            else
            {
                telemetry.Context.Operation.Id = !string.IsNullOrEmpty(telemetry.Context.Operation.Id) ? telemetry.Context.Operation.Id : context.TelemetryContextOperationId;
                if (telemetry is ExceptionTelemetry)
                {
                    telemetry.Context.Operation.ParentId = context.TelemetryId;
                }
                else
                {
                    telemetry.Context.Operation.ParentId = !string.IsNullOrEmpty(telemetry.Context.Operation.ParentId) ? telemetry.Context.Operation.ParentId : context.TelemetryContextOperationParentId;
                }
            }
        }
Пример #5
0
        static List <OperationTelemetry> GetCorrelationSortedList(OperationTelemetry parent, List <OperationTelemetry> current)
        {
            var result = new List <OperationTelemetry>();

            if (current.Count != 0)
            {
                foreach (var some in current)
                {
                    if (parent.Id == some.Context.Operation.ParentId)
                    {
                        Console.WriteLine("match");
                    }
                }

                IOrderedEnumerable <OperationTelemetry> nexts = current.Where(p => p.Context.Operation.ParentId == parent.Id).OrderBy(p => p.Timestamp.Ticks);
                foreach (OperationTelemetry next in nexts)
                {
                    current.RemoveOperationTelemetry(next);
                    result.Add(next);
                    var childResult = GetCorrelationSortedList(next, current);
                    result.AddRange(childResult);
                }
            }

            return(result);
        }
Пример #6
0
        /// <summary>
        /// Generate random operation Id and set it to OperationContext.
        /// </summary>
        /// <param name="telemetry">Telemetry to initialize Operation id for.</param>
        public static void GenerateOperationId(this OperationTelemetry telemetry)
        {
            if (telemetry == null)
            {
                throw new ArgumentNullException(nameof(telemetry));
            }

            telemetry.GenerateId();
        }
        public async Task <bool?> Handle(Update update, OperationTelemetry telemetry, CancellationToken cancellationToken = default)
        {
            var inlineQuery = update.InlineQuery;

            telemetry.Properties["uid"]      = inlineQuery.From?.Id.ToString();
            telemetry.Properties["username"] = inlineQuery.From?.Username;
            telemetry.Properties["query"]    = inlineQuery.Query;
            return(await HandlerExtentions <bool?> .Handle(myInlineQueryHandlers, inlineQuery, new object(), cancellationToken).ConfigureAwait(false));
        }
Пример #8
0
        /// <summary>
        /// An extension to telemetry item that starts the timer for the the respective telemetry.
        /// </summary>
        /// <param name="telemetry">Telemetry item object that calls this extension method.</param>
        public static void Start(this OperationTelemetry telemetry)
        {
            telemetry.Timestamp = DateTimeOffset.UtcNow;

            // Begin time is used internally for calculating duration of operation at the end call,
            // and hence is stored using higher precision Clock.
            // Stopwatch.GetTimestamp() is used (instead of ElapsedTicks) as it is thread-safe.
            telemetry.BeginTimeInTicks = Stopwatch.GetTimestamp();
        }
Пример #9
0
 protected virtual void PopulateTags(Activity activity, OperationTelemetry telemetry)
 {
     foreach (var item in activity.Tags)
     {
         if (!telemetry.Properties.ContainsKey(item.Key))
         {
             telemetry.Properties[item.Key] = item.Value;
         }
     }
 }
        public async Task <bool?> Handle(Update update, OperationTelemetry telemetry, CancellationToken cancellationToken = default)
        {
            var chosenInlineResult = update.ChosenInlineResult;

            telemetry.Properties["uid"]      = chosenInlineResult.From?.Id.ToString();
            telemetry.Properties["username"] = chosenInlineResult.From?.Username;
            telemetry.Properties["query"]    = chosenInlineResult.Query;
            telemetry.Properties["result"]   = chosenInlineResult.ResultId;
            return(await HandlerExtentions <bool?> .Handle(myChosenInlineResultHandlers, chosenInlineResult, new object(), cancellationToken).ConfigureAwait(false));
        }
Пример #11
0
 /// <summary>
 /// An extension method to telemetry item that stops the timer and computes the duration of the request or dependency.
 /// </summary>
 /// <param name="telemetry">Telemetry item object that calls this extension method.</param>
 public static void Stop(this OperationTelemetry telemetry)
 {
     if (telemetry.BeginTimeInTicks != 0L)
     {
         StopImpl(telemetry, timestamp: Stopwatch.GetTimestamp());
     }
     else
     {
         StopImpl(telemetry, duration: TimeSpan.Zero);
     }
 }
Пример #12
0
 /// <summary>
 /// An extension method to telemetry item that stops the timer and computes the duration of the request or dependency.
 /// </summary>
 /// <param name="telemetry">Telemetry item object that calls this extension method.</param>
 /// <param name="timestamp">A high-resolution timestamp from <see cref="Stopwatch"/>.</param>
 public static void Stop(this OperationTelemetry telemetry, long timestamp)
 {
     if (telemetry.BeginTimeInTicks != 0L)
     {
         StopImpl(telemetry, timestamp);
     }
     else
     {
         StopImpl(telemetry, duration: TimeSpan.Zero);
     }
 }
Пример #13
0
        /// <summary>
        /// Record the duration and, optionally, set the timestamp to the current time.
        /// </summary>
        /// <param name="telemetry">Telemetry item object to update.</param>
        /// <param name="duration">The duration of the operation.</param>
        private static void StopImpl(OperationTelemetry telemetry, TimeSpan duration)
        {
            telemetry.Duration = duration;

            if (telemetry.Timestamp == DateTimeOffset.MinValue)
            {
                telemetry.Timestamp = PreciseTimestamp.GetUtcNow();
            }

            RichPayloadEventSource.Log.ProcessOperationStop(telemetry);
        }
Пример #14
0
 static void UpsertTelemetryProperty(OperationTelemetry operationTelemetry, string propertyName, string propertyValue)
 {
     if (operationTelemetry.Properties.ContainsKey(propertyName))
     {
         operationTelemetry.Properties[propertyName] = propertyValue;
     }
     else
     {
         operationTelemetry.Properties.Add(propertyName, propertyValue);
     }
 }
        /// <summary>
        /// An extension to telemetry item that initializes the timer for the respective telemetry
        /// using a timestamp from a high-resolution <see cref="Stopwatch"/>.
        /// </summary>
        /// <param name="telemetry">Telemetry item object that calls this extension method.</param>
        /// <param name="timestamp">A high-resolution timestamp from <see cref="Stopwatch"/>.</param>
        public static void Start(this OperationTelemetry telemetry, long timestamp)
        {
            telemetry.Timestamp = PreciseTimestamp.GetUtcNow();

            // Begin time is used internally for calculating duration of operation at the end call,
            // and hence is stored using higher precision Clock.
            // Stopwatch.GetTimestamp() is used (instead of ElapsedTicks) as it is thread-safe.
            telemetry.BeginTimeInTicks = timestamp;

            RichPayloadEventSource.Log.ProcessOperationStart(telemetry);
        }
Пример #16
0
 /// <summary>
 /// An extension method to telemetry item that stops the timer and computes the duration of the request or dependency.
 /// </summary>
 /// <param name="telemetry">Telemetry item object that calls this extension method.</param>
 public static void Stop(this OperationTelemetry telemetry)
 {
     if (telemetry.Timestamp != DateTimeOffset.MinValue)
     {
         telemetry.Duration = DateTimeOffset.UtcNow - telemetry.Timestamp;
     }
     else
     {
         telemetry.Timestamp = DateTimeOffset.UtcNow;
         telemetry.Duration  = TimeSpan.Zero;
     }
 }
        private static void SetOperationContext(Span span, OperationTelemetry telemetry)
        {
            string traceId = BytesStringToHexString(span.TraceId);

            telemetry.Context.Operation.Id = BytesStringToHexString(span.TraceId);
            if (span.ParentSpanId != null && !span.ParentSpanId.IsEmpty)
            {
                telemetry.Context.Operation.ParentId = FormatId(traceId, BytesStringToHexString(span.ParentSpanId));
            }

            telemetry.Id = FormatId(traceId, BytesStringToHexString(span.SpanId));
        }
 /// <summary>
 /// An extension method to telemetry item that stops the timer and computes the duration of the request or dependency.
 /// </summary>
 /// <param name="telemetry">Telemetry item object that calls this extension method.</param>
 public static void Stop(this OperationTelemetry telemetry)
 {
     if (telemetry.StartTime != DateTimeOffset.MinValue)
     {
         telemetry.Duration = Clock.Instance.Time - telemetry.StartTime;
     }
     else
     {
         telemetry.Timestamp = Clock.Instance.Time;
         telemetry.StartTime = telemetry.Timestamp;
         telemetry.Duration  = TimeSpan.Zero;
     }
 }
Пример #19
0
        /// <summary>
        /// Record the duration and, optionally, set the timestamp to the current time.
        /// </summary>
        /// <param name="telemetry">Telemetry item object to update.</param>
        /// <param name="duration">The duration of the operation.</param>
        private static void StopImpl(OperationTelemetry telemetry, TimeSpan duration)
        {
            telemetry.Duration = duration;

            if (telemetry.Timestamp == DateTimeOffset.MinValue)
            {
                telemetry.Timestamp = DateTimeOffset.UtcNow;
            }

#if !CORE_PCL
            RichPayloadEventSource.Log.ProcessOperationStop(telemetry);
#endif
        }
Пример #20
0
        private void SetEventHubsProperties(SpanData span, OperationTelemetry telemetry)
        {
            string endpoint  = null;
            string queueName = null;

            foreach (var attribute in span.Attributes)
            {
                if (attribute.Key == "peer.address" && attribute.Value is string)
                {
                    endpoint = (string)attribute.Value;
                }
                else if (attribute.Key == "message_bus.destination")
                {
                    queueName = (string)attribute.Value;
                }
                else
                {
                    AddPropertyWithAdjustedName(telemetry.Properties, attribute.Key, attribute.Value.ToString());
                }
            }

            string eventHubsInfo = null;

            // Target/source uniquely identifies the resource, we use both: queueName and endpoint
            if (endpoint != null && queueName != null)
            {
                eventHubsInfo = string.Concat(endpoint, "/", queueName);
            }

            if (telemetry is DependencyTelemetry dependency)
            {
                dependency.Type = dependency.Type == QueueMessageDependencyType?string.Concat(dependency.Type, " | ", EventHubsDependencyType) : EventHubsDependencyType;

                if (eventHubsInfo != null)
                {
                    dependency.Target = eventHubsInfo;
                }
            }
            else if (telemetry is RequestTelemetry request)
            {
                if (eventHubsInfo != null)
                {
                    request.Source = eventHubsInfo;
                }

                if (this.TryGetAverageTimeInQueueForBatch(span, out long enqueuedTime))
                {
                    request.Metrics["timeSinceEnqueued"] = enqueuedTime;
                }
            }
        }
Пример #21
0
        private void ValidateRootTelemetry(OperationTelemetry operationTelemetry, string expectedOperationId, string expectedId, string expectedOperationParentId, bool isW3C)
        {
            Assert.AreEqual(expectedOperationParentId, operationTelemetry.Context.Operation.ParentId);
            Assert.IsNotNull(operationTelemetry.Context.Operation.Id);

            Assert.AreEqual(expectedOperationId, operationTelemetry.Context.Operation.Id);

            if (isW3C)
            {
                Assert.IsTrue(W3CUtilities.IsCompatibleW3CTraceId(operationTelemetry.Context.Operation.Id));
            }

            Assert.IsNotNull(operationTelemetry.Id);
            Assert.AreEqual(expectedId, operationTelemetry.Id);
        }
Пример #22
0
        /// <summary>
        /// An extension method to telemetry item that stops the timer and computes the duration of the request or dependency.
        /// </summary>
        /// <param name="telemetry">Telemetry item object that calls this extension method.</param>
        /// <param name="timestamp">A high-resolution timestamp from <see cref="Stopwatch"/>.</param>
        public static void Stop(this OperationTelemetry telemetry, long timestamp)
        {
            if (telemetry == null)
            {
                throw new ArgumentNullException(nameof(telemetry));
            }

            if (telemetry.BeginTimeInTicks != 0L)
            {
                StopImpl(telemetry, timestamp);
            }
            else
            {
                StopImpl(telemetry, duration: TimeSpan.Zero);
            }
        }
Пример #23
0
        internal static void UpdateTelemetryW3C(ITelemetry telemetry, W3CTraceContext context)
        {
            OperationTelemetry opTelemetry = telemetry as OperationTelemetry;

            bool initializeFromCurrent = opTelemetry != null;

            if (initializeFromCurrent)
            {
                initializeFromCurrent &= !(opTelemetry is DependencyTelemetry dependency &&
                                           dependency.Type == SqlRemoteDependencyType &&
                                           dependency.Context.GetInternalContext().SdkVersion
                                           .StartsWith(RddDiagnosticSourcePrefix, StringComparison.Ordinal));
            }

            if (!string.IsNullOrEmpty(context.TraceState))
            {
                opTelemetry.Properties["w3c_tracestate"] = context.TraceState;
            }

            TraceParent traceParent = context.TraceParent.ToTraceParent();

            if (initializeFromCurrent)
            {
                if (string.IsNullOrEmpty(opTelemetry.Id))
                {
                    opTelemetry.Id = StringUtilities.FormatRequestId(telemetry.Context.Operation.Id, traceParent.SpanId);
                }

                if (string.IsNullOrEmpty(context.ParentSpanId))
                {
                    telemetry.Context.Operation.ParentId = StringUtilities.FormatRequestId(telemetry.Context.Operation.Id, context.ParentSpanId);
                }
            }
            else
            {
                if (telemetry.Context.Operation.Id == null)
                {
                    telemetry.Context.Operation.Id = traceParent.TraceId;
                }

                if (telemetry.Context.Operation.ParentId == null) // TODO check if it works.
                {
                    telemetry.Context.Operation.ParentId = StringUtilities.FormatRequestId(telemetry.Context.Operation.Id, traceParent.SpanId);
                }
            }
        }
Пример #24
0
        /// <summary>
        /// An extension method to telemetry item that stops the timer and computes the duration of the request or dependency.
        /// </summary>
        /// <param name="telemetry">Telemetry item object that calls this extension method.</param>
        public static void Stop(this OperationTelemetry telemetry)
        {
            if (telemetry.BeginTimeInTicks != 0L)
            {
                long   stopWatchTicksDiff  = Stopwatch.GetTimestamp() - telemetry.BeginTimeInTicks;
                double durationInMillisecs = stopWatchTicksDiff * 1000 / (double)Stopwatch.Frequency;
                telemetry.Duration = TimeSpan.FromMilliseconds(durationInMillisecs);
            }
            else
            {
                telemetry.Duration = TimeSpan.Zero;
            }

            if (telemetry.Timestamp == DateTimeOffset.MinValue)
            {
                telemetry.Timestamp = DateTimeOffset.UtcNow;
            }
        }
Пример #25
0
        private void ValidateRootTelemetry(OperationTelemetry operationTelemetry, string expectedOperationId = "", string expectedOperationParentId = null, bool isW3C = true)
        {
            Assert.AreEqual(expectedOperationParentId, operationTelemetry.Context.Operation.ParentId);
            Assert.IsNotNull(operationTelemetry.Context.Operation.Id);

            if (!string.IsNullOrEmpty(expectedOperationId))
            {
                Assert.AreEqual(expectedOperationId, operationTelemetry.Context.Operation.Id);
            }

            if (isW3C)
            {
                Assert.IsTrue(W3CUtilities.IsCompatibleW3CTraceId(operationTelemetry.Context.Operation.Id));
            }
            Assert.IsNotNull(operationTelemetry.Id);
            // ID is shaped like |TraceID.SpanID.
            Assert.IsTrue(operationTelemetry.Id.Contains(operationTelemetry.Context.Operation.Id));
        }
        private static void SetEventHubsProperties(Activity activity, OperationTelemetry telemetry)
        {
            string endpoint  = null;
            string queueName = null;

            foreach (var tag in activity.Tags)
            {
                if (tag.Key == "peer.address")
                {
                    endpoint = tag.Value;
                }
                else if (tag.Key == "message_bus.destination")
                {
                    queueName = tag.Value;
                }
            }

            if (endpoint == null || queueName == null)
            {
                return;
            }

            // Target uniquely identifies the resource, we use both: queueName and endpoint
            // with schema used for SQL-dependencies
            string separator = "/";

            if (endpoint.EndsWith(separator, StringComparison.Ordinal))
            {
                separator = string.Empty;
            }

            string eventHubInfo = string.Concat(endpoint, separator, queueName);

            if (telemetry is DependencyTelemetry dependency)
            {
                dependency.Target = eventHubInfo;
            }
            else if (telemetry is RequestTelemetry request)
            {
                request.Source = eventHubInfo;
            }
        }
Пример #27
0
        internal static void UpdateTelemetry(ITelemetry telemetry, Activity activity, bool forceUpdate)
        {
            if (activity == null)
            {
                return;
            }

            // Requests and dependnecies are initialized from the current Activity
            // (i.e. telemetry.Id = current.Id). Activity is created for such requests specifically
            // Traces, exceptions, events on the other side are children of current activity
            // There is one exception - SQL DiagnosticSource where current Activity is a parent
            // for dependency calls.

            OperationTelemetry opTelemetry = telemetry as OperationTelemetry;
            bool initializeFromCurrent     = opTelemetry != null;

            if (initializeFromCurrent)
            {
                initializeFromCurrent &= !(opTelemetry is DependencyTelemetry dependency &&
                                           dependency.Type == SqlRemoteDependencyType &&
                                           dependency.Context.GetInternalContext().SdkVersion
                                           .StartsWith(RddDiagnosticSourcePrefix, StringComparison.Ordinal));
            }

            if (telemetry is OperationTelemetry operation)
            {
                operation.Properties[TracestateTag] = activity.TraceStateString;
            }

            if (initializeFromCurrent)
            {
                opTelemetry.Id = activity.SpanId.ToHexString();
                if (activity.ParentSpanId != null)
                {
                    opTelemetry.Context.Operation.ParentId = activity.ParentSpanId.ToHexString();
                }
            }
            else
            {
                telemetry.Context.Operation.ParentId = activity.SpanId.ToHexString();
            }
        }
Пример #28
0
        internal bool IsSuppressedTelemetry(ITelemetry telemetry)
        {
            OperationTelemetry opTelemetry = telemetry as OperationTelemetry;

            if (telemetry is DependencyTelemetry)
            {
                DependencyTelemetry dTelemetry = telemetry as DependencyTelemetry;

                if (!string.IsNullOrEmpty(dTelemetry.CommandName))
                {
                    var host = new Uri(dTelemetry.CommandName).Host;
                    if (ExcludeComponentCorrelationHttpHeadersOnDomains.Contains(host))
                    {
                        return(true);
                    }
                }
            }

            return(false);
        }
        private static void PopulateLinks(IEnumerable <Activity> links, OperationTelemetry telemetry)
        {
            if (links.Any())
            {
                var linksJson = new StringBuilder();
                linksJson.Append('[');
                foreach (var link in links)
                {
                    var linkTraceId = link.TraceId.ToHexString();

                    // avoiding json serializers for now because of extra dependency.
                    // serialization is trivial and looks like `links` property with json blob
                    // [{"operation_Id":"5eca8b153632494ba00f619d6877b134","id":"d4c1279b6e7b7c47"},
                    //  {"operation_Id":"ff28988d0776b44f9ca93352da126047","id":"bf4fa4855d161141"}]
                    linksJson
                    .Append('{')
                    .Append("\"operation_Id\":")
                    .Append('\"')
                    .Append(linkTraceId)
                    .Append('\"')
                    .Append(',');
                    linksJson
                    .Append("\"id\":")
                    .Append('\"')
                    .Append(link.ParentSpanId.ToHexString())
                    .Append('\"');

                    // we explicitly ignore sampling flag, tracestate and attributes at this point.
                    linksJson.Append("},");
                }

                if (linksJson.Length > 0)
                {
                    // trim trailing comma - json does not support it
                    linksJson.Remove(linksJson.Length - 1, 1);
                }

                linksJson.Append(']');
                telemetry.Properties["_MS.links"] = linksJson.ToString();
            }
        }
Пример #30
0
        private static void InitializeOperationTelemetry(OperationTelemetry telemetry, string spanName, string requestId, string parentRequestId,
                                                         long spanStatusCode, string spanStatusMessage, DateTimeOffset?startTime, DateTimeOffset?endTime, string roleName, string roleInstance)
        {
            telemetry.Name = spanName;

            var now = DateTimeOffset.UtcNow;

            telemetry.Timestamp = startTime ?? now;
            var endTimeAdjusted = endTime ?? now;

            telemetry.Duration = endTimeAdjusted - telemetry.Timestamp;

            SetOperationContext(requestId, parentRequestId, telemetry);

            telemetry.Success = spanStatusCode == 0;
            if (!string.IsNullOrEmpty(spanStatusMessage))
            {
                telemetry.Properties["statusDescription"] = spanStatusMessage;
            }

            SetPeerInfo(telemetry, roleName, roleInstance);
        }