Skip to content

feat(otel): Add proto bounds to otel logs - #6644

Open
klochek wants to merge 1 commit into
masterfrom
christopherklochek/bound_prost_otel
Open

klochek wants to merge 1 commit into
masterfrom
christopherklochek/bound_prost_otel

Conversation

@klochek

@klochek klochek commented Nov 4, 2026

Copy link
Copy Markdown
Contributor

Actually hook up the proto bounding code to our otel log processor. Note that there is some noise in this PR due to upgrading otel (in relay-otel) to latest in order to get the proto descriptor changes, hence the "Strindex" lines. Setting them to default values is the right thing to do, here (the index refers to a new capability to intern strings in a proto message and just refer to them by index.)

Tests by Claude, but they look sane to me.

@klochek
klochek requested a review from a team as a code owner November 4, 2026 21:56
Comment on lines +306 to +314
// resource_logs + scope_logs + one op per record.
let payload = logs_with_records(1_001).encode_to_vec();

assert!(matches!(
parse_logs_data(OtelFormat::Protobuf, &payload, 1000),
Err(Error::Invalid(DiscardReason::InvalidProtobuf))
));
assert!(parse_logs_data(OtelFormat::Protobuf, &payload, 1003).is_ok());
}

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Resource/scope attributes re-cloned per log record with no memoization

After bounded decode, expand still fans out shared resource/scope attributes onto every log record via otel_to_sentry_log, so a small payload (one large shared attr + many tiny records) under max_ops materializes multi-GB output before any size check.

Evidence
  • expand (otel.rs:87-105) loops every log_record and calls otel_to_sentry_log(log_record, resource, scope) with the same shared resource/scope.
  • otel_scope_into_attributes (relay-otel/src/lib.rs:112-128) .clone()s every resource/scope attribute into each log's Attributes map with no memoization.
  • parse_logs_data / decode_bounded only meters input field occurrences (max_ops); empty records cost 1 op each (see test_abusive_protobuf and bounded_decode test_logs_many_records_exceed_budget), while a large string attr still costs a few ops regardless of byte size.
  • max_log_size (2 MiB) is enforced only later in LogsProcessor (validate::size), after OTEL expand has already built and serialized the full intermediate container via create_intermediates.

Identified by Warden · wrdn-dos-review · DZG-CT3

This branch has not been deployed

No deployments
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.

1 participant