CVE-2024-10451
Description
A flaw was found in Keycloak. This issue occurs because sensitive runtime values, such as passwords, may be captured during the Keycloak build process and embedded as default values in bytecode, leading to unintended information disclosure. In Keycloak 26, sensitive data specified directly in environment variables during the build process is also stored as a default values, making it accessible during runtime. Indirect usage of environment variables for SPI options and Quarkus properties is also vulnerable due to unconditional expansion by PropertyMapper logic, capturing sensitive data as default values in all Keycloak versions up to 26.0.2.
Affected packages
Versions sourced from the GitHub Security Advisory.
| Package | Affected versions | Patched versions |
|---|---|---|
org.keycloak:keycloak-quarkus-serverMaven | < 24.0.9 | 24.0.9 |
org.keycloak:keycloak-quarkus-serverMaven | >= 25.0.0, < 26.0.6 | 26.0.6 |
Patches
1198214310eb4fix: ensures that properties are runtime properties are filtered (#35246)
3 files changed · +42 −29
quarkus/runtime/src/main/java/org/keycloak/quarkus/runtime/configuration/mappers/PropertyMapper.java+0 −21 modified@@ -41,7 +41,6 @@ import org.keycloak.config.DeprecatedMetadata; import org.keycloak.config.Option; -import org.keycloak.config.OptionBuilder; import org.keycloak.config.OptionCategory; import org.keycloak.quarkus.runtime.cli.PropertyException; import org.keycloak.quarkus.runtime.cli.ShortErrorMessageHandler; @@ -55,26 +54,6 @@ public class PropertyMapper<T> { - static PropertyMapper<?> IDENTITY = new PropertyMapper<>( - new OptionBuilder<>(null, String.class).build(), - null, - () -> false, - "", - null, - null, - null, - null, - false, - null, - null, - () -> false, - "") { - @Override - public ConfigValue getConfigValue(String name, ConfigSourceInterceptorContext context) { - return context.proceed(name); - } - }; - private final Option<T> option; private final String to; private BooleanSupplier enabled;
quarkus/runtime/src/main/java/org/keycloak/quarkus/runtime/configuration/mappers/PropertyMappers.java+22 −8 modified@@ -14,6 +14,7 @@ import org.keycloak.quarkus.runtime.cli.command.Build; import org.keycloak.quarkus.runtime.cli.command.ShowConfig; import org.keycloak.quarkus.runtime.configuration.DisabledMappersInterceptor; +import org.keycloak.quarkus.runtime.configuration.MicroProfileConfigProvider; import org.keycloak.quarkus.runtime.configuration.PersistedConfigSource; import java.util.ArrayList; @@ -36,14 +37,14 @@ import static org.keycloak.quarkus.runtime.configuration.KeycloakConfigSourceProvider.isKeyStoreConfigSource; public final class PropertyMappers { - + public static final String KC_SPI_PREFIX = "kc.spi"; public static String VALUE_MASK = "*******"; private static MappersConfig MAPPERS; private static final Logger log = Logger.getLogger(PropertyMappers.class); private PropertyMappers(){} - + static { reset(); } @@ -74,13 +75,28 @@ public static void reset() { } public static ConfigValue getValue(ConfigSourceInterceptorContext context, String name) { - return getMapperOrDefault(name, PropertyMapper.IDENTITY).getConfigValue(name, context); + PropertyMapper<?> mapper = getMapper(name); + // during re-aug do not resolve the server runtime properties and avoid they included by quarkus in the default value config source + if ((isRebuild() || Environment.isRebuildCheck()) && isKeycloakRuntime(name, mapper)) { + return ConfigValue.builder().withName(name).build(); + } + if (mapper == null) { + return context.proceed(name); + } + return mapper.getConfigValue(name, context); } public static boolean isSpiBuildTimeProperty(String name) { return name.startsWith(KC_SPI_PREFIX) && (name.endsWith("-provider") || name.endsWith("-enabled") || name.endsWith("-provider-default")); } + private static boolean isKeycloakRuntime(String name, PropertyMapper<?> mapper) { + if (mapper == null) { + return name.startsWith(MicroProfileConfigProvider.NS_KEYCLOAK) && !isSpiBuildTimeProperty(name); + } + return mapper.isRunTime(); + } + public static Map<OptionCategory, List<PropertyMapper<?>>> getRuntimeMappers() { return MAPPERS.getRuntimeMappers(); } @@ -150,10 +166,6 @@ private static PropertyMapper<?> getMapperOrDefault(String property, PropertyMap }; } - private static PropertyMapper<?> getMapperOrDefault(String property, PropertyMapper<?> defaultMapper) { - return getMapperOrDefault(property, defaultMapper, null); - } - public static PropertyMapper<?> getMapper(String property, OptionCategory category) { return getMapperOrDefault(property, null, category); } @@ -172,7 +184,9 @@ public static boolean isSupported(PropertyMapper<?> mapper) { } public static Optional<PropertyMapper<?>> getDisabledMapper(String property) { - if (property == null) return Optional.empty(); + if (property == null) { + return Optional.empty(); + } PropertyMapper<?> mapper = getDisabledBuildTimeMappers().get(property); if (mapper == null) {
quarkus/tests/integration/src/test/java/org/keycloak/it/cli/dist/StartCommandDistTest.java+20 −0 modified@@ -247,4 +247,24 @@ void testInvalidConfigFileOption(CLIResult cliResult) { cliResult.assertError("File specified via '--config-file' or '-cf' option does not exist."); cliResult.assertError(String.format("Try '%s --help' for more information on the available options.", KeycloakDistribution.SCRIPT_CMD)); } + + @RawDistOnly(reason = "Containers are immutable") + @Test + void testRuntimeValuesAreNotCaptured(KeycloakDistribution dist) { + // confirm that the invalid value prevents startup - if this passes, then we need to use a different + // spi provider + CLIResult cliResult = dist.run("start", "--spi-events-listener-jboss-logging-success-level=invalid", "--http-enabled", "true", "--hostname-strict", "false"); + cliResult.assertError("Failed to start quarkus"); + + // if there was no auto-build use an explicit build to potentially capture the runtime default + if (!cliResult.getOutput().contains("Server configuration updated and persisted")) { + cliResult = dist.run("build", "--spi-events-listener-jboss-logging-success-level=invalid"); + cliResult.assertBuild(); + } + + // the invalid value should not be the default + cliResult = dist.run("start", "--http-enabled", "true", "--hostname-strict", "false"); + cliResult.assertNoBuild(); + cliResult.assertStarted(); + } }
Vulnerability mechanics
Generated by null/stub on May 9, 2026. Inputs: CWE entries + fix-commit diffs from this CVE's patches. Citations validated against bundle.
References
10- github.com/advisories/GHSA-v7gv-xpgf-6395ghsaADVISORY
- nvd.nist.gov/vuln/detail/CVE-2024-10451ghsaADVISORY
- access.redhat.com/errata/RHSA-2024:10175nvdWEB
- access.redhat.com/errata/RHSA-2024:10176nvdWEB
- access.redhat.com/errata/RHSA-2024:10177nvdWEB
- access.redhat.com/errata/RHSA-2024:10178nvdWEB
- access.redhat.com/security/cve/CVE-2024-10451nvdWEB
- bugzilla.redhat.com/show_bug.cginvdWEB
- github.com/keycloak/keycloak/commit/198214310eb45b86707f823ccb5a2d65c814b528ghsaWEB
- github.com/keycloak/keycloak/security/advisories/GHSA-v7gv-xpgf-6395ghsaWEB
News mentions
0No linked articles in our index yet.