Skip to content

feat(aws-lambda-microvm): refresh identity on Flask run hook - #19825

Draft
litianningdatadog wants to merge 1 commit into
tianning.li/2-flask-web-request-starting-eventfrom
tianning.li/4-1-flask-microvm-run-hook-activation
Draft

feat(aws-lambda-microvm): refresh identity on Flask run hook#19825
litianningdatadog wants to merge 1 commit into
tianning.li/2-flask-web-request-starting-eventfrom
tianning.li/4-1-flask-microvm-run-hook-activation

Conversation

@litianningdatadog

@litianningdatadog litianningdatadog commented Aug 23, 2026

Copy link
Copy Markdown
Contributor

Description

This is the Flask-only MicroVM /run activation path. When running inside an AWS Lambda MicroVM image, runtime registers a listener for the pre-request web event emitted by Flask. The listener matches the fixed platform hook:

POST /aws/lambda-microvms/runtime/v1/run

and calls runtime.refresh_identity() once per process. This keeps the activation path focused on Flask while the identity consumers are split across the 3-series draft PRs.

Testing

  • scripts/lint fmt ddtrace/internal/runtime/__init__.py tests/tracer/runtime/test_runtime_id.py tests/contrib/flask/test_microvm_identity_refresh.py
  • scripts/lint format_check ddtrace/internal/runtime/__init__.py tests/tracer/runtime/test_runtime_id.py tests/contrib/flask/test_microvm_identity_refresh.py
  • git diff --check
  • scripts/run-tests tests/tracer/runtime/test_runtime_id.py --venv 1fa38a1 -- -- -q tests/tracer/runtime/test_runtime_id.py
    • Failed before tests ran due to the existing local native extension issue: ImportError: cannot import name 'process_metrics' from 'ddtrace.internal.native._native'
  • scripts/run-tests tests/contrib/flask/test_microvm_identity_refresh.py --venv 1c6c710 -- -- -q tests/contrib/flask/test_microvm_identity_refresh.py
    • Failed before tests ran due to the same existing local native extension issue: ImportError: cannot import name 'process_metrics' from 'ddtrace.internal.native._native'

Stack

Stacked on #19816.

Extracted from #19781 (closed)

@litianningdatadog litianningdatadog added the aws-microvm Work related to AWS MicroVM onboarding label Aug 23, 2026
@cit-pr-commenter-54b7da

Copy link
Copy Markdown

Codeowners resolved as

Resolved from the full PR diff against tianning.li/2-flask-web-request-starting-event using the target branch CODEOWNERS file.
CODEOWNERS team requests not listed below are not required by the current file set.

ddtrace/internal/runtime/__init__.py                                    @DataDog/apm-sdk-capabilities-python
releasenotes/notes/aws-lambda-microvm-identity-refresh-3a672cd6bcbad16d.yaml  @DataDog/apm-python
tests/contrib/flask/test_microvm_identity_refresh.py                    @DataDog/apm-core-python @DataDog/apm-idm-python
tests/tracer/runtime/test_runtime_id.py                                 @DataDog/apm-sdk-capabilities-python

@cit-pr-commenter-54b7da

cit-pr-commenter-54b7da Bot commented Aug 23, 2026

Copy link
Copy Markdown

Circular import analysis

🚨 New circular imports detected 🚨

1 new circular import(s) have been introduced by this PR:

ddtrace._trace._span_pointer -> ddtrace._trace.telemetry -> ddtrace.internal.telemetry -> ddtrace.internal.telemetry.writer -> ddtrace.internal.runtime -> ddtrace.contrib._events.web_framework -> ddtrace._trace.events -> ddtrace._trace.provider -> ddtrace._trace.span -> ddtrace._trace._span_pointer

Please consider refactoring your changes in accordance to the Separation of Concerns principle.

⚠️ Existing circular imports

There are 3 circular imports that already exist on the base branch and have not been changed by this PR.

ddtrace.llmobs -> ddtrace.llmobs._evaluators -> ddtrace.llmobs._evaluators.format -> ddtrace.llmobs._experiment -> ddtrace.llmobs
ddtrace.errortracking._handled_exceptions.bytecode_injector -> ddtrace.errortracking._handled_exceptions.callbacks -> ddtrace.errortracking._handled_exceptions.collector -> ddtrace.errortracking._handled_exceptions.bytecode_reporting -> ddtrace.errortracking._handled_exceptions.bytecode_injector
ddtrace.appsec._asm_request_context -> ddtrace.appsec._iast._iast_request_context_base -> ddtrace.appsec._iast._iast_env -> ddtrace.appsec._iast.reporter -> ddtrace.appsec._exploit_prevention.stack_traces -> ddtrace.appsec._asm_request_context

@cit-pr-commenter-54b7da

cit-pr-commenter-54b7da Bot commented Aug 23, 2026

