| File: Telemetry\TelemetryDiskLogger.cs | Web Access |
| Project: src\sdk\src\Cli\dotnet\dotnet.csproj (dotnet) |
// Licensed to the .NET Foundation under one or more agreements. // The .NET Foundation licenses this file to you under the MIT license. using System.Diagnostics; using System.Text.Json; using System.Text.Json.Nodes; using System.Text.Json.Serialization; namespace Microsoft.DotNet.Cli.Telemetry; internal static class TelemetryDiskLogger { private static readonly JsonSerializerOptions s_jsonOptions; private static readonly TelemetryDiskLoggerJsonSerializerContext s_jsonContext; public record EventModel( string name, DateTimeOffset timestamp, Dictionary<string, object?> tags); public record SourceModel( string name, string? version, Dictionary<string, object?>? tags); public record IdentifiersModel( string? id, string traceId, string spanId, string parentSpanId, string? parentId, string? rootId); public record ActivityModel( string operationName, string displayName, TimeSpan duration, IdentifiersModel identifiers, SourceModel source, Dictionary<string, string?> tags, EventModel[] events); static TelemetryDiskLogger() { s_jsonOptions = new(JsonSerializerDefaults.Web) { WriteIndented = false }; s_jsonContext = new(s_jsonOptions); } public static void WriteLog(string logPath, IEnumerable<Activity> activies) { try { var jsonText = !File.Exists(logPath) ? """{"activities":[]}""" : File.ReadAllText(logPath); var root = JsonNode.Parse(jsonText)!; var activitiesArray = root["activities"]!.AsArray(); foreach (var activity in activies) { activitiesArray.Add(JsonNode.Parse(JsonSerializer.Serialize(CreateActivityJsonModel(activity), s_jsonContext.ActivityModel))); } root["activities"] = activitiesArray; File.WriteAllText(logPath, root.ToJsonString(s_jsonOptions)); } catch { // Swallow any exceptions to avoid interfering with telemetry shutdown. } } private static ActivityModel CreateActivityJsonModel(Activity activity) => new( operationName: activity.OperationName, displayName: activity.DisplayName, duration: activity.Duration, identifiers: new( id: activity.Id, traceId: activity.TraceId.ToString(), spanId: activity.SpanId.ToString(), parentSpanId: activity.ParentSpanId.ToString(), parentId: activity.ParentId, rootId: activity.RootId ), source: new( name: activity.Source.Name, version: activity.Source.Version, tags: activity.Source.Tags?.ToDictionary() ), tags: activity.Tags.ToDictionary(), events: [.. activity.Events.Select(e => new EventModel( name: e.Name, timestamp: e.Timestamp, tags: e.Tags.ToDictionary() ))] ); } [JsonSerializable(typeof(TelemetryDiskLogger.ActivityModel))] internal partial class TelemetryDiskLoggerJsonSerializerContext : JsonSerializerContext;