Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
- Correctly handle minidump objecstore upload failures. ([#6033](https://github.com/getsentry/relay/pull/6033))
- Add `client.address` attribute to known IP fields. ([#6058](https://github.com/getsentry/relay/pull/6058))
- Fix a bug in mobile attribute normalization. ([#6065](https://github.com/getsentry/relay/pull/6065))
- Stop using cross-org DSC data in v2 span normalization. ([#6073](https://github.com/getsentry/relay/pull/6073))

**Internal**:

Expand Down
54 changes: 17 additions & 37 deletions relay-event-normalization/src/eap/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ use relay_conventions::attributes::*;
use relay_conventions::{AttributeInfo, ReplacementName, WriteBehavior};
use relay_event_schema::protocol::{Attribute, AttributeType, Attributes, BrowserContext, Geo};
use relay_protocol::{Annotated, Error, ErrorKind, Meta, Remark, RemarkType, Value};
use relay_sampling::DynamicSamplingContext;
use relay_spans::derive_op_for_v2_span;

use crate::span::TABLE_NAME_REGEX;
Expand All @@ -19,7 +20,7 @@ use crate::span::tag_extraction::{
domain_from_scrubbed_http, domain_from_server_address, span_op_to_category,
sql_action_from_query, sql_tables_from_query,
};
use crate::{ClientHints, EnrichedDsc, FromUserAgentInfo as _, RawUserAgentInfo};
use crate::{ClientHints, FromUserAgentInfo as _, RawUserAgentInfo};

mod ai;
mod mobile;
Expand Down Expand Up @@ -356,7 +357,7 @@ pub fn normalize_user_geo(
pub fn normalize_dsc(
attributes: &mut Annotated<Attributes>,
is_segment: &Annotated<bool>,
dsc: Option<EnrichedDsc>,
dsc: Option<&DynamicSamplingContext>,
) {
let Some(dsc) = dsc else {
return;
Expand All @@ -368,26 +369,28 @@ pub fn normalize_dsc(
if attributes.contains_key(SENTRY__DSC__TRACE_ID) {
return;
}
attributes.insert(SENTRY__DSC__TRACE_ID, dsc.dsc.trace_id.to_string());
attributes.insert(SENTRY__DSC__TRACE_ID, dsc.trace_id.to_string());

if let Some(transaction) = &dsc.dsc.transaction {
if let Some(transaction) = &dsc.transaction {
attributes.insert(SENTRY__DSC__TRANSACTION, transaction.clone());
}

attributes.insert(SENTRY__DSC__PROJECT_ID, dsc.sampling_project_id.to_string());
if let Some(project_id) = &dsc.project_id {
attributes.insert(SENTRY__DSC__PROJECT_ID, project_id.to_string());
}

if is_segment.value().is_some_and(|is_segment| *is_segment) {
attributes.insert(SENTRY__DSC__PUBLIC_KEY, dsc.dsc.public_key.to_string());
if let Some(release) = &dsc.dsc.release {
attributes.insert(SENTRY__DSC__PUBLIC_KEY, dsc.public_key.to_string());
if let Some(release) = &dsc.release {
attributes.insert(SENTRY__DSC__RELEASE, release.clone());
}
if let Some(environment) = &dsc.dsc.environment {
if let Some(environment) = &dsc.environment {
attributes.insert(SENTRY__DSC__ENVIRONMENT, environment.clone());
}
if let Some(sample_rate) = dsc.dsc.sample_rate {
if let Some(sample_rate) = dsc.sample_rate {
attributes.insert(SENTRY__DSC__SAMPLE_RATE, sample_rate);
}
if let Some(sampled) = dsc.dsc.sampled {
if let Some(sampled) = dsc.sampled {
attributes.insert(SENTRY__DSC__SAMPLED, sampled);
}
}
Expand Down Expand Up @@ -825,6 +828,7 @@ mod tests {
DynamicSamplingContext {
trace_id: "67e5504410b1426f9247bb680e5fe0c8".parse().unwrap(),
public_key: "12345678901234567890123456789012".parse().unwrap(),
project_id: Some(ProjectId::new(42)),
release: None,
environment: None,
transaction: transaction.map(str::to_owned),
Expand All @@ -847,15 +851,7 @@ mod tests {
fn test_normalize_dsc_child_span_no_transaction() {
let mut attributes = Annotated::empty();
let dsc = &mock_dsc(None);
let sampling_project_id = ProjectId::new(42);
normalize_dsc(
&mut attributes,
&Annotated::new(false),
Some(EnrichedDsc {
dsc,
sampling_project_id,
}),
);
normalize_dsc(&mut attributes, &Annotated::new(false), Some(dsc));
assert_annotated_snapshot!(attributes, @r#"
{
"sentry.dsc.project_id": {
Expand All @@ -874,15 +870,7 @@ mod tests {
fn test_normalize_dsc_child_span() {
let mut attributes = Annotated::empty();
let dsc = &mock_dsc(Some("/some/endpoint"));
let sampling_project_id = ProjectId::new(42);
normalize_dsc(
&mut attributes,
&Annotated::new(false),
Some(EnrichedDsc {
dsc,
sampling_project_id,
}),
);
normalize_dsc(&mut attributes, &Annotated::new(false), Some(dsc));
assert_annotated_snapshot!(attributes, @r#"
{
"sentry.dsc.project_id": {
Expand All @@ -905,15 +893,7 @@ mod tests {
fn test_normalize_dsc_segment() {
let mut attributes = Annotated::empty();
let dsc = &mock_dsc(Some("/some/endpoint"));
let sampling_project_id = ProjectId::new(42);
normalize_dsc(
&mut attributes,
&Annotated::new(true),
Some(EnrichedDsc {
dsc,
sampling_project_id,
}),
);
normalize_dsc(&mut attributes, &Annotated::new(true), Some(dsc));
assert_annotated_snapshot!(attributes, @r#"
{
"sentry.dsc.project_id": {
Expand Down
9 changes: 5 additions & 4 deletions relay-event-normalization/src/event.rs
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@ use relay_protocol::{
Annotated, Empty, Error, ErrorKind, FiniteF64, FromValue, Getter, Meta, Object, Remark,
RemarkType, TryFromFloatError, Value,
};
use relay_sampling::DynamicSamplingContext;
use smallvec::SmallVec;
use uuid::Uuid;

Expand All @@ -41,8 +42,8 @@ use crate::span::ai::enrich_ai_event_data;
use crate::span::tag_extraction::{extract_segment_name_from_event, extract_span_tags_from_event};
use crate::utils::{self, MAX_DURATION_MOBILE_MS, get_event_user_tag};
use crate::{
BorrowedSpanOpDefaults, BreakdownsConfig, CombinedMeasurementsConfig, EnrichedDsc, GeoIpLookup,
MaxChars, ModelMetadata, PerformanceScoreConfig, RawUserAgentInfo, SpanDescriptionRule,
BorrowedSpanOpDefaults, BreakdownsConfig, CombinedMeasurementsConfig, GeoIpLookup, MaxChars,
ModelMetadata, PerformanceScoreConfig, RawUserAgentInfo, SpanDescriptionRule,
TransactionNameConfig, breakdowns, event_error, legacy, mechanism, remove_other, schema, span,
stacktrace, transactions, trimming, user_agent,
};
Expand Down Expand Up @@ -182,8 +183,8 @@ pub struct NormalizationConfig<'a> {
/// the SDK.
pub force_trace_context: bool,

/// Dynamic sampling context and additional attributes used for dsc span normalization.
pub dsc: Option<EnrichedDsc<'a>>,
/// Dynamic sampling context used for dsc span normalization.
pub dsc: Option<&'a DynamicSamplingContext>,
}

impl Default for NormalizationConfig<'_> {
Expand Down
11 changes: 0 additions & 11 deletions relay-event-normalization/src/normalize/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,11 +3,9 @@ use std::{collections::HashMap, sync::LazyLock};

use regex::Regex;
use relay_base_schema::metrics::MetricUnit;
use relay_base_schema::project::ProjectId;
use relay_event_schema::protocol::VALID_PLATFORMS;
use relay_pattern::Pattern;
use relay_protocol::{FiniteF64, RuleCondition};
use relay_sampling::DynamicSamplingContext;
use serde::{Deserialize, Serialize};

pub mod breakdowns;
Expand Down Expand Up @@ -366,15 +364,6 @@ pub struct ModelMetadataEntry {
pub context_size: Option<u64>,
}

/// [`DynamicSamplingContext`] plus additional attributes used for dsc span normalization.
#[derive(Debug, Clone, Copy)]
pub struct EnrichedDsc<'a> {
/// Dynamic sampling context containing the trace id and root transaction that started the trace.
pub dsc: &'a DynamicSamplingContext,
/// ID of the project where the trace originated.
pub sampling_project_id: ProjectId,
}

#[cfg(test)]
mod tests {
use chrono::{TimeZone, Utc};
Expand Down
18 changes: 11 additions & 7 deletions relay-event-normalization/src/normalize/span/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,9 @@
use regex::Regex;
use relay_event_schema::protocol::{Event, SpanData, TraceContext};
use relay_protocol::Annotated;
use relay_sampling::DynamicSamplingContext;
use std::sync::LazyLock;

use crate::EnrichedDsc;

pub mod ai;
pub mod country_subregion;
pub mod description;
Expand Down Expand Up @@ -61,7 +60,7 @@ pub fn normalize_app_start_spans(event: &mut Event) {
///
/// If `sentry.dsc.trace_id` is already present in a span's `data`, the function does nothing for
/// that span.
pub fn normalize_dsc_for_event_spans(event: &mut Event, dsc: Option<EnrichedDsc>) {
pub fn normalize_dsc_for_event_spans(event: &mut Event, dsc: Option<&DynamicSamplingContext>) {
if let Some(ctx) = event.context_mut::<TraceContext>() {
normalize_dsc_for_span_data(&mut ctx.data, dsc);
}
Expand All @@ -77,7 +76,10 @@ pub fn normalize_dsc_for_event_spans(event: &mut Event, dsc: Option<EnrichedDsc>
/// Writes DSC attributes needed for dynamic sampling into `span_data`.
///
/// If `sentry.dsc.trace_id` is already present in `span_data`, the function does nothing.
pub fn normalize_dsc_for_span_data(span_data: &mut Annotated<SpanData>, dsc: Option<EnrichedDsc>) {
pub fn normalize_dsc_for_span_data(
span_data: &mut Annotated<SpanData>,
dsc: Option<&DynamicSamplingContext>,
) {
let Some(dsc) = dsc else {
return;
};
Expand All @@ -86,9 +88,11 @@ pub fn normalize_dsc_for_span_data(span_data: &mut Annotated<SpanData>, dsc: Opt
if data.sentry_dsc_trace_id.value().is_some() {
return;
}
data.sentry_dsc_trace_id = Annotated::new(dsc.dsc.trace_id.to_string());
data.sentry_dsc_project_id = Annotated::new(dsc.sampling_project_id.to_string());
if let Some(transaction) = &dsc.dsc.transaction {
data.sentry_dsc_trace_id = Annotated::new(dsc.trace_id.to_string());
if let Some(project_id) = &dsc.project_id {
data.sentry_dsc_project_id = Annotated::new(project_id.to_string());
}
Comment thread
sentry[bot] marked this conversation as resolved.
if let Some(transaction) = &dsc.transaction {
data.sentry_dsc_transaction = Annotated::new(transaction.to_string());
}
}
12 changes: 11 additions & 1 deletion relay-sampling/src/dsc.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@
use std::collections::BTreeMap;
use std::fmt;

use relay_base_schema::project::ProjectKey;
use relay_base_schema::project::{ProjectId, ProjectKey};
use relay_event_schema::protocol::TraceId;
use relay_protocol::{Getter, Val};
use serde::{Deserialize, Serialize};
Expand All @@ -28,6 +28,13 @@ pub struct DynamicSamplingContext {
pub trace_id: TraceId,
/// The project key.
pub public_key: ProjectKey,
/// The sampling project id.
///
/// Not part of the DSC protocol, but accessed and used together with the rest of the DSC.
/// Placed here for ergonomy and to avoid having to mutate the request context when the sampling
/// org is different from the sending org.
#[serde(skip)]
pub project_id: Option<ProjectId>,
/// The release.
#[serde(default)]
pub release: Option<String>,
Expand Down Expand Up @@ -562,6 +569,7 @@ mod tests {
let dsc = DynamicSamplingContext {
trace_id: "67e5504410b1426f9247bb680e5fe0c8".parse().unwrap(),
public_key: ProjectKey::parse("abd0f232775f45feab79864e580d160b").unwrap(),
project_id: Some(ProjectId::new(42)),
release: Some("1.1.1".into()),
user: TraceUserContext {
user_segment: "user-seg".into(),
Expand Down Expand Up @@ -600,6 +608,7 @@ mod tests {
let dsc = DynamicSamplingContext {
trace_id: "67e5504410b1426f9247bb680e5fe0c8".parse().unwrap(),
public_key: ProjectKey::parse("abd0f232775f45feab79864e580d160b").unwrap(),
project_id: Some(ProjectId::new(42)),
release: None,
user: TraceUserContext::default(),
environment: None,
Expand All @@ -619,6 +628,7 @@ mod tests {
let dsc = DynamicSamplingContext {
trace_id: "67e5504410b1426f9247bb680e5fe0c8".parse().unwrap(),
public_key: ProjectKey::parse("abd0f232775f45feab79864e580d160b").unwrap(),
project_id: Some(ProjectId::new(42)),
release: None,
user: TraceUserContext::default(),
environment: None,
Expand Down
2 changes: 2 additions & 0 deletions relay-sampling/src/evaluation.rs
Original file line number Diff line number Diff line change
Expand Up @@ -258,6 +258,7 @@ impl fmt::Display for MatchedRuleIds {
#[cfg(test)]
mod tests {
use chrono::TimeZone;
use relay_base_schema::project::ProjectId;
use relay_protocol::RuleCondition;
use similar_asserts::assert_eq;
use std::str::FromStr;
Expand Down Expand Up @@ -299,6 +300,7 @@ mod tests {
let mut dsc = DynamicSamplingContext {
trace_id: "67e5504410b1426f9247bb680e5fe0c8".parse().unwrap(),
public_key: "12345678123456781234567812345678".parse().unwrap(),
project_id: Some(ProjectId::new(42)),
release: None,
environment: None,
transaction: None,
Expand Down
13 changes: 13 additions & 0 deletions relay-server/src/envelope/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -189,6 +189,18 @@ impl<M> EnvelopeHeaders<M> {
}
}

/// Returns a mutable reference to the dynamic sampling context from the headers, if present.
pub fn dsc_mut(&mut self) -> Option<&mut DynamicSamplingContext> {
match &mut self.trace {
None => None,
Some(ErrorBoundary::Err(e)) => {
relay_log::debug!(error = e.as_ref(), "failed to parse sampling context");
None
}
Some(ErrorBoundary::Ok(t)) => Some(t),
}
}

/// Overrides the dynamic sampling context in envelope headers.
pub fn set_dsc(&mut self, dsc: DynamicSamplingContext) {
self.trace = Some(ErrorBoundary::Ok(dsc));
Expand Down Expand Up @@ -1243,6 +1255,7 @@ mod tests {
let dsc = DynamicSamplingContext {
trace_id: "67e5504410b1426f9247bb680e5fe0c8".parse().unwrap(),
public_key: ProjectKey::parse("abd0f232775f45feab79864e580d160b").unwrap(),
project_id: None,
release: Some("1.1.1".to_owned()),
user: Default::default(),
replay_id: None,
Expand Down
4 changes: 2 additions & 2 deletions relay-server/src/processing/legacy_spans/normalize.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@

use crate::services::processor::ProcessingError;
use chrono::{DateTime, Utc};
use relay_event_normalization::EnrichedDsc;
use relay_event_normalization::span::{self, ai};
use relay_event_normalization::{
BorrowedSpanOpDefaults, ClientHints, CombinedMeasurementsConfig, FromUserAgentInfo,
Expand All @@ -15,6 +14,7 @@ use relay_event_schema::processor::{ProcessingState, process_value};
use relay_event_schema::protocol::{BrowserContext, EventId, IpAddr, Span, SpanData};
use relay_metrics::UnixTimestamp;
use relay_protocol::{Annotated, Empty, Value};
use relay_sampling::DynamicSamplingContext;

/// Config needed to normalize a standalone span.
#[derive(Clone, Debug)]
Expand Down Expand Up @@ -57,7 +57,7 @@ pub struct NormalizeSpanConfig<'a> {
pub geo_lookup: &'a GeoIpLookup,
pub span_op_defaults: BorrowedSpanOpDefaults<'a>,
/// Dynamic sampling context plus additional attributes used for dsc span normalization.
pub dsc: Option<EnrichedDsc<'a>>,
pub dsc: Option<&'a DynamicSamplingContext>,
}

fn set_segment_attributes(span: &mut Annotated<Span>) {
Expand Down
24 changes: 9 additions & 15 deletions relay-server/src/processing/legacy_spans/process.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,4 @@
use relay_event_normalization::{
CombinedMeasurementsConfig, EnrichedDsc, GeoIpLookup, MeasurementsConfig,
};
use relay_event_normalization::{CombinedMeasurementsConfig, GeoIpLookup, MeasurementsConfig};
use relay_event_schema::processor::{ProcessingAction, ProcessingState, process_value};
use relay_event_schema::protocol::Span;
use relay_metrics::MetricNamespace;
Expand Down Expand Up @@ -46,18 +44,14 @@ pub fn normalize(
) {
let aggregator_config = ctx.config.aggregator_config_for(MetricNamespace::Spans);
let model_data = ctx.global_config.ai_model_metadata();
let sampling_project_id = ctx
let mut dsc = spans.headers.dsc().cloned();
let project_id = ctx
.sampling_project_info
.and_then(|p| p.project_id)
.or(ctx.project_info.project_id);
let dsc = spans.headers.dsc().cloned();
let dsc = dsc
.as_ref()
.zip(sampling_project_id)
.map(|(dsc, sampling_project_id)| EnrichedDsc {
dsc,
sampling_project_id,
});
.unwrap_or(ctx.project_info)
.project_id;
if let Some(dsc) = &mut dsc {
dsc.project_id = project_id;
}
Comment thread
elramen marked this conversation as resolved.
let norm = normalize::NormalizeSpanConfig {
received_at: spans.received_at(),
timestamp_range: aggregator_config.timestamp_range(),
Expand All @@ -79,7 +73,7 @@ pub fn normalize(
client_ip: spans.headers.meta().client_addr().map(Into::into),
geo_lookup,
span_op_defaults: ctx.global_config.span_op_defaults.borrow(),
dsc,
dsc: dsc.as_ref(),
};

spans.retain(
Expand Down
Loading
Loading