Skip to content

fix(ffe): fall back to direct EVP intake in agentless mode - #4489

Merged
bwoebi merged 8 commits into
masterfrom
leo/php-agentless-evp-fallback-20261112
Nov 15, 2026
Merged

bwoebi merged 8 commits into
masterfrom
leo/php-agentless-evp-fallback-20261112

Conversation

@leoromanovsky

@leoromanovsky leoromanovsky commented Nov 12, 2026 •

Copy link
Copy Markdown
Contributor

Description

Agentless flag evaluation currently configures event delivery as Agent-only. Exposures and evaluation-count events therefore have no direct delivery path.

Use libdatadog's shared local-proxy discovery and HTTPS fallback for both streams in agentless mode. Direct delivery uses DD_API_KEY and the intake derived from DD_SITE. A custom CDN URL never becomes the authenticated event destination. Missing credentials or an invalid site retain local-proxy discovery. Remote Config keeps its existing Agent-only route. Runtime test-session changes preserve the destination of batches already handed to the sidecar. PHP-buffered exposures and deferred userland observations use the session active at handoff, not necessarily the session active during evaluation.

The native transport fixture now reads concurrent HTTP requests without blocking on idle sockets. It retains the route, identity, credential, payload, and duplicate checks.

Validation

Tested commit Validation Result
DataDog/dd-trace-php@a122cbc2ee47551e911de695ea2d45d0e1f4dc99 System tests: direct and serverless-relay exposures and evaluation counts, explicit CDN configuration; Apache/PHP 8.2; system-tests@7f153aa229a1ce67559bb47acf1fb3986c1be6af 5 passed, 0 failed, 0 skipped, 1 deselected; development-version override
DataDog/dd-trace-php@a122cbc2ee47551e911de695ea2d45d0e1f4dc99 System tests: direct-EVP shutdown delivery Not run; disabled in the PHP manifest. PHP-FPM was not tested.

Reviewer checklist

  • Test coverage seems ok.
  • Appropriate labels assigned.

@datadog-datadog-prod-us1

datadog-datadog-prod-us1 Bot commented Nov 12, 2026 •

Copy link
Copy Markdown

Pipelines  Tests

✨ Unblock PR with BitsAI

❌ Errors

Your PR has failed checks. Please review the issues below and take necessary action before merging.

🚦 30 Pipeline jobs failed

DataDog/apm-reliability/dd-trace-php | System Tests: [INTEGRATIONS] — ❌ 2 tests failed · 🔧 Needs a code fix, caused by this PR

View more details · View in GitLab

❌ tests.integrations.test_db_integrations_sql.Test_MySql.test_span_kind[apache-mod-8.0] from system_tests_suite
KeyError: 'span.kind'

self = <tests.integrations.test_db_integrations_sql.Test_MySql object at 0x7f17d6b951c0>
excluded_operations = ()

    def test_span_kind(self, excluded_operations: tuple[str, ...] = ()):
        """Describes the relationship between the Span, its parents, and its children in a Trace."""
    
        for _, span_meta in self.get_spans_meta(excluded_operations):
>           assert span_meta["span.kind"] == "client"
...
❌ tests.integrations.test_db_integrations_sql.Test_Postgres.test_span_kind[apache-mod-8.0] from system_tests_suite
KeyError: 'span.kind'

self = <tests.integrations.test_db_integrations_sql.Test_Postgres object at 0x7f17d6b815b0>
excluded_operations = ()

    def test_span_kind(self, excluded_operations: tuple[str, ...] = ()):
        """Describes the relationship between the Span, its parents, and its children in a Trace."""
    
        for _, span_meta in self.get_spans_meta(excluded_operations):
>           assert span_meta["span.kind"] == "client"
...
DataDog/apm-reliability/dd-trace-php | System Tests: [parametric] 1/2 — ❌ 21 tests failed · 🔧 Needs a code fix, caused by this PR

View more details · View in GitLab

