Skip to content

Commit

Permalink
lambda instrumentation - support for flush timeout (#825)
Browse files Browse the repository at this point in the history
* lambda instrumentation - support for flush timeout

* Update instrumentation/opentelemetry-instrumentation-aws-lambda/tests/test_aws_lambda_instrumentation_manual.py

Co-authored-by: (Eliseo) Nathaniel Ruiz Nowell <[email protected]>

* Update instrumentation/opentelemetry-instrumentation-aws-lambda/tests/test_aws_lambda_instrumentation_manual.py

Co-authored-by: (Eliseo) Nathaniel Ruiz Nowell <[email protected]>

* fixing lint

* fixing django lint

Co-authored-by: (Eliseo) Nathaniel Ruiz Nowell <[email protected]>
  • Loading branch information
kuba-wu and NathanielRN authored Dec 14, 2021
1 parent 444e0a1 commit 07f8146
Show file tree
Hide file tree
Showing 6 changed files with 54 additions and 2 deletions.
4 changes: 4 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,10 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0

## [Unreleased](https://github.com/open-telemetry/opentelemetry-python/compare/v1.7.0-0.26b0...HEAD)

### Added

- `opentelemetry-instrumentation-aws-lambda` Adds support for configurable flush timeout via `OTEL_INSTRUMENTATION_AWS_LAMBDA_FLUSH_TIMEOUT` property. ([#825](https://github.com/open-telemetry/opentelemetry-python-contrib/pull/825))

### Fixed

- `opentelemetry-exporter-richconsole` Fixed attribute error on parentless spans.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -97,6 +97,9 @@ def custom_event_context_extractor(lambda_event):
_HANDLER = "_HANDLER"
_X_AMZN_TRACE_ID = "_X_AMZN_TRACE_ID"
ORIG_HANDLER = "ORIG_HANDLER"
OTEL_INSTRUMENTATION_AWS_LAMBDA_FLUSH_TIMEOUT = (
"OTEL_INSTRUMENTATION_AWS_LAMBDA_FLUSH_TIMEOUT"
)


def _default_event_context_extractor(lambda_event: Any) -> Context:
Expand Down Expand Up @@ -167,6 +170,7 @@ def _determine_parent_context(
def _instrument(
wrapped_module_name,
wrapped_function_name,
flush_timeout,
event_context_extractor: Callable[[Any], Context],
tracer_provider: TracerProvider = None,
):
Expand Down Expand Up @@ -222,7 +226,7 @@ def _instrumented_lambda_handler_call(
# NOTE: `force_flush` before function quit in case of Lambda freeze.
# Assumes we are using the OpenTelemetry SDK implementation of the
# `TracerProvider`.
_tracer_provider.force_flush()
_tracer_provider.force_flush(flush_timeout)
except Exception: # pylint: disable=broad-except
logger.error(
"TracerProvider was missing `force_flush` method. This is necessary in case of a Lambda freeze and would exist in the OTel SDK implementation."
Expand Down Expand Up @@ -262,9 +266,22 @@ def _instrument(self, **kwargs):
self._wrapped_function_name,
) = lambda_handler.rsplit(".", 1)

flush_timeout_env = os.environ.get(
OTEL_INSTRUMENTATION_AWS_LAMBDA_FLUSH_TIMEOUT, ""
)
flush_timeout = 30000
try:
flush_timeout = int(flush_timeout_env)
except ValueError:
logger.warning(
"Could not convert OTEL_INSTRUMENTATION_AWS_LAMBDA_FLUSH_TIMEOUT value %s to int",
flush_timeout_env,
)

_instrument(
self._wrapped_module_name,
self._wrapped_function_name,
flush_timeout,
event_context_extractor=kwargs.get(
"event_context_extractor", _default_event_context_extractor
),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@
from opentelemetry.instrumentation.aws_lambda import (
_HANDLER,
_X_AMZN_TRACE_ID,
OTEL_INSTRUMENTATION_AWS_LAMBDA_FLUSH_TIMEOUT,
AwsLambdaInstrumentor,
)
from opentelemetry.propagate import get_global_textmap
Expand Down Expand Up @@ -246,3 +247,30 @@ def custom_event_context_extractor(lambda_event):
self.assertTrue(parent_context.is_remote)

test_env_patch.stop()

def test_lambda_no_error_with_invalid_flush_timeout(self):

test_env_patch = mock.patch.dict(
"os.environ",
{
**os.environ,
# NOT Active Tracing
_X_AMZN_TRACE_ID: MOCK_XRAY_TRACE_CONTEXT_NOT_SAMPLED,
# NOT using the X-Ray Propagator
OTEL_PROPAGATORS: "tracecontext",
OTEL_INSTRUMENTATION_AWS_LAMBDA_FLUSH_TIMEOUT: "invalid-timeout-string",
},
)
test_env_patch.start()

AwsLambdaInstrumentor().instrument()

mock_execute_lambda()

spans = self.memory_exporter.get_finished_spans()

assert spans

self.assertEqual(len(spans), 1)

test_env_patch.stop()
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,6 @@ def __call__(self, request):
response = self.get_response(request)
return self.process_response(request, response)


else:
# Django versions 1.x can use `settings.MIDDLEWARE_CLASSES` and expect
# old-style middlewares, which are created by inheriting from
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,8 @@
# See the License for the specific language governing permissions and
# limitations under the License.

# pylint: disable=E0611

from sys import modules
from unittest.mock import Mock, patch

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,8 @@
# See the License for the specific language governing permissions and
# limitations under the License.

# pylint: disable=E0611

from sys import modules
from unittest.mock import Mock, patch

Expand Down

0 comments on commit 07f8146

Please sign in to comment.