Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
49 commits
Select commit Hold shift + click to select a range
8b99d2d
declarative config
zeitlinger Jun 18, 2025
1ef1148
isolate map converter
zeitlinger Jun 18, 2025
92c6618
embedded config file
zeitlinger Jun 18, 2025
4fb1363
embedded config file
zeitlinger Jun 18, 2025
6bd882e
config bridge
zeitlinger Jun 18, 2025
b65d454
config bridge
zeitlinger Jun 18, 2025
5da12b3
use InstrumentationConfig for encapsulation
zeitlinger Jun 18, 2025
15c2890
use InstrumentationConfig for encapsulation
zeitlinger Jun 18, 2025
87d75a1
use InstrumentationConfig for encapsulation
zeitlinger Jun 18, 2025
25b7884
use InstrumentationConfig for encapsulation
zeitlinger Jun 18, 2025
d61e7b1
create component loader directly (doesn't work otherwise)
zeitlinger Jun 19, 2025
db2b93f
fix disabled config
zeitlinger Jun 19, 2025
9d69d5e
add test
zeitlinger Jun 19, 2025
cd7f827
add test
zeitlinger Jun 19, 2025
0a165ae
add test
zeitlinger Jun 19, 2025
451f3ee
add test
zeitlinger Jun 19, 2025
00eae94
add test
zeitlinger Jun 19, 2025
be11de3
add test
zeitlinger Jun 19, 2025
7e1d3a7
add test
zeitlinger Jun 19, 2025
443828a
add test
zeitlinger Jun 19, 2025
ff121c3
add test
zeitlinger Jun 19, 2025
809c906
add test
zeitlinger Jun 19, 2025
4136013
cleanup
zeitlinger Jun 19, 2025
39214aa
cleanup
zeitlinger Jun 19, 2025
ec91535
format
zeitlinger Jun 19, 2025
8dda0fa
fix rebase
zeitlinger Jun 30, 2025
9c68b5f
fix rebase
zeitlinger Jun 30, 2025
4dfd9e8
./gradlew spotlessApply
otelbot[bot] Jun 30, 2025
7c01608
fix rebase
zeitlinger Jul 7, 2025
440d997
extract condition
zeitlinger Jul 7, 2025
27f3919
use _
zeitlinger Jul 8, 2025
fef2953
use declarative config properties
zeitlinger Jul 8, 2025
1aa0a45
use declarative config properties
zeitlinger Jul 8, 2025
9c5b7ba
fix rebase
zeitlinger Aug 15, 2025
fa5ef15
fix rebase
zeitlinger Aug 16, 2025
fcd4fe2
fix rebase
zeitlinger Aug 29, 2025
e82c5f6
fix rebase
zeitlinger Aug 29, 2025
f480ec8
fix test
zeitlinger Sep 5, 2025
fb975cc
bug was fixed
zeitlinger Sep 17, 2025
d4fd64a
add distro
zeitlinger Sep 17, 2025
63a318a
map default enabled
zeitlinger Sep 17, 2025
1b4a2a0
simplify
zeitlinger Sep 29, 2025
62903e5
api diff
zeitlinger Sep 29, 2025
c3dcfc8
fix
zeitlinger Sep 30, 2025
94bef10
fix
zeitlinger Sep 30, 2025
a7540f5
add test condition
jaydeluca Oct 7, 2025
823068d
reorder
zeitlinger Oct 7, 2025
f6af6c1
add spring starter declarative config span logging
zeitlinger Sep 5, 2025
521d166
Merge branch 'main' into spring-starter-declarative-config-logging-ex…
zeitlinger Oct 8, 2025
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
Original file line number Diff line number Diff line change
@@ -1,2 +1,5 @@
Comparing source compatibility of opentelemetry-spring-boot-autoconfigure-2.21.0-SNAPSHOT.jar against opentelemetry-spring-boot-autoconfigure-2.20.1.jar
No changes.
=== UNCHANGED CLASS: PUBLIC io.opentelemetry.instrumentation.spring.autoconfigure.OpenTelemetryAutoConfiguration (not serializable)
=== CLASS FILE FORMAT VERSION: 52.0 <- 52.0
--- REMOVED ANNOTATION: org.springframework.boot.context.properties.EnableConfigurationProperties
--- REMOVED ELEMENT: value=io.opentelemetry.instrumentation.spring.autoconfigure.internal.properties.OtlpExporterProperties,io.opentelemetry.instrumentation.spring.autoconfigure.internal.properties.OtelResourceProperties,io.opentelemetry.instrumentation.spring.autoconfigure.internal.properties.OtelSpringProperties (-)
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,9 @@ dependencies {
annotationProcessor("org.springframework.boot:spring-boot-autoconfigure-processor:$springBootVersion")
annotationProcessor("org.springframework.boot:spring-boot-configuration-processor:$springBootVersion")
implementation("javax.validation:validation-api")
// snake yaml is already used by "spring-boot-resources"
// and less likely to cause problems compared to jackson
implementation("org.snakeyaml:snakeyaml-engine")

implementation(project(":instrumentation-annotations-support"))
implementation(project(":instrumentation:kafka:kafka-clients:kafka-clients-2.6:library"))
Expand Down Expand Up @@ -65,7 +68,9 @@ dependencies {
library("org.springframework.boot:spring-boot-starter-data-jdbc:$springBootVersion")

implementation("io.opentelemetry:opentelemetry-sdk-extension-autoconfigure")
implementation("io.opentelemetry:opentelemetry-sdk-extension-incubator")
implementation(project(":sdk-autoconfigure-support"))
implementation(project(":declarative-config-bridge"))
compileOnly("io.opentelemetry:opentelemetry-extension-trace-propagators")
compileOnly("io.opentelemetry.contrib:opentelemetry-aws-xray-propagator")
compileOnly("io.opentelemetry:opentelemetry-exporter-logging")
Expand All @@ -80,6 +85,7 @@ dependencies {
testLibrary("org.springframework.boot:spring-boot-starter-test:$springBootVersion") {
exclude("org.junit.vintage", "junit-vintage-engine")
}

testImplementation("javax.servlet:javax.servlet-api:3.1.0")
testImplementation("jakarta.servlet:jakarta.servlet-api:5.0.0")
testRuntimeOnly("com.h2database:h2:1.4.197")
Expand Down Expand Up @@ -173,6 +179,17 @@ testing {
}
}
}

val testDeclarativeConfig by registering(JvmTestSuite::class) {
dependencies {
implementation(project())
implementation("io.opentelemetry:opentelemetry-sdk")
implementation("org.springframework.boot:spring-boot-starter-test:$springBootVersion") {
exclude("org.junit.vintage", "junit-vintage-engine")
}
implementation("org.springframework.boot:spring-boot-starter-web:$springBootVersion")
}
}
}
}

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,91 @@
/*
* Copyright The OpenTelemetry Authors
* SPDX-License-Identifier: Apache-2.0
*/