❌ tests.parametric.test_otel_api_interoperability.Test_Otel_API_Interoperability.test_distributed_headers_are_propagated_tracecontext[library_env0, parametric-... from system_tests_suite
KeyError: '_dd.p.dm'

self = <tests.parametric.test_otel_api_interoperability.Test_Otel_API_Interoperability object at 0x7f8a1550b770>
test_agent = <utils.docker_fixtures._test_agent.TestAgentAPI object at 0x7f8a126c6330>
test_library = <utils.docker_fixtures._test_clients._test_client_parametric.ParametricTestClientApi object at 0x7f8a072a5160>

    def test_distributed_headers_are_propagated_tracecontext(self, test_agent: TestAgentAPI, test_library: APMLibrary):
        """- Test that distributed tracecontext headers are propagated across APIs"""
        trace_id = "0000000000000000000000000000002a"  # 42
        parent_id = "0000000000000003"  # 3
...
❌ tests.parametric.test_otel_api_interoperability.Test_Otel_API_Interoperability.test_set_attribute_from_otel[library_env0, parametric-php] from system_tests_suite
KeyError: 'bool'

self = <tests.parametric.test_otel_api_interoperability.Test_Otel_API_Interoperability object at 0x7f8a1550b560>
test_agent = <utils.docker_fixtures._test_agent.TestAgentAPI object at 0x7f8a126c6330>
test_library = <utils.docker_fixtures._test_clients._test_client_parametric.ParametricTestClientApi object at 0x7f8a072a8cb0>

    def test_set_attribute_from_otel(self, test_agent: TestAgentAPI, test_library: APMLibrary):
        """- Test that attributes can be set on a Datadog span using the OTel API"""
        with test_library, test_library.dd_start_span("dd_span") as dd_span:
            otel_span = test_library.otel_current_span()
...
↳ and 19 more — View all
DataDog/apm-reliability/dd-trace-php | System Tests: [parametric] 2/2 — ❌ 2 tests failed · 🔧 Needs a code fix, caused by this PR

View more details · View in GitLab

❌ tests.parametric.test_tracer.Test_TracerSCITagging.test_tracer_commit_sha_environment_variable[library_env0, parametric-php] from system_tests_suite
AssertionError: assert 2 == 1
 +  where 2 = len([{'duration': 135243795, 'meta': {'_dd.git.commit.sha': 'aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa', '_dd.p.tid': '6af8...aries,runtime.sapi:cli,svc.auto:server.php'}, 'metrics': {'_sampling_priority_v1': 1}, 'name': 'operation.child', ...}])

self = <tests.parametric.test_tracer.Test_TracerSCITagging object at 0x7f6c2b73ffe0>
library_env = {'DD_GIT_COMMIT_SHA': 'aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa'}
test_agent = <utils.docker_fixtures._test_agent.TestAgentAPI object at 0x7f6c28b33560>
test_library = <utils.docker_fixtures._test_clients._test_client_parametric.ParametricTestClientApi object at 0x7f6c1db9ab40>

    @parametrize("library_env", [{"DD_GIT_COMMIT_SHA": "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"}])
    def test_tracer_commit_sha_environment_variable(
...
❌ tests.parametric.test_tracer.Test_TracerSCITagging.test_tracer_repository_url_environment_variable[library_env0, parametric-php] from system_tests_suite
AssertionError: assert 2 == 1
 +  where 2 = len([{'duration': 135857858, 'meta': {'_dd.git.repository_url': 'https://github.com/DataDog/dd-trace-go', '_dd.p.tid': '6a...aries,runtime.sapi:cli,svc.auto:server.php'}, 'metrics': {'_sampling_priority_v1': 1}, 'name': 'operation.child', ...}])

self = <tests.parametric.test_tracer.Test_TracerSCITagging object at 0x7f6c2b73c530>
library_env = {'DD_GIT_REPOSITORY_URL': 'https://github.com/DataDog/dd-trace-go'}
test_agent = <utils.docker_fixtures._test_agent.TestAgentAPI object at 0x7f6c28b33560>
test_library = <utils.docker_fixtures._test_clients._test_client_parametric.ParametricTestClientApi object at 0x7f6c1db99400>

    @parametrize("library_env", [{"DD_GIT_REPOSITORY_URL": "https://github.com/DataDog/dd-trace-go"}])
    def test_tracer_repository_url_environment_variable(
...

View all 30 failed jobs.

⚠️ Warnings

❄️ 10 New flaky tests detected

FFE agentless discovers a shared local EVP route while Remote Config keeps EVP v2 from PHP.tmp.build_extension.tests.ext.ffe
007+ 
008+ Fatal error: Uncaught RuntimeException: remote-config: missing event stream; received exposures/transport-session; child output: delivered
007- remote-config/false: expected streams delivered with PHP identity, token and no API key
008- remote-config/true: expected streams delivered with PHP identity, token and no API key
009+  in tmp/build_extension/tests/ext/ffe/stubs/agentless_evp_transport.inc:102
010+ Stack trace:
011+ #0 tmp/build_extension/tests/ext/ffe/agentless_evp_transport.php(3): require()
012+ #1 {main}
013+   thrown in tmp/build_extension/tests/ext/ffe/stubs/agentless_evp_transport.inc on line 102
FFE keeps local EVP discovery when managed CDN setup fails from PHP.tmp.build_extension.tests.ext.ffe
001+ Fatal error: Uncaught RuntimeException: managed-no-key: missing event stream; received ; child output: delivered
002+  in tmp/build_extension/tests/ext/ffe/stubs/agentless_evp_transport.inc:102
003+ Stack trace:
004+ #0 tmp/build_extension/tests/ext/ffe/agentless_evp_managed_failure.php(3): require()
001- managed-no-key/false: expected streams delivered with PHP identity, token and no API key
002- managed-no-key/true: expected streams delivered with PHP identity, token and no API key
003- managed-invalid-site/false: expected streams delivered with PHP identity, token and no API key
004- managed-invalid-site/true: expected streams delivered with PHP identity, token and no API key
005+ #1 {main}
006+   thrown in tmp/build_extension/tests/ext/ffe/stubs/agentless_evp_transport.inc on line 102

View in Flaky Test Management

ℹ️ Info

🎯 Code Coverage (details)
• Patch Coverage: 100.00%
• Overall Coverage: 80.12% (-0.01%)

Useful? React with 👍 / 👎

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

@leoromanovsky leoromanovsky added the crucible: reviewing A Crucible review has started; this PR has reviewer attention. label Nov 12, 2026
@leoromanovsky leoromanovsky removed the crucible: reviewing A Crucible review has started; this PR has reviewer attention. label Nov 13, 2026
@pr-commenter

pr-commenter Bot commented Nov 13, 2026 •

Copy link
Copy Markdown

Benchmarks [ tracer ]

Benchmark execution time: 2026-11-15 00:05:24

Comparing candidate commit a98560d in PR branch leo/php-agentless-evp-fallback-20261112 with baseline commit 14d2bef in branch master.

📊 Benchmarking dashboard

Found 0 performance improvements and 2 performance regressions! Performance is the same for 216 metrics, 0 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:SamplingRuleMatchingBench/benchGlobMatching4-opcache

  • 🟥 execution_time [+61.698ns; +212.902ns] or [+2.044%; +7.054%]

scenario:SamplingRuleMatchingBench/benchRegexMatching4

  • 🟥 execution_time [+35.306ns; +115.494ns] or [+2.383%; +7.796%]

@leoromanovsky
leoromanovsky marked this pull request as ready for review November 13, 2026 01:28
@leoromanovsky
leoromanovsky requested review from a team as code owners November 13, 2026 01:28
@leoromanovsky
leoromanovsky requested a review from bwoebi November 13, 2026 01:28
@chatgpt-codex-connector

chatgpt-codex-connector Bot commented Nov 13, 2026 •

Copy link
Copy Markdown
Codex Review Summary: ✅ Completed

This comment shows the latest Codex review activity on this pull request.

Review Status Commit Review trigger
📝 Code Review ✅ Completed 2026-11-13T01:29:46.694309Z ec428b1 Draft marked ready
🔒 Security Review ✅ Completed 2026-11-13T01:33:49.969778Z ec428b1 Draft marked ready
ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review" or "@codex security review".

Codex reacts with 👀 while any review is running, comments if it has suggestions, and reacts with 👍 once all reviews finish with no findings.

@datadog-datadog-prod-us1 datadog-datadog-prod-us1 Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Bits Code Review: PASS

More details

The authenticated fallback remains separate from custom CDN URLs, and static review raised no reportable concerns about routing or test-token propagation. Native delivery could not be independently validated because required runtime dependencies were unavailable.

Was this helpful? React 👍 or 👎

Open Bits AI session

🤖 Bits Code Review · Commit ec428b1

Comment thread ext/sidecar.c Resolved
Comment thread ext/sidecar.c Resolved
Comment thread ext/sidecar.c Resolved

@vjfridge vjfridge 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.

Approach looks good. I posted some p2 comments for you to consider and looks like CI needs iteration, but I trust you'll take care of those!

@leoromanovsky leoromanovsky added crucible: reviewing A Crucible review has started; this PR has reviewer attention. and removed crucible: reviewing A Crucible review has started; this PR has reviewer attention. labels Nov 13, 2026
bwoebi and others added 2 commits November 14, 2026 21:49
…-agentless-evp-fallback-20261112

* 'master' of github.com:DataDog/dd-trace-php:
  feat(tracer): send traces as V1 payloads through the libdatadog builder FFI (#4453)
  Move profiling storage and export into SSI common (#4455)
…ndows

Valgrind: the sidecar builds its rustls root store lazily inside the first
timed /info probe. Under valgrind that alone takes several seconds, so the
5s DD_TRACE_AGENT_TIMEOUT expired, no EVP route was found and the
flagevaluation batch was dropped. Raise the child's agent timeout when
running under valgrind.

Windows: every subprocess sidecar is spawned from the fixed trampoline
%TEMP%\datadog-ipc-helper-<session>, with a single ".old" slot for a
still-running predecessor. The test's own shared sidecar plus the previous
child's lingering per-process sidecar occupy both slots, so the second
child failed with ERROR_FILE_EXISTS (os error 80). Give each child a private
TMP/TEMP directory.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@bwoebi
bwoebi disabled auto-merge November 15, 2026 01:46
@bwoebi
bwoebi merged commit b1c7b41 into master Nov 15, 2026
2326 of 2342 checks passed
@bwoebi
bwoebi deleted the leo/php-agentless-evp-fallback-20261112 branch November 15, 2026 01:46
@github-actions github-actions Bot added this to the 1.28.0 milestone Nov 15, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants