OTEL: Profile Feature

Closes #32231

Signed-off-by: Martin Bartoš <mabartos@redhat.com>
This commit is contained in:
Martin Bartoš 2024-08-27 17:53:39 +02:00 • committed by Alexander Schwartz
parent af53af1506
commit afcbf79582
11 changed files with 45 additions and 10 deletions

View file

@ -114,6 +114,8 @@ public class Profile {
OID4VC_VCI("Support for the OID4VCI protocol as part of OID4VC.", Type.EXPERIMENTAL),
OPENTELEMETRY("OpenTelemetry Tracing", Type.PREVIEW),
DECLARATIVE_UI("declarative ui spi", Type.EXPERIMENTAL),
ORGANIZATION("Organization support within realms", Type.PREVIEW),

View file

@ -17,9 +17,9 @@ It also provides valuable insights into performance bottlenecks and can help opt
== Enable tracing
It is possible to enable exposing traces using the build time option `tracing-enabled` as follows:
It is possible to enable exposing traces using the build time option `tracing-enabled`, and enabling `opentelemetry` feature as follows:
<@kc.start parameters="--tracing-enabled=true"/>
<@kc.start parameters="--tracing-enabled=true --features=opentelemetry"/>
By default, the trace exporters send out data in batches, using the `gRPC` protocol and endpoint `+http://localhost:4317+`.
@ -77,7 +77,7 @@ The format of the log records may start as follows:
You can hide tracing information in specific log handlers by specifying their associated {project_name} option `log-<handler-name>-include-trace`, where `<handler-name>` is the name of the log handler.
For instance, to disable trace info in the `console` log, you can turn it off as follows:
<@kc.start parameters="--tracing-enabled=true --log=console --log-console-include-trace=false"/>
<@kc.start parameters="--tracing-enabled=true --features=opentelemetry --log=console --log-console-include-trace=false"/>
NOTE: When you explicitly override the log format for the particular log handlers, the `*-include-trace` options do not have any effect, and no tracing is included.

View file

@ -47,6 +47,7 @@ import org.keycloak.operator.crds.v2alpha1.deployment.Keycloak;
import org.keycloak.operator.crds.v2alpha1.deployment.KeycloakStatusCondition;
import org.keycloak.operator.crds.v2alpha1.deployment.ValueOrSecret;
import org.keycloak.operator.crds.v2alpha1.deployment.spec.BootstrapAdminSpec;
import org.keycloak.operator.crds.v2alpha1.deployment.spec.FeatureSpec;
import org.keycloak.operator.crds.v2alpha1.deployment.spec.HostnameSpecBuilder;
import org.keycloak.operator.testsuite.unit.WatchedResourcesTest;
import org.keycloak.operator.testsuite.utils.CRAssert;
@ -390,6 +391,9 @@ public class KeycloakDeploymentTest extends BaseOperatorTest {
@Test
public void testPodNamePropagation() {
var kc = getTestKeycloakDeployment(true);
var featureSpec = new FeatureSpec();
featureSpec.setEnabledFeatures(List.of("opentelemetry"));
kc.getSpec().setFeatureSpec(featureSpec);
kc.getSpec().getAdditionalOptions().add(new ValueOrSecret("tracing-enabled", "true"));
kc.getSpec().getAdditionalOptions().add(new ValueOrSecret("log-level", "io.opentelemetry:fine"));
deployKeycloak(k8sclient, kc, true);

View file

@ -225,7 +225,7 @@ public final class LoggingPropertyMappers {
* Add tracing info to the log if the format is not explicitly set, and tracing and {@code includeTraceOption} options are enabled
*/
private static Optional<String> addTracingInfo(Optional<String> value, Option<Boolean> includeTraceOption) {
var isTracingEnabled = Configuration.isTrue(TracingOptions.TRACING_ENABLED);
var isTracingEnabled = TracingPropertyMappers.isTracingEnabled();
var includeTrace = Configuration.isTrue(includeTraceOption);
var isChangedLogFormat = !DEFAULT_LOG_FORMAT.equals(value.get());

View file

@ -18,6 +18,8 @@
package org.keycloak.quarkus.runtime.configuration.mappers;
import io.smallrye.config.ConfigValue;
import org.keycloak.common.Profile;
import org.keycloak.quarkus.runtime.Environment;
import org.keycloak.quarkus.runtime.cli.PropertyException;
import org.keycloak.quarkus.runtime.configuration.Configuration;
import org.keycloak.utils.StringUtil;
@ -38,7 +40,8 @@ import static org.keycloak.config.TracingOptions.TRACING_SERVICE_NAME;
import static org.keycloak.quarkus.runtime.configuration.mappers.PropertyMapper.fromOption;
public class TracingPropertyMappers {
private static final String TRACING_ENABLED_MSG = "Tracing is enabled";
private static final String OTEL_FEATURE_ENABLED_MSG = "'opentelemetry' feature is enabled";
private static final String TRACING_ENABLED_MSG = "'opentelemetry' feature and Tracing is enabled";
private TracingPropertyMappers() {
}
@ -46,6 +49,7 @@ public class TracingPropertyMappers {
public static PropertyMapper<?>[] getMappers() {
return new PropertyMapper[]{
fromOption(TRACING_ENABLED)
.isEnabled(TracingPropertyMappers::isFeatureEnabled, OTEL_FEATURE_ENABLED_MSG)
.to("quarkus.otel.traces.enabled")
.build(),
fromOption(TRACING_ENDPOINT)
@ -118,6 +122,11 @@ public class TracingPropertyMappers {
}
}
private static boolean isFeatureEnabled() {
Environment.getCurrentOrCreateFeatureProfile();
return Profile.isFeatureEnabled(Profile.Feature.OPENTELEMETRY);
}
public static boolean isTracingEnabled() {
return Configuration.isTrue(TRACING_ENABLED);
}

View file

@ -35,6 +35,7 @@ public class TracingDistTest {
private void assertTracingEnabled(CLIResult result) {
result.assertMessage("opentelemetry");
result.assertMessage("service.name=\"keycloak\"");
result.assertMessage("Preview features enabled: opentelemetry");
}
private void assertTracingDisabled(CLIResult result) {
@ -42,6 +43,7 @@ public class TracingDistTest {
result.assertNoMessage("service.name=\"keycloak\"");
result.assertNoMessage("Failed to export spans.");
result.assertNoMessage("Connection refused: localhost/127.0.0.1:4317");
result.assertNoMessage("Preview features enabled: opentelemetry");
}
@Test
@ -56,16 +58,34 @@ public class TracingDistTest {
@Test
@Order(2)
@Launch({"start-dev", "--tracing-enabled=true", "--log-level=io.opentelemetry:fine"})
void enabledJdbc(LaunchResult result) {
@Launch({"start-dev", "--tracing-service-name=should-fail"})
void disabledOption(LaunchResult result) {
CLIResult cliResult = (CLIResult) result;
cliResult.assertStartedDevMode();
assertTracingEnabled(cliResult);
cliResult.assertError("Disabled option: '--tracing-service-name'. Available only when 'opentelemetry' feature and Tracing is enabled");
}
@Test
@Order(3)
@Launch({"build", "--tracing-enabled=true"})
@Launch({"start-dev", "--tracing-enabled=true"})
void disabledFeature(LaunchResult result) {
CLIResult cliResult = (CLIResult) result;
cliResult.assertError("Disabled option: '--tracing-enabled'. Available only when 'opentelemetry' feature is enabled");
}
@Test
@Order(4)
@Launch({"start-dev", "--features=opentelemetry", "--tracing-enabled=false", "--tracing-endpoint=something"})
void disabledTracing(LaunchResult result) {
CLIResult cliResult = (CLIResult) result;
cliResult.assertError("Disabled option: '--tracing-endpoint'. Available only when 'opentelemetry' feature and Tracing is enabled");
}
@Test
@Order(5)
@Launch({"build", "--tracing-enabled=true", "--features=opentelemetry"})
void buildTracingEnabled(LaunchResult result) {
CLIResult cliResult = (CLIResult) result;