Skip to content

feat(aap): In App WAF support#744

Open
CarlesDD wants to merge 19 commits into
mainfrom
ccapell/APPSEC-60752/in-app-waf-port
Open

feat(aap): In App WAF support#744
CarlesDD wants to merge 19 commits into
mainfrom
ccapell/APPSEC-60752/in-app-waf-port

Conversation

@CarlesDD

@CarlesDD CarlesDD commented Mar 16, 2026

Copy link
Copy Markdown
Collaborator

What does this PR do?

Adds AppSec support to the Lambda layer by extracting HTTP data from Lambda events and publishing it to diagnostic channels consumed by dd-trace-js's AppSec subsystem.

inappwafport

Changes:

  • Dockerfile + move script: move_ddtrace_dependency.js now reads @datadog/native-appsec from dd-trace's optionalDependencies and promotes it to a direct dependency so it survives --ignore-optional. The Dockerfile runs the script before rm -rf node_modules and strips unused native prebuilds (non-Linux-glibc platforms)
  • Event data extractor (src/appsec/event-data-extractor.ts): Parses API Gateway v1/v2, ALB, and Lambda Function URL events, extracting headers, method, path, query, body, client IP, path params, cookies, and route
  • Orchestrator (src/appsec/index.ts): Checks DD_APPSEC_ENABLED and publishes extracted data to datadog:lambda:start-invocation / datadog:lambda:end-invocation diagnostic channels
  • TraceListener integration: initAppsec() called in onStartInvocation, processAppSecRequest and processAppSecResponse called in onEndingInvocation

Motivation

Porting the In-App WAF security product to AWS Lambda for the Node.js runtime. The Lambda layer extracts HTTP data and dispatches it to the tracer for WAF execution and reporting.

The layer is intentionally kept thin, only extracting and publishing data. All security logic (WAF, reporting, trace keeping) lives in dd-trace-js.

Testing Guidelines

  • Unit tests for the event data extractor cover all 4 HTTP event types (API GW v1/v2, ALB, Lambda Function URL) and non-HTTP events
  • Unit tests for the orchestrator verify configuration gating and channel publishing
  • Existing listener tests pass unchanged

Additional Notes

  • @datadog/native-appsec is NOT added to this repo's package.json. The version is read dynamically from dd-trace's optionalDependencies at build time, so dd-trace-js remains the single owner of the native module version.
  • No new environment variables, using the existing DD_APPSEC_ENABLED.
  • This is a monitoring-only first iteration. Blocking, Remote Config, and telemetry are out of scope.
  • Companion PR in dd-trace-js: feat(aap): In App WAF support for lambda dd-trace-js#7783

Types of Changes

  • Bug fix
  • New feature
  • Breaking change
  • Misc (docs, refactoring, dependency upgrade, etc.)

Check all that apply

  • This PR's description is comprehensive
  • This PR contains breaking changes that are documented in the description
  • This PR introduces new APIs or parameters that are documented and unlikely to change in the foreseeable future
  • This PR impacts documentation, and it has been updated (or a ticket has been logged)
  • This PR's changes are covered by the automated tests
  • This PR collects user input/sensitive content into Datadog
  • This PR passes the integration tests (ask a Datadog member to run the tests)

APPSEC-60752

Comment thread scripts/move_ddtrace_dependency.js Outdated
Comment thread src/trace/listener.ts Outdated
Comment thread src/appsec/event-data-extractor.ts
Comment thread src/appsec/event-data-extractor.ts
@CarlesDD CarlesDD force-pushed the ccapell/APPSEC-60752/in-app-waf-port branch from a9a47e9 to a79197a Compare April 21, 2026 15:06
Comment thread src/appsec/index.ts
@datadog-datadog-prod-us1

datadog-datadog-prod-us1 Bot commented Jun 16, 2026

Copy link
Copy Markdown

Pipelines

Fix all issues with BitsAI

⚠️ Warnings

🚦 4 Pipeline jobs failed

DataDog/datadog-lambda-js | check layer size (node18)   View in Datadog   GitLab

DataDog/datadog-lambda-js | check layer size (node20)   View in Datadog   GitLab

DataDog/datadog-lambda-js | check layer size (node22)   View in Datadog   GitLab

View all 4 failed jobs.

Useful? React with 👍 / 👎

This comment will be updated automatically if new data arrives.
🔗 Commit SHA: c09ecd5 | Docs | Datadog PR Page | Give us feedback!

@CarlesDD CarlesDD marked this pull request as ready for review June 30, 2026 05:58
@CarlesDD CarlesDD requested review from a team as code owners June 30, 2026 05:58
@CarlesDD CarlesDD requested a review from shreyamalpani June 30, 2026 05:58
Comment thread src/trace/listener.ts Outdated
if (!this.tracerWrapper.currentSpan) return false;
this.wrappedCurrentSpan = new SpanWrapper(this.tracerWrapper.currentSpan, {});

processAppsecRequest(event, this.tracerWrapper.currentSpan);

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.

Should this happen at the beginning of the invocation? I'm wondering if this should be moved to onStartInvocation.

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

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

Good catch. processAppsecRequest ran after the handler, too late to ever support blocking. Moved it to onRequestStart, called right before the handler runs, once the span is active. Couldnt be onStartInvocation itself since the span doesnt exist yet there.

Comment thread src/trace/listener.ts
* @param event
*/
public onRequestStart(event: any): void {
processAppsecRequest(event, this.tracerWrapper.currentSpan);

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.

Is there a reason we can't just put this into onStartInvocation?

Comment thread src/trace/listener.ts
}

public async onStartInvocation(event: any, context: Context) {
initAppsec();

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.

Looks like there's a this.config object available. Makes sense to add the appsec enabled check to the config.

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.

4 participants