Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[OpenTelemetry.Instrumentation.AWSLambda] Do not crash on empty LambdaContext #2457

Merged
Merged
Show file tree
Hide file tree
Changes from all 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
4 changes: 4 additions & 0 deletions src/OpenTelemetry.Instrumentation.AWSLambda/CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,10 @@

## Unreleased

* Trace instrumentation will not fail with an exception
if empty `LambdaContext` instance is passed.
([#2457](https://github.com/open-telemetry/opentelemetry-dotnet-contrib/pull/2457))

## 1.10.0-rc.1

Released 2025-Jan-06
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -170,14 +170,19 @@ internal IEnumerable<KeyValuePair<string, object>> GetFunctionTags<TInput>(TInpu
return items.Length >= 5 ? items[4] : null;
}

private static string GetFaasId(string functionArn)
private static string? GetFaasId(string? functionArn)
{
if (string.IsNullOrEmpty(functionArn))
{
return null;
}

var faasId = functionArn;

// According to faas.id description https://github.com/open-telemetry/opentelemetry-specification/blob/main/specification/trace/semantic_conventions/instrumentation/aws-lambda.md#all-triggers
// the 8th part of arn (function version or alias, see https://docs.aws.amazon.com/lambda/latest/dg/lambda-api-permissions-ref.html)
// should not be included into faas.id
var items = functionArn.Split(':');
var items = functionArn!.Split(':');
if (items.Length >= 8)
{
faasId = string.Join(":", items.Take(7));
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -264,6 +264,35 @@ public void OnFunctionStart_ColdStart_ColdStartTagHasCorrectValue(int invocation
Assert.Contains(activity.TagObjects, x => x.Key == ExpectedSemanticConventions.AttributeFaasColdStart && expectedColdStartValue.Equals(x.Value));
}

[Fact]
public async Task TraceAsyncDoesNotCrashForEmptyLambdaContext()
{
var emptyLambdaContext = new SampleLambdaContext
{
AwsRequestId = null!,
ClientContext = null,
FunctionName = null!,
FunctionVersion = null!,
Identity = null!,
InvokedFunctionArn = null!,
Logger = null!,
LogGroupName = null!,
LogStreamName = null!,
MemoryLimitInMB = 0,
RemainingTime = TimeSpan.Zero,
};

using var tracerProvider = Sdk.CreateTracerProviderBuilder()
.AddAWSLambdaConfigurations(opt =>
{
opt.SemanticConventionVersion = SemanticConventionVersion.Latest;
})
.Build();

// We simply verify that no exception is thrown here.
await AWSLambdaWrapper.TraceAsync(tracerProvider, this.sampleHandlers.SampleHandlerAsyncInputAndNoReturn, "TestStream", emptyLambdaContext);
}

private static ActivityContext CreateParentContext()
{
var traceId = ActivityTraceId.CreateFromString(TraceId.AsSpan());
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,25 +7,25 @@ namespace OpenTelemetry.Instrumentation.AWSLambda.Tests;

internal class SampleLambdaContext : ILambdaContext
{
public string AwsRequestId { get; } = "testrequestid";
public string AwsRequestId { get; set; } = "testrequestid";

public IClientContext? ClientContext { get; }
public IClientContext? ClientContext { get; set; }

public string FunctionName { get; } = "testfunction";
public string FunctionName { get; set; } = "testfunction";

public string FunctionVersion { get; } = "latest";
public string FunctionVersion { get; set; } = "latest";

public ICognitoIdentity? Identity { get; }
public ICognitoIdentity? Identity { get; set; }

public string InvokedFunctionArn { get; } = "arn:aws:lambda:us-east-1:111111111111:function:testfunction";
public string InvokedFunctionArn { get; set; } = "arn:aws:lambda:us-east-1:111111111111:function:testfunction";

public ILambdaLogger? Logger { get; }
public ILambdaLogger? Logger { get; set; }

public string? LogGroupName { get; }
public string? LogGroupName { get; set; }

public string? LogStreamName { get; }
public string? LogStreamName { get; set; }

public int MemoryLimitInMB { get; }
public int MemoryLimitInMB { get; set; }

public TimeSpan RemainingTime { get; }
public TimeSpan RemainingTime { get; set; }
}
Loading