From 327df95c81fefb5a3a5258f0797435ea5403f800 Mon Sep 17 00:00:00 2001 From: Alexander Dinauer Date: Tue, 14 Apr 2026 06:59:41 +0200 Subject: [PATCH 1/2] fix(test): Enable Kafka profile for Spring Kafka system tests Make the system test runner configure Kafka requirements by module. Start Kafka and set SPRING_PROFILES_ACTIVE=kafka for modules that need Kafka-backed Spring endpoints so queue system tests run with the expected routing and broker configuration. Co-Authored-By: Claude --- test/system-test-runner.py | 18 +++++++++++++++++- 1 file changed, 17 insertions(+), 1 deletion(-) diff --git a/test/system-test-runner.py b/test/system-test-runner.py index 64979b3e0e..5102c66d92 100644 --- a/test/system-test-runner.py +++ b/test/system-test-runner.py @@ -68,6 +68,13 @@ KAFKA_CONTAINER_NAME = "sentry-java-system-test-kafka" KAFKA_BOOTSTRAP_SERVERS = "localhost:9092" +KAFKA_BROKER_REQUIRED_MODULES = { + "sentry-samples-console", + "sentry-samples-spring-boot-jakarta", +} +KAFKA_PROFILE_REQUIRED_MODULES = { + "sentry-samples-spring-boot-jakarta", +} class ServerType(Enum): TOMCAT = 0 @@ -202,7 +209,10 @@ def kill_process(self, pid: int, name: str) -> None: print(f"Process {pid} was already dead") def module_requires_kafka(self, sample_module: str) -> bool: - return sample_module == "sentry-samples-console" + return sample_module in KAFKA_BROKER_REQUIRED_MODULES + + def module_requires_kafka_profile(self, sample_module: str) -> bool: + return sample_module in KAFKA_PROFILE_REQUIRED_MODULES def wait_for_port(self, host: str, port: int, max_attempts: int = 20) -> bool: for _ in range(max_attempts): @@ -423,6 +433,12 @@ def start_spring_server(self, sample_module: str, java_agent: str, java_agent_au env.update(SENTRY_ENVIRONMENT_VARIABLES) env["SENTRY_AUTO_INIT"] = java_agent_auto_init + if self.module_requires_kafka_profile(sample_module): + env["SPRING_PROFILES_ACTIVE"] = "kafka" + print("Enabling Spring profile: kafka") + else: + env.pop("SPRING_PROFILES_ACTIVE", None) + # Build command jar_path = f"sentry-samples/{sample_module}/build/libs/{sample_module}-0.0.1-SNAPSHOT.jar" cmd = ["java"] From bd9d3b5e0e9b595797bf0fbb1148b080be099a7b Mon Sep 17 00:00:00 2001 From: Alexander Dinauer Date: Fri, 17 Apr 2026 06:42:36 +0200 Subject: [PATCH 2/2] fix(spring): Guard Kafka auto-config on sentry-kafka Require the sentry-kafka producer interceptor class before activating Spring Boot Jakarta queue auto-configuration. This keeps sentry-kafka optional for customers who only use the starter without Kafka queue tracing support on the classpath. Add a regression test that hides sentry-kafka from the classloader and verifies the Kafka bean post-processors are skipped instead of being registered. Co-Authored-By: Claude --- .../boot/jakarta/SentryAutoConfiguration.java | 7 +++++-- .../jakarta/SentryKafkaAutoConfigurationTest.kt | 15 +++++++++++++++ 2 files changed, 20 insertions(+), 2 deletions(-) diff --git a/sentry-spring-boot-jakarta/src/main/java/io/sentry/spring/boot/jakarta/SentryAutoConfiguration.java b/sentry-spring-boot-jakarta/src/main/java/io/sentry/spring/boot/jakarta/SentryAutoConfiguration.java index 0499df95b1..688153046f 100644 --- a/sentry-spring-boot-jakarta/src/main/java/io/sentry/spring/boot/jakarta/SentryAutoConfiguration.java +++ b/sentry-spring-boot-jakarta/src/main/java/io/sentry/spring/boot/jakarta/SentryAutoConfiguration.java @@ -77,7 +77,6 @@ import org.springframework.core.annotation.Order; import org.springframework.core.env.Environment; import org.springframework.graphql.execution.DataFetcherExceptionResolverAdapter; -import org.springframework.kafka.core.KafkaTemplate; import org.springframework.scheduling.quartz.SchedulerFactoryBean; import org.springframework.security.core.context.SecurityContextHolder; import org.springframework.web.client.RestClient; @@ -250,7 +249,11 @@ static class SentryCacheConfiguration { } @Configuration(proxyBeanMethods = false) - @ConditionalOnClass(KafkaTemplate.class) + @ConditionalOnClass( + name = { + "org.springframework.kafka.core.KafkaTemplate", + "io.sentry.kafka.SentryKafkaProducerInterceptor" + }) @ConditionalOnProperty(name = "sentry.enable-queue-tracing", havingValue = "true") @ConditionalOnMissingClass("io.sentry.opentelemetry.SentryAutoConfigurationCustomizerProvider") @Open diff --git a/sentry-spring-boot-jakarta/src/test/kotlin/io/sentry/spring/boot/jakarta/SentryKafkaAutoConfigurationTest.kt b/sentry-spring-boot-jakarta/src/test/kotlin/io/sentry/spring/boot/jakarta/SentryKafkaAutoConfigurationTest.kt index c0963580f3..ee4779b8a3 100644 --- a/sentry-spring-boot-jakarta/src/test/kotlin/io/sentry/spring/boot/jakarta/SentryKafkaAutoConfigurationTest.kt +++ b/sentry-spring-boot-jakarta/src/test/kotlin/io/sentry/spring/boot/jakarta/SentryKafkaAutoConfigurationTest.kt @@ -1,5 +1,6 @@ package io.sentry.spring.boot.jakarta +import io.sentry.kafka.SentryKafkaProducerInterceptor import io.sentry.opentelemetry.SentryAutoConfigurationCustomizerProvider import io.sentry.spring.jakarta.kafka.SentryKafkaConsumerBeanPostProcessor import io.sentry.spring.jakarta.kafka.SentryKafkaProducerBeanPostProcessor @@ -30,6 +31,9 @@ class SentryKafkaAutoConfigurationTest { private val noOtelClassLoader = FilteredClassLoader(SentryAutoConfigurationCustomizerProvider::class.java) + private val noSentryKafkaClassLoader = + FilteredClassLoader(SentryKafkaProducerInterceptor::class.java) + @Test fun `registers Kafka BPPs when queue tracing is enabled`() { contextRunner @@ -49,6 +53,17 @@ class SentryKafkaAutoConfigurationTest { } } + @Test + fun `does not register Kafka BPPs when sentry-kafka is not present`() { + contextRunner + .withClassLoader(noSentryKafkaClassLoader) + .withPropertyValues("sentry.enable-queue-tracing=true") + .run { context -> + assertThat(context).doesNotHaveBean(SentryKafkaProducerBeanPostProcessor::class.java) + assertThat(context).doesNotHaveBean(SentryKafkaConsumerBeanPostProcessor::class.java) + } + } + @Test fun `does not register Kafka BPPs when queue tracing is explicitly false`() { contextRunner