package io.opentelemetry.instrumentation.spring.autoconfigure;

import io.opentelemetry.sdk.extension.incubator.fileconfig.DeclarativeConfiguration;
import io.opentelemetry.sdk.extension.incubator.fileconfig.internal.model.OpenTelemetryConfigurationModel;
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.nio.charset.StandardCharsets;
import java.util.Map;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import javax.annotation.Nullable;
import org.snakeyaml.engine.v2.api.Dump;
import org.snakeyaml.engine.v2.api.DumpSettings;
import org.snakeyaml.engine.v2.api.Load;
import org.snakeyaml.engine.v2.api.LoadSettings;
import org.springframework.boot.env.OriginTrackedMapPropertySource;
import org.springframework.core.env.ConfigurableEnvironment;
import org.springframework.core.env.PropertySource;

class EmbeddedConfigFile {

private EmbeddedConfigFile() {
// Utility class
}

private static final Pattern PATTERN =
Pattern.compile(
"^Config resource 'class path resource \\[(.+)]' via location 'optional:classpath:/'$");

static OpenTelemetryConfigurationModel extractModel(ConfigurableEnvironment environment)
throws IOException {
for (PropertySource<?> propertySource : environment.getPropertySources()) {
if (propertySource instanceof OriginTrackedMapPropertySource) {
return getModel(environment, (OriginTrackedMapPropertySource) propertySource);
}
}
throw new IllegalStateException("No application.yaml file found.");
}

private static OpenTelemetryConfigurationModel getModel(
ConfigurableEnvironment environment, OriginTrackedMapPropertySource source)
throws IOException {
Matcher matcher = PATTERN.matcher(source.getName());
if (matcher.matches()) {
String file = matcher.group(1);

try (InputStream resourceAsStream =
environment.getClass().getClassLoader().getResourceAsStream(file)) {
if (resourceAsStream != null) {
return extractOtelConfigFile(resourceAsStream);
} else {
throw new IllegalStateException("Unable to load " + file + " in the classpath.");
}
}
} else {
throw new IllegalStateException(
"No OpenTelemetry configuration found in the application.yaml file.");
}
}

@Nullable
@SuppressWarnings("unchecked")
private static String parseOtelNode(InputStream in) {
Load load = new Load(LoadSettings.builder().build());
Dump dump = new Dump(DumpSettings.builder().build());
for (Object o : load.loadAllFromInputStream(in)) {
Map<String, Object> data = (Map<String, Object>) o;
Map<String, Map<String, Object>> otel = (Map<String, Map<String, Object>>) data.get("otel");
if (otel != null) {
return dump.dumpToString(otel);
}
}
throw new IllegalStateException("No 'otel' configuration found in the YAML file.");
}

private static OpenTelemetryConfigurationModel extractOtelConfigFile(InputStream content) {
String node = parseOtelNode(content);
if (node == null || node.isEmpty()) {
throw new IllegalStateException("otel node is empty or null in the YAML file.");
}

return DeclarativeConfiguration.parse(
new ByteArrayInputStream(node.getBytes(StandardCharsets.UTF_8)));
}
}
Loading
Loading