Copy link
Copy Markdown

Dependency direction analysis

📈 Existing violations got worse

46 pre-existing violation(s) increased in severity (e.g. their target became more depended-on, or got pulled into an import cycle), though the edge itself isn't new:

Show violations that got worse (showing 5 of 46 highest severity)
ddtrace.internal.span_bus =×=> ddtrace._trace.span  (internal-core -> product:tracing, score=63, +5 vs base)
ddtrace.debugging._probe.status =×=> ddtrace.internal.runtime  (product:debugging -> product:runtime, score=17, +5 vs base)
ddtrace._trace.tracer =×=> ddtrace.internal.runtime  (product:tracing -> product:runtime, score=17, +5 vs base)
ddtrace.internal.opentelemetry.context =×=> ddtrace._trace.span  (product:opentelemetry -> product:tracing, score=61, +5 vs base)
ddtrace.internal.ci_visibility.context =×=> ddtrace._trace.provider  (product:ci_visibility -> product:tracing, score=16, +5 vs base)

To see all violations, download the layers-base.json and layers-pr.json artifacts from this CI job and run:

uv run --script scripts/import-analysis/layers.py compare layers-base.json layers-pr.json

⚠️ Existing dependency direction violations

There are 250 dependency direction violations that already exist on the base branch and have not been changed by this PR.

Show existing violations (showing 5 of 250 highest severity)
ddtrace.internal.tracemethods -×-> ddtrace.trace  (internal-core -> product:tracing, score=135)
ddtrace.llmobs._integrations.pydantic_ai -×-> ddtrace.trace  (product:llmobs -> product:tracing, score=133)
ddtrace.internal.ci_visibility.git_client -×-> ddtrace.trace  (product:ci_visibility -> product:tracing, score=133)
ddtrace.llmobs._integrations.bedrock_agents -×-> ddtrace.trace  (product:llmobs -> product:tracing, score=133)
ddtrace.llmobs._integrations.openai_agents -×-> ddtrace.trace  (product:llmobs -> product:tracing, score=133)

To see all violations, download the layers-base.json and layers-pr.json artifacts from this CI job and run:

uv run --script scripts/import-analysis/layers.py compare layers-base.json layers-pr.json

@datadog-datadog-us1-prod

datadog-datadog-us1-prod Bot commented Aug 23, 2026

Copy link
Copy Markdown

Pipelines  Tests

Unblock PR with BitsAI

⚠️ Warnings

🚦 19 Pipeline jobs failed

DataDog/apm-reliability/dd-trace-py | core/tracer 1/19 — 🔧 Needs a code fix, caused by this PR

View in Datadog · View in GitLab

DataDog/apm-reliability/dd-trace-py | core/tracer 11/19 — 🔧 Needs a code fix, caused by this PR

View in Datadog · View in GitLab

DataDog/apm-reliability/dd-trace-py | core/tracer 12/19 — 🔧 Needs a code fix, caused by this PR

View in Datadog · View in GitLab

View all 19 failed jobs.

ℹ️ Info

No other issues found (see more)

🧪 All tests passed
❄️ No new flaky tests detected

Useful? React with 👍 / 👎

This comment will be updated automatically if new data arrives.
🔗 Commit SHA: 5d444c6 | Docs | View more details | Give us feedback!

@litianningdatadog
litianningdatadog force-pushed the tianning.li/4-1-flask-microvm-run-hook-activation branch from aba2924 to 5d444c6 Compare August 23, 2026 22:24
@pr-commenter

pr-commenter Bot commented Aug 23, 2026

Copy link
Copy Markdown

Benchmarks

Benchmark execution time: 2026-08-23 22:47:53

Comparing candidate commit 5d444c6 in PR branch tianning.li/4-1-flask-microvm-run-hook-activation with baseline commit d59e112 in branch tianning.li/2-flask-web-request-starting-event.

📊 Benchmarking dashboard

Found 0 performance improvements and 4 performance regressions! Performance is the same for 383 metrics, 9 unstable metrics.

Explanation

This is an A/B test comparing a candidate commit's performance against that of a baseline commit. Performance changes are noted in the tables below as:

  • 🟩 = significantly better candidate vs. baseline
  • 🟥 = significantly worse candidate vs. baseline

We compute a confidence interval (CI) over the relative difference of means between metrics from the candidate and baseline commits, considering the baseline as the reference.

If the CI is entirely outside the configured SIGNIFICANT_IMPACT_THRESHOLD (or the deprecated UNCONFIDENCE_THRESHOLD), the change is considered significant.

Feel free to reach out to #apm-benchmarking-platform on Slack if you have any questions.

More details about the CI and significant changes

You can imagine this CI as a range of values that is likely to contain the true difference of means between the candidate and baseline commits.

CIs of the difference of means are often centered around 0%, because often changes are not that big:

