Skip to content
Open
Show file tree
Hide file tree
Changes from 7 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
OpenTelemetry.Instrumentation.AWSLambda.AWSLambdaResourceBuilderExtensions
static OpenTelemetry.Instrumentation.AWSLambda.AWSLambdaResourceBuilderExtensions.AddAWSLambdaDetector(this OpenTelemetry.Resources.ResourceBuilder! builder, System.Action<OpenTelemetry.Instrumentation.AWSLambda.AWSLambdaInstrumentationOptions!>? configure = null) -> OpenTelemetry.Resources.ResourceBuilder!
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
// Copyright The OpenTelemetry Authors
// SPDX-License-Identifier: Apache-2.0

using OpenTelemetry.AWS;
using OpenTelemetry.Instrumentation.AWSLambda.Implementation;
using OpenTelemetry.Internal;
using OpenTelemetry.Resources;
using OpenTelemetry.Trace;

namespace OpenTelemetry.Instrumentation.AWSLambda;

/// <summary>
/// Extension methods to simplify registering of AWS Lambda resource detectors.
/// </summary>
public static class AWSLambdaResourceBuilderExtensions
{
/// <summary>
/// Enables AWS Lambda resource detector. Do not call this method while also calling <see cref="TracerProviderBuilderExtensions.AddAWSLambdaConfigurations(TracerProviderBuilder)" /> or <see cref="TracerProviderBuilderExtensions.AddAWSLambdaConfigurations(TracerProviderBuilder, System.Action{AWSLambdaInstrumentationOptions})" />.
/// </summary>
/// <param name="builder">The <see cref="ResourceBuilder"/> being configured.</param>
/// <param name="configure">Optional callback action for configuring <see cref="AWSLambdaInstrumentationOptions"/>.</param>
/// <returns>The instance of <see cref="ResourceBuilder"/> being configured.</returns>
public static ResourceBuilder AddAWSLambdaDetector(this ResourceBuilder builder, Action<AWSLambdaInstrumentationOptions>? configure = null)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What happens if this is called when also adding the resource detector implicitly via the instrumentation (

builder.ConfigureResource(x => x.AddDetector(new AWSLambdaResourceDetector(awsSemanticConventions)));
)? Couldn't this easily lead to double-detection of resources? I think it may be easy to misuse this method, if they are going to be in the same package, maybe it's better to enhance the instrumentation method with a parameter/add an option inside AWSLambdaInstrumentationOptions to add only resource detection without instrumentation? That would make it hard to accidentally add it twice.

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Its a valid point.
However just enhancing TracerProviderBuilderExtensions.AddAWSLambdaConfigurations to add only resource detection will not work in that case because the extension is exposed on TracerProviderBuilder. Resource detectors should be allowed to be added for logs and metrics too (similar to the other resource detectors) and be exposed on ResourceBuilder instead.

I enhanced the XML docs to make it easier to understand how the 2 extensions are expected to be used, should make it clearer to avoid double resource detection.
Let me know what you think.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Does it make sense to accept AWSLambdaInstrumentationOptions here? The detector is not an instrumentation, and indeed it seems like all options except SemanticConventionVersion are ignored.

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Was mostly trying to keep it close to the other detectors extensions. but its a valid point - removed the AWSLambdaInstrumentationOptions to use the default semantic convention version

Would appreciate another review please

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@Oberon00 🙏

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why not accept (just) the semantic convention version as parameter?

{
Guard.ThrowIfNull(builder);

var options = new AWSLambdaInstrumentationOptions();
configure?.Invoke(options);

var semanticConventionBuilder = new AWSSemanticConventions(options.SemanticConventionVersion);

return builder.AddDetector(new AWSLambdaResourceDetector(semanticConventionBuilder));
}
}
1 change: 1 addition & 0 deletions src/OpenTelemetry.Instrumentation.AWSLambda/CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ Released 2025-Nov-13
* Update Amazon.Lambda.Core dependency from 2.2.0 to 2.8.0 which reworks the internal
logic for determining the trace id created by AWS Lambda.
([#3410](https://github.com/open-telemetry/opentelemetry-dotnet-contrib/pull/3410))
* Implement AWS Lambda detector ([#3411](https://github.com/open-telemetry/opentelemetry-dotnet-contrib/pull/3411))

* Update .NET 10.0 NuGet package versions from `10.0.0-rc.2.25502.107` to `10.0.0`.
([#3403](https://github.com/open-telemetry/opentelemetry-dotnet-contrib/pull/3403))
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ public static TracerProviderBuilder AddAWSLambdaConfigurations(this TracerProvid
AddAWSLambdaConfigurations(builder, configure: null);

/// <summary>
/// Add AWS Lambda configurations.
/// Add AWS Lambda configurations. Do not call this method while also calling <see cref="AWSLambdaResourceBuilderExtensions.AddAWSLambdaDetector" />.
/// </summary>
/// <param name="builder"><see cref="TracerProviderBuilder"/> being configured.</param>
/// <param name="configure">AWS lambda instrumentation options.</param>
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,51 @@
// Copyright The OpenTelemetry Authors
// SPDX-License-Identifier: Apache-2.0

using OpenTelemetry.Resources;
using Xunit;

namespace OpenTelemetry.Instrumentation.AWSLambda.Tests;

public class AWSLambdaResourceBuilderExtensionsTests : IDisposable
{
// Expected Semantic Conventions
private const string AttributeCloudProvider = "cloud.provider";
private const string AttributeCloudRegion = "cloud.region";
private const string AttributeFaasName = "faas.name";
private const string AttributeFaasVersion = "faas.version";
private const string AttributeFaasInstance = "faas.instance";
private const string AttributeFaasMaxMemory = "faas.max_memory";

private readonly IDisposable environmentScope = EnvironmentVariableScope.Create(
("AWS_REGION", "us-east-1"),
("AWS_LAMBDA_FUNCTION_NAME", "testfunction"),
("AWS_LAMBDA_FUNCTION_VERSION", "latest"),
("AWS_LAMBDA_FUNCTION_MEMORY_SIZE", "128"),
("AWS_LAMBDA_LOG_STREAM_NAME", "2025/07/21/[$LATEST]7b176c212e954e62adfb9b5451cb5374"));

public void Dispose() => this.environmentScope.Dispose();

[Fact]
public void AssertAttributes()
{
var resourceBuilder = ResourceBuilder.CreateDefault();
resourceBuilder.AddAWSLambdaDetector();

var resource = resourceBuilder.Build();

var resourceAttributes = resource.Attributes
.ToDictionary(x => x.Key, x => x.Value);

Assert.Equal("aws", resourceAttributes[AttributeCloudProvider]);
Assert.Equal("us-east-1", resourceAttributes[AttributeCloudRegion]);
Assert.Equal("testfunction", resourceAttributes[AttributeFaasName]);
Assert.Equal("latest", resourceAttributes[AttributeFaasVersion]);
Assert.Equal("2025/07/21/[$LATEST]7b176c212e954e62adfb9b5451cb5374",
resourceAttributes[AttributeFaasInstance]);
Assert.Equal(134217728L, resourceAttributes[AttributeFaasMaxMemory]);
}

[Fact]
public void AssertArgumentNullException() =>
Assert.Throws<ArgumentNullException>(() => AWSLambdaResourceBuilderExtensions.AddAWSLambdaDetector(null!));
}