Allow Embedded Cache sizes to be configured via the CLI
Closes #31514 Signed-off-by: Ryan Emerson <remerson@redhat.com>
This commit is contained in:
parent
2d6140cb34
commit
adb8d989f5
15 changed files with 415 additions and 67 deletions
|
@ -159,6 +159,10 @@ The `proxy-trusted-addresses` can be used when the `proxy-headers` option is set
|
|||
|
||||
The `https-certificates-reload-period` option can be set to define the reloading period of key store, trust store, and certificate files referenced by https-* options. Use -1 to disable reloading. Defaults to 1h (one hour).
|
||||
|
||||
= Options to configure cache max-count added
|
||||
|
||||
The `--cache-embedded-$\{CACHE_NAME}-max-count=` can be set to define an upper bound on the number of cache entries in the specified cache.
|
||||
|
||||
= Property `origin` in the `UserRepresentation` is deprecated
|
||||
|
||||
The `origin` property in the `UserRepresentation` is deprecated and planned to be removed in future releases.
|
||||
|
|
|
@ -166,6 +166,14 @@ This cache is needed for the Brute Force Protection feature to work in a multi-n
|
|||
Action tokens are used for scenarios when a user needs to confirm an action asynchronously, for example in the emails sent by the forgot password flow.
|
||||
The `actionTokens` distributed cache is used to track metadata about action tokens.
|
||||
|
||||
=== Configuring cache maximum size
|
||||
In order to reduce memory usage, it's possible to place an upper bound on the number of entries which are stored in a given
|
||||
cache. To specify an upper bound of on a cache, you must provide the following command line argument
|
||||
`--cache-embedded-$\{CACHE_NAME}-max-count=`, with `$\{CACHE_NAME}` replaced with the name of the cache you would like to
|
||||
apply the upper bound to. For example, to apply an upper-bound of `1000` to the `offlineSessions` cache you would configure
|
||||
`--cache-embedded-offline-sessions-max-count=1000`. An upper bound can not be defined on the following caches:
|
||||
`actionToken`, `authenticationSessions`, `loginFailures`, `work`.
|
||||
|
||||
=== Configuring caches for availability
|
||||
|
||||
Distributed caches replicate cache entries on a subset of nodes in a cluster and assigns entries to fixed owner nodes.
|
||||
|
|
|
@ -1,15 +1,15 @@
|
|||
package org.keycloak.config;
|
||||
|
||||
import java.io.File;
|
||||
import java.util.List;
|
||||
import java.util.stream.Collectors;
|
||||
import java.util.stream.Stream;
|
||||
|
||||
import com.google.common.base.CaseFormat;
|
||||
|
||||
public class CachingOptions {
|
||||
|
||||
public static final String CACHE_CONFIG_FILE_PROPERTY = "cache-config-file";
|
||||
|
||||
private static final String CACHE_EMBEDDED_MTLS_PREFIX = "cache-embedded-mtls";
|
||||
private static final String CACHE_EMBEDDED_PREFIX = "cache-embedded";
|
||||
private static final String CACHE_EMBEDDED_MTLS_PREFIX = CACHE_EMBEDDED_PREFIX + "-mtls";
|
||||
public static final String CACHE_EMBEDDED_MTLS_ENABLED_PROPERTY = CACHE_EMBEDDED_MTLS_PREFIX + "-enabled";
|
||||
public static final String CACHE_EMBEDDED_MTLS_KEYSTORE_FILE_PROPERTY = CACHE_EMBEDDED_MTLS_PREFIX + "-key-store-file";
|
||||
public static final String CACHE_EMBEDDED_MTLS_KEYSTORE_PASSWORD_PROPERTY = CACHE_EMBEDDED_MTLS_PREFIX + "-key-store-password";
|
||||
|
@ -26,6 +26,10 @@ public class CachingOptions {
|
|||
private static final String CACHE_METRICS_PREFIX = "cache-metrics";
|
||||
public static final String CACHE_METRICS_HISTOGRAMS_ENABLED_PROPERTY = CACHE_METRICS_PREFIX + "-histograms-enabled";
|
||||
|
||||
public static final String[] LOCAL_MAX_COUNT_CACHES = new String[]{"authorization", "keys", "realms", "users", };
|
||||
|
||||
public static final String[] CLUSTERED_MAX_COUNT_CACHES = new String[]{"clientSessions", "offlineSessions", "offlineClientSessions", "sessions"};
|
||||
|
||||
public enum Mechanism {
|
||||
ispn,
|
||||
local
|
||||
|
@ -131,4 +135,16 @@ public class CachingOptions {
|
|||
.description("Enable TLS support to communicate with a secured remote Infinispan server. Recommended to be enabled in production.")
|
||||
.defaultValue(Boolean.TRUE)
|
||||
.build();
|
||||
|
||||
public static Option<Integer> maxCountOption(String cache) {
|
||||
return new OptionBuilder<>(cacheMaxCountProperty(cache), Integer.class)
|
||||
.category(OptionCategory.CACHE)
|
||||
.description(String.format("The maximum number of entries that can be stored in-memory by the %s cache.", cache))
|
||||
.build();
|
||||
}
|
||||
|
||||
public static String cacheMaxCountProperty(String cacheName) {
|
||||
cacheName = CaseFormat.LOWER_CAMEL.to(CaseFormat.LOWER_HYPHEN, cacheName);
|
||||
return String.format("%s-%s-max-count", CACHE_EMBEDDED_PREFIX, cacheName);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,17 +1,25 @@
|
|||
package org.keycloak.quarkus.runtime.configuration.mappers;
|
||||
|
||||
import org.keycloak.config.CachingOptions;
|
||||
import org.keycloak.quarkus.runtime.Environment;
|
||||
|
||||
import io.smallrye.config.ConfigSourceInterceptorContext;
|
||||
|
||||
import static java.util.Optional.of;
|
||||
import static org.keycloak.quarkus.runtime.configuration.Configuration.getOptionalKcValue;
|
||||
import static org.keycloak.quarkus.runtime.configuration.mappers.PropertyMapper.fromOption;
|
||||
|
||||
import java.io.File;
|
||||
import java.nio.file.Paths;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
import java.util.Optional;
|
||||
import java.util.function.BooleanSupplier;
|
||||
import java.util.stream.Stream;
|
||||
|
||||
import org.keycloak.config.CachingOptions;
|
||||
import org.keycloak.config.OptionBuilder;
|
||||
import org.keycloak.config.OptionCategory;
|
||||
import org.keycloak.infinispan.util.InfinispanUtils;
|
||||
import org.keycloak.quarkus.runtime.Environment;
|
||||
|
||||
import io.smallrye.config.ConfigSourceInterceptorContext;
|
||||
|
||||
final class CachingPropertyMappers {
|
||||
|
||||
|
@ -21,61 +29,71 @@ final class CachingPropertyMappers {
|
|||
}
|
||||
|
||||
public static PropertyMapper<?>[] getClusteringPropertyMappers() {
|
||||
return new PropertyMapper[] {
|
||||
fromOption(CachingOptions.CACHE)
|
||||
.paramLabel("type")
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_STACK)
|
||||
.to("kc.spi-connections-infinispan-quarkus-stack")
|
||||
.paramLabel("stack")
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_CONFIG_FILE)
|
||||
.mapFrom("cache")
|
||||
.to("kc.spi-connections-infinispan-quarkus-config-file")
|
||||
.transformer(CachingPropertyMappers::resolveConfigFile)
|
||||
.paramLabel("file")
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_EMBEDDED_MTLS_ENABLED)
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_EMBEDDED_MTLS_KEYSTORE.withRuntimeSpecificDefault(getDefaultKeystorePathValue()))
|
||||
.paramLabel("file")
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_EMBEDDED_MTLS_KEYSTORE_PASSWORD)
|
||||
.paramLabel("password")
|
||||
.isMasked(true)
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_EMBEDDED_MTLS_TRUSTSTORE.withRuntimeSpecificDefault(getDefaultTruststorePathValue()))
|
||||
.paramLabel("file")
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_EMBEDDED_MTLS_TRUSTSTORE_PASSWORD)
|
||||
.paramLabel("password")
|
||||
.isMasked(true)
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_REMOTE_HOST)
|
||||
.paramLabel("hostname")
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_REMOTE_PORT)
|
||||
.isEnabled(CachingPropertyMappers::remoteHostSet, CachingPropertyMappers.REMOTE_HOST_SET)
|
||||
.paramLabel("port")
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_REMOTE_TLS_ENABLED)
|
||||
.isEnabled(CachingPropertyMappers::remoteHostSet, CachingPropertyMappers.REMOTE_HOST_SET)
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_REMOTE_USERNAME)
|
||||
.isEnabled(CachingPropertyMappers::remoteHostSet, CachingPropertyMappers.REMOTE_HOST_SET)
|
||||
.paramLabel("username")
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_REMOTE_PASSWORD)
|
||||
.isEnabled(CachingPropertyMappers::remoteHostSet, CachingPropertyMappers.REMOTE_HOST_SET)
|
||||
.paramLabel("password")
|
||||
.isMasked(true)
|
||||
.build(),
|
||||
List<PropertyMapper<?>> staticMappers = List.of(
|
||||
fromOption(CachingOptions.CACHE)
|
||||
.paramLabel("type")
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_STACK)
|
||||
.to("kc.spi-connections-infinispan-quarkus-stack")
|
||||
.paramLabel("stack")
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_CONFIG_FILE)
|
||||
.mapFrom("cache")
|
||||
.to("kc.spi-connections-infinispan-quarkus-config-file")
|
||||
.transformer(CachingPropertyMappers::resolveConfigFile)
|
||||
.paramLabel("file")
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_EMBEDDED_MTLS_ENABLED)
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_EMBEDDED_MTLS_KEYSTORE.withRuntimeSpecificDefault(getDefaultKeystorePathValue()))
|
||||
.paramLabel("file")
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_EMBEDDED_MTLS_KEYSTORE_PASSWORD)
|
||||
.paramLabel("password")
|
||||
.isMasked(true)
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_EMBEDDED_MTLS_TRUSTSTORE.withRuntimeSpecificDefault(getDefaultTruststorePathValue()))
|
||||
.paramLabel("file")
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_EMBEDDED_MTLS_TRUSTSTORE_PASSWORD)
|
||||
.paramLabel("password")
|
||||
.isMasked(true)
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_REMOTE_HOST)
|
||||
.paramLabel("hostname")
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_REMOTE_PORT)
|
||||
.isEnabled(CachingPropertyMappers::remoteHostSet, CachingPropertyMappers.REMOTE_HOST_SET)
|
||||
.paramLabel("port")
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_REMOTE_TLS_ENABLED)
|
||||
.isEnabled(CachingPropertyMappers::remoteHostSet, CachingPropertyMappers.REMOTE_HOST_SET)
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_REMOTE_USERNAME)
|
||||
.isEnabled(CachingPropertyMappers::remoteHostSet, CachingPropertyMappers.REMOTE_HOST_SET)
|
||||
.paramLabel("username")
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_REMOTE_PASSWORD)
|
||||
.isEnabled(CachingPropertyMappers::remoteHostSet, CachingPropertyMappers.REMOTE_HOST_SET)
|
||||
.paramLabel("password")
|
||||
.isMasked(true)
|
||||
.build(),
|
||||
fromOption(CachingOptions.CACHE_METRICS_HISTOGRAMS_ENABLED)
|
||||
.isEnabled(MetricsPropertyMappers::metricsEnabled, MetricsPropertyMappers.METRICS_ENABLED_MSG)
|
||||
.build()
|
||||
);
|
||||
|
||||
fromOption(CachingOptions.CACHE_METRICS_HISTOGRAMS_ENABLED)
|
||||
.isEnabled(MetricsPropertyMappers::metricsEnabled, MetricsPropertyMappers.METRICS_ENABLED_MSG)
|
||||
.build(),
|
||||
int numMappers = staticMappers.size() + CachingOptions.LOCAL_MAX_COUNT_CACHES.length + CachingOptions.CLUSTERED_MAX_COUNT_CACHES.length;
|
||||
List<PropertyMapper<?>> mappers = new ArrayList<>(numMappers);
|
||||
mappers.addAll(staticMappers);
|
||||
|
||||
};
|
||||
for (String cache : CachingOptions.LOCAL_MAX_COUNT_CACHES)
|
||||
mappers.add(maxCountOpt(cache, () -> true, ""));
|
||||
|
||||
for (String cache : CachingOptions.CLUSTERED_MAX_COUNT_CACHES)
|
||||
mappers.add(maxCountOpt(cache, InfinispanUtils::isEmbeddedInfinispan, "embedded Infinispan clusters configured"));
|
||||
|
||||
return mappers.toArray(new PropertyMapper[0]);
|
||||
}
|
||||
|
||||
private static boolean remoteHostSet() {
|
||||
|
@ -128,4 +146,11 @@ final class CachingPropertyMappers {
|
|||
|
||||
return null;
|
||||
}
|
||||
|
||||
private static PropertyMapper<?> maxCountOpt(String cacheName, BooleanSupplier isEnabled, String enabledWhen) {
|
||||
return fromOption(CachingOptions.maxCountOption(cacheName))
|
||||
.isEnabled(isEnabled, enabledWhen)
|
||||
.paramLabel("max-count")
|
||||
.build();
|
||||
}
|
||||
}
|
||||
|
|
|
@ -312,9 +312,10 @@ public class CacheManagerFactory {
|
|||
configureTransportStack(builder);
|
||||
configureRemoteStores(builder);
|
||||
}
|
||||
configureCacheMaxCount(builder, CachingOptions.CLUSTERED_MAX_COUNT_CACHES);
|
||||
configureSessionsCaches(builder);
|
||||
}
|
||||
|
||||
configureCacheMaxCount(builder, CachingOptions.LOCAL_MAX_COUNT_CACHES);
|
||||
checkForRemoteStores(builder);
|
||||
|
||||
var start = isStartEagerly();
|
||||
|
@ -500,6 +501,19 @@ public class CacheManagerFactory {
|
|||
});
|
||||
}
|
||||
|
||||
private static void configureCacheMaxCount(ConfigurationBuilderHolder holder, String[] caches) {
|
||||
for (String cache : caches) {
|
||||
String propKey = CachingOptions.cacheMaxCountProperty(cache);
|
||||
Configuration.getOptionalKcValue(propKey)
|
||||
.map(Integer::parseInt)
|
||||
.ifPresent(maxCount -> holder.getNamedConfigurationBuilders()
|
||||
.get(cache)
|
||||
.memory()
|
||||
.maxCount(maxCount)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
private static String requiredStringProperty(String propertyName) {
|
||||
return Configuration.getOptionalKcValue(propertyName).orElseThrow(() -> new RuntimeException("Property " + propertyName + " required but not specified"));
|
||||
}
|
||||
|
|
|
@ -24,8 +24,12 @@ import static org.keycloak.quarkus.runtime.Environment.isWindows;
|
|||
import static org.keycloak.quarkus.runtime.configuration.ConfigArgsConfigSource.CLI_ARGS;
|
||||
|
||||
import java.nio.file.Path;
|
||||
import java.util.Arrays;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
import java.util.stream.Collectors;
|
||||
import java.util.stream.Stream;
|
||||
|
||||
import io.smallrye.config.SmallRyeConfig;
|
||||
import org.hibernate.dialect.H2Dialect;
|
||||
|
@ -38,6 +42,7 @@ import org.hibernate.dialect.MariaDBDialect;
|
|||
import org.junit.Assert;
|
||||
import org.junit.Test;
|
||||
import org.keycloak.Config;
|
||||
import org.keycloak.config.CachingOptions;
|
||||
import org.keycloak.quarkus.runtime.configuration.ConfigArgsConfigSource;
|
||||
|
||||
import org.keycloak.quarkus.runtime.Environment;
|
||||
|
@ -486,4 +491,25 @@ public class ConfigurationTest extends AbstractConfigurationTest {
|
|||
ConfigArgsConfigSource.setCliArgs("--https-certificates-reload-period=2h");
|
||||
assertEquals("2h", createConfig().getConfigValue("quarkus.http.ssl.certificate.reload-period").getValue());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testCacheMaxCount() {
|
||||
int maxCount = 500;
|
||||
Set<String> maxCountCaches = Stream.of(CachingOptions.LOCAL_MAX_COUNT_CACHES, CachingOptions.CLUSTERED_MAX_COUNT_CACHES)
|
||||
.flatMap(Arrays::stream)
|
||||
.collect(Collectors.toSet());
|
||||
|
||||
StringBuilder sb = new StringBuilder();
|
||||
for (String cache : maxCountCaches)
|
||||
sb.append(" --").append(CachingOptions.cacheMaxCountProperty(cache)).append("=").append(maxCount);
|
||||
|
||||
String args = sb.toString();
|
||||
ConfigArgsConfigSource.setCliArgs(args.split(" "));
|
||||
SmallRyeConfig config = createConfig();
|
||||
|
||||
for (String cache : maxCountCaches) {
|
||||
String prop = "kc." + CachingOptions.cacheMaxCountProperty(cache);
|
||||
assertEquals(Integer.toString(maxCount), config.getConfigValue(prop).getValue());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -17,13 +17,21 @@
|
|||
|
||||
package org.keycloak.it.resource.realm;
|
||||
|
||||
import org.infinispan.Cache;
|
||||
import org.infinispan.commons.configuration.io.ConfigurationWriter;
|
||||
import org.infinispan.commons.io.StringBuilderWriter;
|
||||
import org.infinispan.configuration.parsing.ParserRegistry;
|
||||
import org.jboss.logging.Logger;
|
||||
import org.keycloak.connections.infinispan.InfinispanConnectionProvider;
|
||||
import org.keycloak.models.KeycloakSession;
|
||||
import org.keycloak.services.resource.RealmResourceProvider;
|
||||
|
||||
import jakarta.ws.rs.GET;
|
||||
import jakarta.ws.rs.Path;
|
||||
import jakarta.ws.rs.PathParam;
|
||||
import jakarta.ws.rs.Produces;
|
||||
import jakarta.ws.rs.core.MediaType;
|
||||
import jakarta.ws.rs.core.Response;
|
||||
import org.jboss.logging.Logger;
|
||||
import org.keycloak.services.resource.RealmResourceProvider;
|
||||
|
||||
/**
|
||||
* @author Vaclav Muzikar <vmuzikar@redhat.com>
|
||||
|
@ -31,6 +39,12 @@ import org.keycloak.services.resource.RealmResourceProvider;
|
|||
public class TestRealmResource implements RealmResourceProvider {
|
||||
protected static final Logger logger = Logger.getLogger(TestRealmResource.class);
|
||||
|
||||
final InfinispanConnectionProvider infinispanConnectionProvider;
|
||||
|
||||
public TestRealmResource(KeycloakSession session) {
|
||||
this.infinispanConnectionProvider = session.getProvider(InfinispanConnectionProvider.class);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object getResource() {
|
||||
return this;
|
||||
|
@ -47,6 +61,24 @@ public class TestRealmResource implements RealmResourceProvider {
|
|||
return Response.noContent().build();
|
||||
}
|
||||
|
||||
@Path("cache/{cache}/config")
|
||||
@GET
|
||||
@Produces(MediaType.APPLICATION_JSON)
|
||||
public Response cacheConfig(@PathParam("cache") String cacheName) {
|
||||
Cache<?, ?> cache = infinispanConnectionProvider.getCache(cacheName, false);
|
||||
if (cache == null)
|
||||
return Response.status(Response.Status.NOT_FOUND).build();
|
||||
|
||||
StringBuilderWriter out = new StringBuilderWriter();
|
||||
try (ConfigurationWriter writer = ConfigurationWriter.to(out)
|
||||
.withType(org.infinispan.commons.dataconversion.MediaType.APPLICATION_JSON)
|
||||
.prettyPrint(true)
|
||||
.build()) {
|
||||
new ParserRegistry().serialize(writer, cacheName, cache.getCacheConfiguration());
|
||||
}
|
||||
return Response.ok(out.toString(), MediaType.APPLICATION_JSON).build();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void close() {
|
||||
|
||||
|
|
|
@ -31,7 +31,7 @@ public class TestRealmResourceFactory implements RealmResourceProviderFactory {
|
|||
|
||||
@Override
|
||||
public RealmResourceProvider create(KeycloakSession session) {
|
||||
return new TestRealmResource();
|
||||
return new TestRealmResource(session);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -0,0 +1,79 @@
|
|||
/*
|
||||
* Copyright 2023 Red Hat, Inc. and/or its affiliates
|
||||
* and other contributors as indicated by the @author tags.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.keycloak.it.cli.dist;
|
||||
|
||||
import static io.restassured.RestAssured.when;
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.Set;
|
||||
import java.util.stream.Collectors;
|
||||
import java.util.stream.Stream;
|
||||
|
||||
import org.infinispan.commons.dataconversion.MediaType;
|
||||
import org.infinispan.configuration.cache.Configuration;
|
||||
import org.infinispan.configuration.parsing.ConfigurationBuilderHolder;
|
||||
import org.infinispan.configuration.parsing.ParserRegistry;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.keycloak.config.CachingOptions;
|
||||
import org.keycloak.it.junit5.extension.DistributionTest;
|
||||
import org.keycloak.it.junit5.extension.RawDistOnly;
|
||||
import org.keycloak.it.junit5.extension.TestProvider;
|
||||
import org.keycloak.it.resource.realm.TestRealmResourceTestProvider;
|
||||
import org.keycloak.it.utils.KeycloakDistribution;
|
||||
|
||||
import com.google.common.base.CaseFormat;
|
||||
|
||||
/**
|
||||
* @author Ryan Emerson <remerson@redhat.com>
|
||||
*/
|
||||
@DistributionTest(keepAlive = true, enableTls = true)
|
||||
@RawDistOnly(reason = "Containers are immutable")
|
||||
public class ClusterConfigKeepAliveDistTest {
|
||||
@Test
|
||||
@TestProvider(TestRealmResourceTestProvider.class)
|
||||
void testMaxCountApplied(KeycloakDistribution dist) {
|
||||
int maxCount = 100;
|
||||
Set<String> maxCountCaches = Stream.of(CachingOptions.LOCAL_MAX_COUNT_CACHES, CachingOptions.CLUSTERED_MAX_COUNT_CACHES)
|
||||
.flatMap(Arrays::stream)
|
||||
.collect(Collectors.toSet());
|
||||
|
||||
StringBuilder sb = new StringBuilder("start-dev --cache=ispn");
|
||||
for (String cache : maxCountCaches)
|
||||
sb.append(" --").append(CachingOptions.cacheMaxCountProperty(cache)).append("=").append(maxCount);
|
||||
|
||||
String args = sb.toString();
|
||||
dist.run(args.split(" "));
|
||||
|
||||
ParserRegistry parserRegistry = new ParserRegistry();
|
||||
for (String cache : maxCountCaches) {
|
||||
String configJson = when()
|
||||
.get("/realms/master/test-resources/cache/" + cache + "/config")
|
||||
.thenReturn()
|
||||
.getBody()
|
||||
.jsonPath()
|
||||
.prettyPrint();
|
||||
|
||||
ConfigurationBuilderHolder configHolder = parserRegistry.parse(configJson, MediaType.APPLICATION_JSON);
|
||||
// Workaround for ISPN-16595
|
||||
String cacheName = CaseFormat.LOWER_CAMEL.to(CaseFormat.LOWER_HYPHEN, cache);
|
||||
Configuration config = configHolder.getNamedConfigurationBuilders().get(cacheName).build();
|
||||
assertEquals(maxCount, config.memory().maxCount());
|
||||
}
|
||||
}
|
||||
}
|
|
@ -25,6 +25,15 @@ Cache:
|
|||
--cache-config-file <file>
|
||||
Defines the file from which cache configuration should be loaded from. The
|
||||
configuration file is relative to the 'conf/' directory.
|
||||
--cache-embedded-authorization-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
authorization cache.
|
||||
--cache-embedded-client-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
clientSessions cache. Available only when embedded Infinispan clusters
|
||||
configured.
|
||||
--cache-embedded-keys-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the keys cache.
|
||||
--cache-embedded-mtls-enabled <true|false>
|
||||
Encrypts the network communication between Keycloak servers. Default: false.
|
||||
--cache-embedded-mtls-key-store-file <file>
|
||||
|
@ -39,6 +48,21 @@ Cache:
|
|||
'cache-mtls-truststore.p12' under conf/ directory.
|
||||
--cache-embedded-mtls-trust-store-password <password>
|
||||
The password to access the Truststore.
|
||||
--cache-embedded-offline-client-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
offlineClientSessions cache. Available only when embedded Infinispan
|
||||
clusters configured.
|
||||
--cache-embedded-offline-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
offlineSessions cache. Available only when embedded Infinispan clusters
|
||||
configured.
|
||||
--cache-embedded-realms-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the realms cache.
|
||||
--cache-embedded-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the sessions
|
||||
cache. Available only when embedded Infinispan clusters configured.
|
||||
--cache-embedded-users-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the users cache.
|
||||
--cache-remote-host <hostname>
|
||||
The hostname of the remote server for the remote store configuration. It
|
||||
replaces the 'host' attribute of 'remote-server' tag of the configuration
|
||||
|
|
|
@ -25,6 +25,15 @@ Cache:
|
|||
--cache-config-file <file>
|
||||
Defines the file from which cache configuration should be loaded from. The
|
||||
configuration file is relative to the 'conf/' directory.
|
||||
--cache-embedded-authorization-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
authorization cache.
|
||||
--cache-embedded-client-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
clientSessions cache. Available only when embedded Infinispan clusters
|
||||
configured.
|
||||
--cache-embedded-keys-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the keys cache.
|
||||
--cache-embedded-mtls-enabled <true|false>
|
||||
Encrypts the network communication between Keycloak servers. Default: false.
|
||||
--cache-embedded-mtls-key-store-file <file>
|
||||
|
@ -39,6 +48,21 @@ Cache:
|
|||
'cache-mtls-truststore.p12' under conf/ directory.
|
||||
--cache-embedded-mtls-trust-store-password <password>
|
||||
The password to access the Truststore.
|
||||
--cache-embedded-offline-client-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
offlineClientSessions cache. Available only when embedded Infinispan
|
||||
clusters configured.
|
||||
--cache-embedded-offline-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
offlineSessions cache. Available only when embedded Infinispan clusters
|
||||
configured.
|
||||
--cache-embedded-realms-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the realms cache.
|
||||
--cache-embedded-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the sessions
|
||||
cache. Available only when embedded Infinispan clusters configured.
|
||||
--cache-embedded-users-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the users cache.
|
||||
--cache-metrics-histograms-enabled <true|false>
|
||||
Enable histograms for metrics for the embedded caches. Default: false.
|
||||
Available only when metrics are enabled.
|
||||
|
|
|
@ -26,6 +26,15 @@ Cache:
|
|||
--cache-config-file <file>
|
||||
Defines the file from which cache configuration should be loaded from. The
|
||||
configuration file is relative to the 'conf/' directory.
|
||||
--cache-embedded-authorization-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
authorization cache.
|
||||
--cache-embedded-client-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
clientSessions cache. Available only when embedded Infinispan clusters
|
||||
configured.
|
||||
--cache-embedded-keys-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the keys cache.
|
||||
--cache-embedded-mtls-enabled <true|false>
|
||||
Encrypts the network communication between Keycloak servers. Default: false.
|
||||
--cache-embedded-mtls-key-store-file <file>
|
||||
|
@ -40,6 +49,21 @@ Cache:
|
|||
'cache-mtls-truststore.p12' under conf/ directory.
|
||||
--cache-embedded-mtls-trust-store-password <password>
|
||||
The password to access the Truststore.
|
||||
--cache-embedded-offline-client-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
offlineClientSessions cache. Available only when embedded Infinispan
|
||||
clusters configured.
|
||||
--cache-embedded-offline-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
offlineSessions cache. Available only when embedded Infinispan clusters
|
||||
configured.
|
||||
--cache-embedded-realms-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the realms cache.
|
||||
--cache-embedded-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the sessions
|
||||
cache. Available only when embedded Infinispan clusters configured.
|
||||
--cache-embedded-users-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the users cache.
|
||||
--cache-remote-host <hostname>
|
||||
The hostname of the remote server for the remote store configuration. It
|
||||
replaces the 'host' attribute of 'remote-server' tag of the configuration
|
||||
|
|
|
@ -26,6 +26,15 @@ Cache:
|
|||
--cache-config-file <file>
|
||||
Defines the file from which cache configuration should be loaded from. The
|
||||
configuration file is relative to the 'conf/' directory.
|
||||
--cache-embedded-authorization-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
authorization cache.
|
||||
--cache-embedded-client-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
clientSessions cache. Available only when embedded Infinispan clusters
|
||||
configured.
|
||||
--cache-embedded-keys-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the keys cache.
|
||||
--cache-embedded-mtls-enabled <true|false>
|
||||
Encrypts the network communication between Keycloak servers. Default: false.
|
||||
--cache-embedded-mtls-key-store-file <file>
|
||||
|
@ -40,6 +49,21 @@ Cache:
|
|||
'cache-mtls-truststore.p12' under conf/ directory.
|
||||
--cache-embedded-mtls-trust-store-password <password>
|
||||
The password to access the Truststore.
|
||||
--cache-embedded-offline-client-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
offlineClientSessions cache. Available only when embedded Infinispan
|
||||
clusters configured.
|
||||
--cache-embedded-offline-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
offlineSessions cache. Available only when embedded Infinispan clusters
|
||||
configured.
|
||||
--cache-embedded-realms-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the realms cache.
|
||||
--cache-embedded-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the sessions
|
||||
cache. Available only when embedded Infinispan clusters configured.
|
||||
--cache-embedded-users-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the users cache.
|
||||
--cache-metrics-histograms-enabled <true|false>
|
||||
Enable histograms for metrics for the embedded caches. Default: false.
|
||||
Available only when metrics are enabled.
|
||||
|
|
|
@ -26,6 +26,15 @@ Cache:
|
|||
--cache-config-file <file>
|
||||
Defines the file from which cache configuration should be loaded from. The
|
||||
configuration file is relative to the 'conf/' directory.
|
||||
--cache-embedded-authorization-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
authorization cache.
|
||||
--cache-embedded-client-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
clientSessions cache. Available only when embedded Infinispan clusters
|
||||
configured.
|
||||
--cache-embedded-keys-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the keys cache.
|
||||
--cache-embedded-mtls-enabled <true|false>
|
||||
Encrypts the network communication between Keycloak servers. Default: false.
|
||||
--cache-embedded-mtls-key-store-file <file>
|
||||
|
@ -40,6 +49,21 @@ Cache:
|
|||
'cache-mtls-truststore.p12' under conf/ directory.
|
||||
--cache-embedded-mtls-trust-store-password <password>
|
||||
The password to access the Truststore.
|
||||
--cache-embedded-offline-client-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
offlineClientSessions cache. Available only when embedded Infinispan
|
||||
clusters configured.
|
||||
--cache-embedded-offline-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
offlineSessions cache. Available only when embedded Infinispan clusters
|
||||
configured.
|
||||
--cache-embedded-realms-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the realms cache.
|
||||
--cache-embedded-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the sessions
|
||||
cache. Available only when embedded Infinispan clusters configured.
|
||||
--cache-embedded-users-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the users cache.
|
||||
--cache-remote-host <hostname>
|
||||
The hostname of the remote server for the remote store configuration. It
|
||||
replaces the 'host' attribute of 'remote-server' tag of the configuration
|
||||
|
|
|
@ -26,6 +26,15 @@ Cache:
|
|||
--cache-config-file <file>
|
||||
Defines the file from which cache configuration should be loaded from. The
|
||||
configuration file is relative to the 'conf/' directory.
|
||||
--cache-embedded-authorization-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
authorization cache.
|
||||
--cache-embedded-client-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
clientSessions cache. Available only when embedded Infinispan clusters
|
||||
configured.
|
||||
--cache-embedded-keys-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the keys cache.
|
||||
--cache-embedded-mtls-enabled <true|false>
|
||||
Encrypts the network communication between Keycloak servers. Default: false.
|
||||
--cache-embedded-mtls-key-store-file <file>
|
||||
|
@ -40,6 +49,21 @@ Cache:
|
|||
'cache-mtls-truststore.p12' under conf/ directory.
|
||||
--cache-embedded-mtls-trust-store-password <password>
|
||||
The password to access the Truststore.
|
||||
--cache-embedded-offline-client-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
offlineClientSessions cache. Available only when embedded Infinispan
|
||||
clusters configured.
|
||||
--cache-embedded-offline-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the
|
||||
offlineSessions cache. Available only when embedded Infinispan clusters
|
||||
configured.
|
||||
--cache-embedded-realms-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the realms cache.
|
||||
--cache-embedded-sessions-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the sessions
|
||||
cache. Available only when embedded Infinispan clusters configured.
|
||||
--cache-embedded-users-max-count <max-count>
|
||||
The maximum number of entries that can be stored in-memory by the users cache.
|
||||
--cache-metrics-histograms-enabled <true|false>
|
||||
Enable histograms for metrics for the embedded caches. Default: false.
|
||||
Available only when metrics are enabled.
|
||||
|
|
Loading…
Reference in a new issue