---------------------------------(------|---^--------)-------------------------------->
                              -0.6%    0%  0.3%     +1.2%
                                 |          |        |
         lower bound of the CI --'          |        |
sample mean (center of the CI) -------------'        |
         upper bound of the CI ----------------------'

As described above, a change is considered significant if the CI is entirely outside the configured SIGNIFICANT_IMPACT_THRESHOLD (or the deprecated UNCONFIDENCE_THRESHOLD).

For instance, for an execution time metric, this confidence interval indicates a significantly worse performance:

----------------------------------------|---------|---(---------^---------)---------->
                                       0%        1%  1.3%      2.2%      3.1%
                                                  |   |         |         |
       significant impact threshold --------------'   |         |         |
                      lower bound of CI --------------'         |         |
       sample mean (center of the CI) --------------------------'         |
                      upper bound of CI ----------------------------------'

scenario:httppropagationinject-ids_only

  • 🟥 execution_time [+1.945µs; +2.074µs] or [+10.138%; +10.810%]

scenario:span-start

  • 🟥 execution_time [+1.439ms; +1.613ms] or [+9.690%; +10.865%]

scenario:telemetryaddmetric-1-count-metric-1-times

  • 🟥 execution_time [+470.133ns; +520.830ns] or [+17.485%; +19.371%]

scenario:tracer-small

  • 🟥 execution_time [+24.345µs; +26.080µs] or [+7.187%; +7.699%]

Unstable benchmarks

These benchmarks have a confidence interval too wide to call a change; treat them as noise rather than signal.

scenario:coreapiscenario-context_with_data_listeners

  • unstable execution_time [-756.188ns; +732.203ns] or [-6.846%; +6.629%]

scenario:coreapiscenario-core_dispatch_1_listener

  • unstable execution_time [-35.153ns; +30.924ns] or [-5.745%; +5.054%]

scenario:coreapiscenario-core_dispatch_50_listeners

  • unstable execution_time [-1754.546ns; +1585.948ns] or [-10.197%; +9.217%]

scenario:coreapiscenario-core_dispatch_exception_listeners

  • unstable execution_time [-1237.950ns; +1215.432ns] or [-9.600%; +9.425%]

scenario:coreapiscenario-core_dispatch_listeners

  • unstable execution_time [-336.373ns; +317.877ns] or [-9.123%; +8.621%]

scenario:coreapiscenario-core_dispatch_no_args_listeners

  • unstable execution_time [-274.707ns; +234.346ns] or [-9.375%; +7.997%]

scenario:coreapiscenario-core_dispatch_with_results_1_listener

  • unstable execution_time [-110.818ns; +35.740ns] or [-9.545%; +3.078%]

scenario:coreapiscenario-core_dispatch_with_results_50_listeners

  • unstable execution_time [-4208.718ns; +3719.277ns] or [-10.447%; +9.232%]

scenario:coreapiscenario-core_dispatch_with_results_listeners

  • unstable execution_time [-795.761ns; +740.843ns] or [-9.898%; +9.215%]

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Pull request overview

Adds AWS Lambda MicroVM-specific runtime identity rotation triggered by Flask’s pre-request web event, so restored MicroVM instances regenerate stable identifiers (runtime ID / RC client ID) on the platform /run lifecycle hook.

Changes:

  • Register a WEB_REQUEST_STARTING listener (MicroVM-only) that refreshes identity exactly once when the request matches POST /aws/lambda-microvms/runtime/v1/run.
  • Add subprocess and Flask integration tests covering exact-match behavior, ordering relative to root span creation, concurrency, and no-op behavior outside MicroVMs.
  • Add a release note describing stable identifier regeneration for AWS Lambda MicroVM deployments.

Reviewed changes

Copilot reviewed 4 out of 4 changed files in this pull request and generated 1 comment.

File Description
ddtrace/internal/runtime/__init__.py Adds MicroVM /run hook constants, listener registration, and the once-per-process guarded refresh logic.
tests/tracer/runtime/test_runtime_id.py Adds unit/subprocess tests for hook matching, ordering vs. span creation, thread safety, and no-op cases.
tests/contrib/flask/test_microvm_identity_refresh.py Updates Flask event assertions to use the real MicroVM /run hook path and verifies identity refresh via emitted events.
releasenotes/notes/aws-lambda-microvm-identity-refresh-3a672cd6bcbad16d.yaml Documents the MicroVM-only stable identifier regeneration behavior.

💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.

Comment on lines +85 to +87
# Same env var used by the MicroVM entropy fallback. Read once at import so listener
# registration is skipped outside MicroVM images.
_IS_AWS_LAMBDA_MICROVM = env.get("AWS_LAMBDA_MICROVM_IMAGE_ARN") is not None
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

aws-microvm Work related to AWS MicroVM onboarding

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants