Skip to content
This repository was archived by the owner on Jul 30, 2024. It is now read-only.

Commit 291f996

Browse files
committed
Introduce LoggerDiagnosticsService for improved NuGetGallery.Core logging (#378)
1 parent e8b05bd commit 291f996

16 files changed

Lines changed: 625 additions & 16 deletions

NuGet.Jobs.sln

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -113,6 +113,8 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Validation.Common.Job", "sr
113113
EndProject
114114
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "PackageHash", "src\PackageHash\PackageHash.csproj", "{40843020-6F0A-48F0-AC28-42FFE3A5C21E}"
115115
EndProject
116+
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Validation.Common.Job.Tests", "tests\Validation.Common.Job.Tests\Validation.Common.Job.Tests.csproj", "{430F63C7-20C2-4872-AC3E-DDE846E50AA4}"
117+
EndProject
116118
Global
117119
GlobalSection(SolutionConfigurationPlatforms) = preSolution
118120
Debug|Any CPU = Debug|Any CPU
@@ -289,6 +291,10 @@ Global
289291
{40843020-6F0A-48F0-AC28-42FFE3A5C21E}.Debug|Any CPU.Build.0 = Debug|Any CPU
290292
{40843020-6F0A-48F0-AC28-42FFE3A5C21E}.Release|Any CPU.ActiveCfg = Release|Any CPU
291293
{40843020-6F0A-48F0-AC28-42FFE3A5C21E}.Release|Any CPU.Build.0 = Release|Any CPU
294+
{430F63C7-20C2-4872-AC3E-DDE846E50AA4}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
295+
{430F63C7-20C2-4872-AC3E-DDE846E50AA4}.Debug|Any CPU.Build.0 = Debug|Any CPU
296+
{430F63C7-20C2-4872-AC3E-DDE846E50AA4}.Release|Any CPU.ActiveCfg = Release|Any CPU
297+
{430F63C7-20C2-4872-AC3E-DDE846E50AA4}.Release|Any CPU.Build.0 = Release|Any CPU
292298
EndGlobalSection
293299
GlobalSection(SolutionProperties) = preSolution
294300
HideSolutionNode = FALSE
@@ -336,6 +342,7 @@ Global
336342
{B4B7564A-965B-447B-927F-6749E2C08880} = {6A776396-02B1-475D-A104-26940ADB04AB}
337343
{FA87D075-A934-4443-8D0B-5DB32640B6D7} = {678D7B14-F8BC-4193-99AF-2EE8AA390A02}
338344
{40843020-6F0A-48F0-AC28-42FFE3A5C21E} = {FA5644B5-4F08-43F6-86B3-039374312A47}
345+
{430F63C7-20C2-4872-AC3E-DDE846E50AA4} = {6A776396-02B1-475D-A104-26940ADB04AB}
339346
EndGlobalSection
340347
GlobalSection(ExtensibilityGlobals) = postSolution
341348
SolutionGuid = {284A7AC3-FB43-4F1F-9C9C-2AF0E1F46C2B}

src/NuGet.Services.Validation.Orchestrator/Job.cs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,11 +25,13 @@
2525
using NuGet.Jobs.Validation.PackageSigning.Storage;
2626
using NuGet.Services.Configuration;
2727
using NuGet.Services.KeyVault;
28+
using NuGet.Services.Logging;
2829
using NuGet.Services.ServiceBus;
2930
using NuGet.Services.Validation.Orchestrator.Telemetry;
3031
using NuGet.Services.Validation.PackageCertificates;
3132
using NuGet.Services.Validation.PackageSigning;
3233
using NuGet.Services.Validation.Vcs;
34+
using NuGetGallery.Diagnostics;
3335
using NuGetGallery.Services;
3436

3537
namespace NuGet.Services.Validation.Orchestrator
@@ -235,6 +237,8 @@ private void ConfigureJobServices(IServiceCollection services, IConfigurationRoo
235237
services.AddTransient<IMessageService, MessageService>();
236238
services.AddTransient<ICommonTelemetryService, CommonTelemetryService>();
237239
services.AddTransient<ITelemetryService, TelemetryService>();
240+
services.AddTransient<ITelemetryClient, TelemetryClientWrapper>();
241+
services.AddTransient<IDiagnosticsService, LoggerDiagnosticsService>();
238242
services.AddSingleton(new TelemetryClient());
239243
services.AddTransient<IValidationOutcomeProcessor, ValidationOutcomeProcessor>();
240244
services.AddSingleton(p =>

src/NuGet.Services.Validation.Orchestrator/NuGet.Services.Validation.Orchestrator.csproj

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -108,7 +108,7 @@
108108
</ItemGroup>
109109
<ItemGroup>
110110
<PackageReference Include="NuGet.Services.Validation.Issues">
111-
<Version>2.18.0</Version>
111+
<Version>2.19.1</Version>
112112
</PackageReference>
113113
</ItemGroup>
114114
<ItemGroup>

src/NuGet.Services.Validation.Orchestrator/Telemetry/TelemetryService.cs

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44
using System;
55
using System.Collections.Generic;
66
using Microsoft.ApplicationInsights;
7+
using NuGet.Services.Logging;
78
using NuGetGallery;
89

910
namespace NuGet.Services.Validation.Orchestrator.Telemetry
@@ -46,9 +47,9 @@ public class TelemetryService : ITelemetryService
4647
private const string HashAlgorithm = "HashAlgorithm";
4748
private const string StreamType = "StreamType";
4849

49-
private readonly TelemetryClient _telemetryClient;
50+
private readonly ITelemetryClient _telemetryClient;
5051

51-
public TelemetryService(TelemetryClient telemetryClient)
52+
public TelemetryService(ITelemetryClient telemetryClient)
5253
{
5354
_telemetryClient = telemetryClient ?? throw new ArgumentNullException(nameof(telemetryClient));
5455
}

src/Validation.Common.Job/CommonTelemetryService.cs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33

44
using System;
55
using System.Collections.Generic;
6-
using Microsoft.ApplicationInsights;
6+
using NuGet.Services.Logging;
77

88
namespace NuGet.Jobs.Validation
99
{
@@ -13,9 +13,9 @@ public class CommonTelemetryService : ICommonTelemetryService
1313
private const string PackageUri = "PackageUri";
1414
private const string PackageSize = "PackageSize";
1515

16-
private readonly TelemetryClient _telemetryClient;
16+
private readonly ITelemetryClient _telemetryClient;
1717

18-
public CommonTelemetryService(TelemetryClient telemetryClient)
18+
public CommonTelemetryService(ITelemetryClient telemetryClient)
1919
{
2020
_telemetryClient = telemetryClient ?? throw new ArgumentNullException(nameof(telemetryClient));
2121
}

src/Validation.Common.Job/IPackageDownloader.cs

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,7 @@
1-
using System;
1+
// Copyright (c) .NET Foundation. All rights reserved.
2+
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
3+
4+
using System;
25
using System.IO;
36
using System.Threading;
47
using System.Threading.Tasks;

src/Validation.Common.Job/JsonConfigurationJob.cs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,9 +17,11 @@
1717
using NuGet.Jobs.Configuration;
1818
using NuGet.Services.Configuration;
1919
using NuGet.Services.KeyVault;
20+
using NuGet.Services.Logging;
2021
using NuGet.Services.ServiceBus;
2122
using NuGet.Services.Validation;
2223
using NuGetGallery;
24+
using NuGetGallery.Diagnostics;
2325

2426
namespace NuGet.Jobs.Validation
2527
{
@@ -107,7 +109,9 @@ private void ConfigureDefaultJobServices(IServiceCollection services, IConfigura
107109
services.Configure<ServiceBusConfiguration>(configurationRoot.GetSection(ServiceBusConfigurationSectionName));
108110

109111
services.AddSingleton(new TelemetryClient());
112+
services.AddTransient<ITelemetryClient, TelemetryClientWrapper>();
110113
services.AddTransient<ICommonTelemetryService, CommonTelemetryService>();
114+
services.AddTransient<IDiagnosticsService, LoggerDiagnosticsService>();
111115
services.AddTransient<IPackageDownloader, PackageDownloader>();
112116

113117
services.AddScoped<IValidationEntitiesContext>(p =>
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
// Copyright (c) .NET Foundation. All rights reserved.
2+
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
3+
4+
using System;
5+
using Microsoft.Extensions.Logging;
6+
using NuGet.Services.Logging;
7+
using NuGetGallery.Diagnostics;
8+
9+
namespace NuGet.Jobs.Validation
10+
{
11+
public class LoggerDiagnosticsService : IDiagnosticsService
12+
{
13+
private readonly ILoggerFactory _loggerFactory;
14+
private readonly ITelemetryClient _telemetryClient;
15+
16+
public LoggerDiagnosticsService(ILoggerFactory loggerFactory, ITelemetryClient telemetryClient)
17+
{
18+
_loggerFactory = loggerFactory ?? throw new ArgumentNullException(nameof(loggerFactory));
19+
_telemetryClient = telemetryClient ?? throw new ArgumentNullException(nameof(telemetryClient));
20+
}
21+
22+
public IDiagnosticsSource GetSource(string name)
23+
{
24+
return new LoggerDiagnosticsSource(
25+
_telemetryClient,
26+
_loggerFactory.CreateLogger(name));
27+
}
28+
}
29+
}
Lines changed: 139 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,139 @@
1+
// Copyright (c) .NET Foundation. All rights reserved.
2+
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
3+
4+
using System;
5+
using System.Collections;
6+
using System.Collections.Generic;
7+
using System.Diagnostics;
8+
using System.Runtime.CompilerServices;
9+
using Microsoft.Extensions.Logging;
10+
using NuGet.Services.Logging;
11+
using NuGetGallery.Diagnostics;
12+
13+
namespace NuGet.Jobs.Validation
14+
{
15+
public class LoggerDiagnosticsSource : IDiagnosticsSource
16+
{
17+
private readonly ITelemetryClient _telemetryClient;
18+
private readonly ILogger _logger;
19+
20+
public LoggerDiagnosticsSource(ITelemetryClient telemetryClient, ILogger logger)
21+
{
22+
_telemetryClient = telemetryClient ?? throw new ArgumentNullException(nameof(telemetryClient));
23+
_logger = logger ?? throw new ArgumentNullException(nameof(logger));
24+
}
25+
26+
public void ExceptionEvent(Exception exception)
27+
{
28+
_telemetryClient.TrackException(exception);
29+
}
30+
31+
public void PerfEvent(
32+
string name,
33+
TimeSpan time,
34+
IEnumerable<KeyValuePair<string, object>> payload)
35+
{
36+
_telemetryClient.TrackMetric(
37+
name,
38+
time.TotalMilliseconds,
39+
GetProperties(payload));
40+
}
41+
42+
public void TraceEvent(
43+
TraceEventType type,
44+
int id,
45+
string message,
46+
[CallerMemberName] string member = null,
47+
[CallerFilePath] string file = null,
48+
[CallerLineNumber] int line = 0)
49+
{
50+
_logger.Log(
51+
TraceEventTypeToLogLevel(type),
52+
id,
53+
state: new TraceState(type, id, message, member, file, line),
54+
exception: null,
55+
formatter: (s, e) => s.Message);
56+
}
57+
58+
private static LogLevel TraceEventTypeToLogLevel(TraceEventType type)
59+
{
60+
switch (type)
61+
{
62+
case TraceEventType.Critical:
63+
return LogLevel.Critical;
64+
case TraceEventType.Error:
65+
return LogLevel.Error;
66+
case TraceEventType.Warning:
67+
return LogLevel.Warning;
68+
case TraceEventType.Information:
69+
return LogLevel.Information;
70+
default:
71+
return LogLevel.Trace;
72+
}
73+
}
74+
75+
private static IDictionary<string, string> GetProperties(
76+
IEnumerable<KeyValuePair<string, object>> payload)
77+
{
78+
if (payload == null)
79+
{
80+
return null;
81+
}
82+
83+
var dictionary = new Dictionary<string, string>();
84+
foreach (var pair in payload)
85+
{
86+
dictionary[pair.Key] = pair.Value?.ToString();
87+
}
88+
89+
return dictionary;
90+
}
91+
92+
/// <summary>
93+
/// The parameters provided to <see cref="TraceEvent(TraceEventType, int, string, string, string, int)"/>. This
94+
/// type implements <see cref="IEnumerable{KeyValuePair{string, object}}" /> because Serilog uses this to
95+
/// populate the Application Insights custom dimensions property bag.
96+
/// </summary>
97+
public class TraceState : IEnumerable<KeyValuePair<string, object>>
98+
{
99+
private readonly Dictionary<string, object> _pairs;
100+
101+
public TraceState(TraceEventType traceEventType, int id, string message, string member, string file, int line)
102+
{
103+
TraceEventType = traceEventType;
104+
Id = id;
105+
Message = message;
106+
Member = member;
107+
File = file;
108+
Line = line;
109+
110+
_pairs = new Dictionary<string, object>
111+
{
112+
{ nameof(TraceEventType), TraceEventType },
113+
{ nameof(Id), Id },
114+
{ nameof(Message), Message },
115+
{ nameof(Member), Member },
116+
{ nameof(File), File },
117+
{ nameof(Line), Line },
118+
};
119+
}
120+
121+
public TraceEventType TraceEventType { get; }
122+
public int Id { get; }
123+
public string Message { get; }
124+
public string Member { get; }
125+
public string File { get; }
126+
public int Line { get; }
127+
128+
public IEnumerator<KeyValuePair<string, object>> GetEnumerator()
129+
{
130+
return _pairs.GetEnumerator();
131+
}
132+
133+
IEnumerator IEnumerable.GetEnumerator()
134+
{
135+
return _pairs.GetEnumerator();
136+
}
137+
}
138+
}
139+
}

src/Validation.Common.Job/Validation.Common.Job.csproj

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -41,6 +41,8 @@
4141
<Compile Include="ExceptionExtensions.cs" />
4242
<Compile Include="ICommonTelemetryService.cs" />
4343
<Compile Include="IPackageDownloader.cs" />
44+
<Compile Include="LoggerDiagnosticsService.cs" />
45+
<Compile Include="LoggerDiagnosticsSource.cs" />
4446
<Compile Include="PackageDownloader.cs" />
4547
<Compile Include="Properties\AssemblyInfo.cs" />
4648
<Compile Include="Storage\AddStatusResult.cs" />
@@ -72,19 +74,19 @@
7274
<Version>4.7.0-preview1-4886</Version>
7375
</PackageReference>
7476
<PackageReference Include="NuGet.Services.Configuration">
75-
<Version>2.18.0</Version>
77+
<Version>2.19.1</Version>
7678
</PackageReference>
7779
<PackageReference Include="NuGet.Services.Logging">
78-
<Version>2.18.0</Version>
80+
<Version>2.19.1</Version>
7981
</PackageReference>
8082
<PackageReference Include="NuGet.Services.Storage">
81-
<Version>2.18.0</Version>
83+
<Version>2.19.1</Version>
8284
</PackageReference>
8385
<PackageReference Include="NuGet.Services.Validation">
84-
<Version>2.18.0</Version>
86+
<Version>2.19.1</Version>
8587
</PackageReference>
8688
<PackageReference Include="NuGetGallery.Core">
87-
<Version>4.4.4-dev-25969</Version>
89+
<Version>4.4.4-dev-26021</Version>
8890
</PackageReference>
8991
<PackageReference Include="Serilog">
9092
<Version>2.5.0</Version>

0 commit comments

Comments
 (0)