Skip to content

Commit 2666037

Browse files
[Tracer] Attribute Schema configuration: new configuration and v1 service naming (#4019)
Adds a new opt-in configuration `DD_TRACE_SPAN_ATTRIBUTE_SCHEMA` whose recognized values are "v1" or "v0" (the default value) and performs one (of several) v1 behaviors: the ServiceName for all spans are set to `$DD_SERVICE` instead of `$DD_SERVICE-<library>`.
1 parent a889aeb commit 2666037

File tree

141 files changed

+85652
-2695
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

141 files changed

+85652
-2695
lines changed

tracer/src/Datadog.Trace/ClrProfiler/AutoInstrumentation/AdoNet/DbScopeFactory.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -223,7 +223,7 @@ private static string GetServiceName(Tracer tracer, string dbTypeName)
223223
if (DbTypeName != dbTypeName)
224224
{
225225
// We cannot cache in the base class
226-
return $"{tracer.DefaultServiceName}-{dbTypeName}";
226+
return tracer.Settings.GetServiceName(tracer, dbTypeName);
227227
}
228228

229229
var serviceNameCache = _serviceNameCache;
@@ -239,7 +239,7 @@ private static string GetServiceName(Tracer tracer, string dbTypeName)
239239
// We create or replace the cache with the new service name
240240
// Slowpath
241241
var defaultServiceName = tracer.DefaultServiceName;
242-
serviceName = $"{defaultServiceName}-{dbTypeName}";
242+
serviceName = tracer.Settings.GetServiceName(tracer, dbTypeName);
243243
_serviceNameCache = new KeyValuePair<string, string>(defaultServiceName, serviceName);
244244
}
245245

tracer/src/Datadog.Trace/Configuration/ConfigurationKeys.cs

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -404,6 +404,14 @@ internal static partial class ConfigurationKeys
404404
/// <seealso cref="TracerSettings.DbmPropagationMode"/>
405405
public const string DbmPropagationMode = "DD_DBM_PROPAGATION_MODE";
406406

407+
/// <summary>
408+
/// Configuration key for setting the schema version for service naming and span attributes
409+
/// Accepted values are: "v1", "v0"
410+
/// Default value is "v0"
411+
/// </summary>
412+
/// <seealso cref="TracerSettings.MetadataSchemaVersion"/>
413+
public const string MetadataSchemaVersion = "DD_TRACE_SPAN_ATTRIBUTE_SCHEMA";
414+
407415
/// <summary>
408416
/// String constants for CI Visibility configuration keys.
409417
/// </summary>

tracer/src/Datadog.Trace/Configuration/ImmutableTracerSettings.cs

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -86,6 +86,7 @@ public ImmutableTracerSettings(TracerSettings settings)
8686
HttpClientExcludedUrlSubstrings = settings.HttpClientExcludedUrlSubstrings;
8787
HttpServerErrorStatusCodes = settings.HttpServerErrorStatusCodes;
8888
HttpClientErrorStatusCodes = settings.HttpClientErrorStatusCodes;
89+
MetadataSchemaVersion = settings.MetadataSchemaVersion;
8990
ServiceNameMappings = settings.ServiceNameMappings;
9091
TraceBufferSize = settings.TraceBufferSize;
9192
TraceBatchInterval = settings.TraceBatchInterval;
@@ -434,6 +435,11 @@ public ImmutableTracerSettings(TracerSettings settings)
434435
/// </summary>
435436
internal ImmutableAzureAppServiceSettings? AzureAppServiceMetadata { get; }
436437

438+
/// <summary>
439+
/// Gets the metadata schema version
440+
/// </summary>
441+
internal string MetadataSchemaVersion { get; }
442+
437443
/// <summary>
438444
/// Create a <see cref="ImmutableTracerSettings"/> populated from the default sources
439445
/// returned by <see cref="GlobalConfigurationSource.Instance"/>.

tracer/src/Datadog.Trace/Configuration/ServiceNames.cs

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,9 +13,11 @@ internal class ServiceNames
1313
{
1414
private readonly object _lock = new object();
1515
private Dictionary<string, string> _mappings = null;
16+
private bool _unifyServiceNames;
1617

17-
public ServiceNames(IDictionary<string, string> mappings)
18+
public ServiceNames(IDictionary<string, string> mappings, string metadataSchemaVersion)
1819
{
20+
_unifyServiceNames = metadataSchemaVersion == "v0" ? false : true;
1921
if (mappings?.Count > 0)
2022
{
2123
_mappings = new Dictionary<string, string>(mappings);
@@ -28,6 +30,10 @@ public string GetServiceName(string applicationName, string key)
2830
{
2931
return name;
3032
}
33+
else if (_unifyServiceNames)
34+
{
35+
return applicationName;
36+
}
3137
else
3238
{
3339
return $"{applicationName}-{key}";

tracer/src/Datadog.Trace/Configuration/TracerSettings.cs

Lines changed: 14 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -116,12 +116,13 @@ public TracerSettings(IConfigurationSource? source)
116116
var headerTagsNormalizationFixEnabled = source.GetBool(ConfigurationKeys.FeatureFlags.HeaderTagsNormalizationFixEnabled) ?? true;
117117
// Filter out tags with empty keys or empty values, and trim whitespaces
118118
HeaderTags = InitializeHeaderTags(inputHeaderTags, headerTagsNormalizationFixEnabled);
119+
MetadataSchemaVersion = ParseMetadataSchemaVersion(source.GetString(ConfigurationKeys.MetadataSchemaVersion));
119120

120121
var serviceNameMappings = source.GetDictionary(ConfigurationKeys.ServiceNameMappings)
121122
?.Where(kvp => !string.IsNullOrWhiteSpace(kvp.Key) && !string.IsNullOrWhiteSpace(kvp.Value))
122123
?.ToDictionary(kvp => kvp.Key.Trim(), kvp => kvp.Value.Trim());
123124

124-
ServiceNameMappings = new ServiceNames(serviceNameMappings);
125+
ServiceNameMappings = new ServiceNames(serviceNameMappings, MetadataSchemaVersion);
125126

126127
TracerMetricsEnabled = source.GetBool(ConfigurationKeys.TracerMetricsEnabled) ??
127128
// default value
@@ -609,6 +610,11 @@ public bool DiagnosticSourceEnabled
609610
/// </summary>
610611
internal ImmutableAzureAppServiceSettings? AzureAppServiceMetadata { get; set; }
611612

613+
/// <summary>
614+
/// Gets or sets the metadata schema version
615+
/// </summary>
616+
internal string MetadataSchemaVersion { get; set; }
617+
612618
/// <summary>
613619
/// Create a <see cref="TracerSettings"/> populated from the default sources
614620
/// returned by <see cref="GlobalConfigurationSource.Instance"/>.
@@ -701,6 +707,13 @@ private static IDictionary<string, string> InitializeHeaderTags(IDictionary<stri
701707
return headerTags;
702708
}
703709

710+
private static string ParseMetadataSchemaVersion(string? value) =>
711+
value switch
712+
{
713+
"v1" or "V1" => "v1",
714+
_ => "v0",
715+
};
716+
704717
internal static string[] TrimSplitString(string? textValues, char[] separators)
705718
{
706719
if (string.IsNullOrWhiteSpace(textValues))

tracer/test/Datadog.Trace.ClrProfiler.IntegrationTests/AWS/AwsSqsTests.cs

Lines changed: 15 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -26,18 +26,22 @@ public AwsSqsTests(ITestOutputHelper output)
2626
{
2727
}
2828

29-
public override Result ValidateIntegrationSpan(MockSpan span) =>
30-
span.Name switch
31-
{
32-
"sqs.request" => span.IsAwsSqs(),
33-
_ => Result.DefaultSuccess,
34-
};
29+
public static IEnumerable<object[]> GetEnabledConfig()
30+
=> from packageVersionArray in PackageVersions.AwsSqs
31+
from metadataSchemaVersion in new[] { "v0", "v1" }
32+
select new[] { packageVersionArray[0], metadataSchemaVersion };
33+
34+
public override Result ValidateIntegrationSpan(MockSpan span) => span.IsAwsSqs();
3535

3636
[SkippableTheory]
37-
[MemberData(nameof(PackageVersions.AwsSqs), MemberType = typeof(PackageVersions))]
37+
[MemberData(nameof(GetEnabledConfig))]
3838
[Trait("Category", "EndToEnd")]
39-
public async Task SubmitsTraces(string packageVersion)
39+
public async Task SubmitsTraces(string packageVersion, string metadataSchemaVersion)
4040
{
41+
SetEnvironmentVariable("DD_TRACE_SPAN_ATTRIBUTE_SCHEMA", metadataSchemaVersion);
42+
var isExternalSpan = metadataSchemaVersion == "v0";
43+
var clientSpanServiceName = isExternalSpan ? $"{EnvironmentHelper.FullSampleName}-aws-sqs" : EnvironmentHelper.FullSampleName;
44+
4145
using var telemetry = this.ConfigureTelemetry();
4246
using (var agent = EnvironmentHelper.GetMockAgent())
4347
using (RunSampleAndWaitForExit(agent, packageVersion: packageVersion))
@@ -50,17 +54,13 @@ public async Task SubmitsTraces(string packageVersion)
5054
var frameworkName = "NetCore";
5155
#endif
5256
var spans = agent.WaitForSpans(expectedCount);
53-
foreach (var span in spans)
54-
{
55-
// TODO: Refactor to use ValidateIntegrationSpans later once we figure out how to best handle the combination of "http-client" and "sqs" service names produced by the integration
56-
var result = ValidateIntegrationSpan(span);
57-
Assert.True(result.Success, result.ToString());
58-
}
57+
var sqsSpans = spans.Where(span => span.Name == "sqs.request");
58+
ValidateIntegrationSpans(sqsSpans, expectedServiceName: clientSpanServiceName, isExternalSpan);
5959

6060
var host = Environment.GetEnvironmentVariable("AWS_SQS_HOST");
6161

6262
var settings = VerifyHelper.GetSpanVerifierSettings();
63-
settings.UseFileName($"{nameof(AwsSqsTests)}.{frameworkName}");
63+
settings.UseFileName($"{nameof(AwsSqsTests)}.{frameworkName}.Schema{metadataSchemaVersion.ToUpper()}");
6464
if (!string.IsNullOrWhiteSpace(host))
6565
{
6666
settings.AddSimpleScrubber(host, "localhost:00000");

tracer/test/Datadog.Trace.ClrProfiler.IntegrationTests/AdoNet/DapperTests.cs

Lines changed: 9 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -23,37 +23,28 @@ public DapperTests(ITestOutputHelper output)
2323

2424
[SkippableFact]
2525
[Trait("Category", "EndToEnd")]
26-
public void SubmitsTraces()
27-
{
28-
const int expectedSpanCount = 17;
29-
const string dbType = "postgres";
30-
const string expectedOperationName = dbType + ".query";
31-
const string expectedServiceName = "Samples.Dapper-" + dbType;
32-
33-
using (var agent = EnvironmentHelper.GetMockAgent())
34-
using (RunSampleAndWaitForExit(agent))
35-
{
36-
var spans = agent.WaitForSpans(expectedSpanCount, operationName: expectedOperationName);
37-
Assert.Equal(expectedSpanCount, spans.Count);
38-
ValidateIntegrationSpans(spans, expectedServiceName: expectedServiceName);
39-
}
40-
}
26+
public void SubmitsTracesV0() => RunTest("v0");
4127

4228
[SkippableFact]
4329
[Trait("Category", "EndToEnd")]
44-
public void SubmitsTracesWithNetStandard()
30+
public void SubmitsTracesV1() => RunTest("v1");
31+
32+
private void RunTest(string metadataSchemaVersion)
4533
{
4634
const int expectedSpanCount = 17;
4735
const string dbType = "postgres";
4836
const string expectedOperationName = dbType + ".query";
49-
const string expectedServiceName = "Samples.Dapper-" + dbType;
37+
38+
SetEnvironmentVariable("DD_TRACE_SPAN_ATTRIBUTE_SCHEMA", metadataSchemaVersion);
39+
var isExternalSpan = metadataSchemaVersion == "v0";
40+
var clientSpanServiceName = isExternalSpan ? $"{EnvironmentHelper.FullSampleName}-{dbType}" : EnvironmentHelper.FullSampleName;
5041

5142
using (var agent = EnvironmentHelper.GetMockAgent())
5243
using (RunSampleAndWaitForExit(agent))
5344
{
5445
var spans = agent.WaitForSpans(expectedSpanCount, operationName: expectedOperationName);
5546
Assert.Equal(expectedSpanCount, spans.Count);
56-
ValidateIntegrationSpans(spans, expectedServiceName: expectedServiceName);
47+
ValidateIntegrationSpans(spans, expectedServiceName: clientSpanServiceName, isExternalSpan);
5748
}
5849
}
5950
}

tracer/test/Datadog.Trace.ClrProfiler.IntegrationTests/AdoNet/FakeCommandTests.cs

Lines changed: 12 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,13 @@ public FakeCommandTests(ITestOutputHelper output)
2323

2424
[SkippableFact]
2525
[Trait("Category", "EndToEnd")]
26-
public void SubmitsTraces()
26+
public void SubmitsTracesV0() => RunTest("v0");
27+
28+
[SkippableFact]
29+
[Trait("Category", "EndToEnd")]
30+
public void SubmitsTracesV1() => RunTest("v1");
31+
32+
private void RunTest(string metadataSchemaVersion)
2733
{
2834
// ALWAYS: 91 spans
2935
// - FakeCommand: 21 spans (3 groups * 7 spans)
@@ -37,7 +43,10 @@ public void SubmitsTraces()
3743
const int expectedSpanCount = 91;
3844
const string dbType = "fake";
3945
const string expectedOperationName = dbType + ".query";
40-
const string expectedServiceName = "Samples.FakeDbCommand-fake";
46+
47+
SetEnvironmentVariable("DD_TRACE_SPAN_ATTRIBUTE_SCHEMA", metadataSchemaVersion);
48+
var isExternalSpan = metadataSchemaVersion == "v0";
49+
var clientSpanServiceName = isExternalSpan ? $"{EnvironmentHelper.FullSampleName}-{dbType}" : EnvironmentHelper.FullSampleName;
4150

4251
using var telemetry = this.ConfigureTelemetry();
4352
using var agent = EnvironmentHelper.GetMockAgent();
@@ -46,7 +55,7 @@ public void SubmitsTraces()
4655
int actualSpanCount = spans.Count(s => s.ParentId.HasValue); // Remove unexpected DB spans from the calculation
4756

4857
Assert.Equal(expectedSpanCount, actualSpanCount);
49-
ValidateIntegrationSpans(spans, expectedServiceName: expectedServiceName);
58+
ValidateIntegrationSpans(spans, expectedServiceName: clientSpanServiceName, isExternalSpan);
5059

5160
foreach (var span in spans)
5261
{

tracer/test/Datadog.Trace.ClrProfiler.IntegrationTests/AdoNet/MicrosoftDataSqlClientTests.cs

Lines changed: 13 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44
// </copyright>
55

66
using System;
7+
using System.Collections.Generic;
78
using System.Linq;
89
using Datadog.Trace.Configuration;
910
using Datadog.Trace.TestHelpers;
@@ -21,13 +22,18 @@ public MicrosoftDataSqlClientTests(ITestOutputHelper output)
2122
SetServiceVersion("1.0.0");
2223
}
2324

25+
public static IEnumerable<object[]> GetEnabledConfig()
26+
=> from packageVersionArray in PackageVersions.MicrosoftDataSqlClient
27+
from metadataSchemaVersion in new[] { "v0", "v1" }
28+
select new[] { packageVersionArray[0], metadataSchemaVersion };
29+
2430
public override Result ValidateIntegrationSpan(MockSpan span) => span.IsSqlClient();
2531

2632
[SkippableTheory]
27-
[MemberData(nameof(PackageVersions.MicrosoftDataSqlClient), MemberType = typeof(PackageVersions))]
33+
[MemberData(nameof(GetEnabledConfig))]
2834
[Trait("Category", "EndToEnd")]
2935
[Trait("RunOnWindows", "True")]
30-
public void SubmitsTraces(string packageVersion)
36+
public void SubmitsTraces(string packageVersion, string metadataSchemaVersion)
3137
{
3238
// ALWAYS: 133 spans
3339
// - SqlCommand: 21 spans (3 groups * 7 spans)
@@ -60,7 +66,10 @@ public void SubmitsTraces(string packageVersion)
6066
var expectedSpanCount = isVersion4 ? 91 : 147;
6167
const string dbType = "sql-server";
6268
const string expectedOperationName = dbType + ".query";
63-
const string expectedServiceName = "Samples.Microsoft.Data.SqlClient-" + dbType;
69+
70+
SetEnvironmentVariable("DD_TRACE_SPAN_ATTRIBUTE_SCHEMA", metadataSchemaVersion);
71+
var isExternalSpan = metadataSchemaVersion == "v0";
72+
var clientSpanServiceName = isExternalSpan ? $"{EnvironmentHelper.FullSampleName}-{dbType}" : EnvironmentHelper.FullSampleName;
6473

6574
using var telemetry = this.ConfigureTelemetry();
6675
using var agent = EnvironmentHelper.GetMockAgent();
@@ -69,7 +78,7 @@ public void SubmitsTraces(string packageVersion)
6978
int actualSpanCount = spans.Count(s => s.ParentId.HasValue); // Remove unexpected DB spans from the calculation
7079

7180
Assert.Equal(expectedSpanCount, actualSpanCount);
72-
ValidateIntegrationSpans(spans, expectedServiceName: expectedServiceName);
81+
ValidateIntegrationSpans(spans, expectedServiceName: clientSpanServiceName, isExternalSpan);
7382
telemetry.AssertIntegrationEnabled(IntegrationId.SqlClient);
7483
}
7584

tracer/test/Datadog.Trace.ClrProfiler.IntegrationTests/AdoNet/MicrosoftDataSqliteTests.cs

Lines changed: 13 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66
#if !NETCOREAPP2_1
77

88
using System;
9+
using System.Collections.Generic;
910
using System.Linq;
1011
using Datadog.Trace.Configuration;
1112
using Datadog.Trace.TestHelpers;
@@ -22,14 +23,19 @@ public MicrosoftDataSqliteTests(ITestOutputHelper output)
2223
SetServiceVersion("1.0.0");
2324
}
2425

26+
public static IEnumerable<object[]> GetEnabledConfig()
27+
=> from packageVersionArray in PackageVersions.MicrosoftDataSqlite
28+
from metadataSchemaVersion in new[] { "v0", "v1" }
29+
select new[] { packageVersionArray[0], metadataSchemaVersion };
30+
2531
public override Result ValidateIntegrationSpan(MockSpan span) => span.IsSqlite();
2632

2733
[SkippableTheory]
28-
[MemberData(nameof(PackageVersions.MicrosoftDataSqlite), MemberType = typeof(PackageVersions))]
34+
[MemberData(nameof(GetEnabledConfig))]
2935
[Trait("Category", "EndToEnd")]
3036
[Trait("RunOnWindows", "True")]
3137
[Trait("Category", "ArmUnsupported")]
32-
public void SubmitsTraces(string packageVersion)
38+
public void SubmitsTraces(string packageVersion, string metadataSchemaVersion)
3339
{
3440
#if NETCOREAPP3_0
3541
if (!string.IsNullOrEmpty(Environment.GetEnvironmentVariable("IsAlpine")) // set in dockerfile
@@ -43,15 +49,18 @@ public void SubmitsTraces(string packageVersion)
4349
const int expectedSpanCount = 91;
4450
const string dbType = "sqlite";
4551
const string expectedOperationName = dbType + ".query";
46-
const string expectedServiceName = "Samples.Microsoft.Data.Sqlite-" + dbType;
52+
53+
SetEnvironmentVariable("DD_TRACE_SPAN_ATTRIBUTE_SCHEMA", metadataSchemaVersion);
54+
var isExternalSpan = metadataSchemaVersion == "v0";
55+
var clientSpanServiceName = isExternalSpan ? $"{EnvironmentHelper.FullSampleName}-{dbType}" : EnvironmentHelper.FullSampleName;
4756

4857
using var telemetry = this.ConfigureTelemetry();
4958
using var agent = EnvironmentHelper.GetMockAgent();
5059
using var process = RunSampleAndWaitForExit(agent, packageVersion: packageVersion);
5160
var spans = agent.WaitForSpans(expectedSpanCount, operationName: expectedOperationName);
5261

5362
Assert.Equal(expectedSpanCount, spans.Count);
54-
ValidateIntegrationSpans(spans, expectedServiceName: expectedServiceName);
63+
ValidateIntegrationSpans(spans, expectedServiceName: clientSpanServiceName, isExternalSpan);
5564

5665
telemetry.AssertIntegrationEnabled(IntegrationId.Sqlite);
5766
}

0 commit comments

Comments
 (0)