diff options
author | Tor Brede Vekterli <vekterli@yahooinc.com> | 2022-01-26 14:04:23 +0100 |
---|---|---|
committer | Tor Brede Vekterli <vekterli@yahooinc.com> | 2022-01-27 11:01:34 +0100 |
commit | 69dcc2d3a9ff069da85b6744a9274d7944d26c69 (patch) | |
tree | 85bde0fcd9985b920b896ed1d58b56248ab20182 | |
parent | c790fe3631168f68efcc8c9e8fe5a30e414517d2 (diff) |
Add feature flags for dynamic persistence throttling window size tuning
Added flags:
* Window size decrement factor (default 1.2)
* Window size backoff (default 0.95)
6 files changed, 83 insertions, 12 deletions
diff --git a/config-model-api/src/main/java/com/yahoo/config/model/api/ModelContext.java b/config-model-api/src/main/java/com/yahoo/config/model/api/ModelContext.java index 3bb6c7c0511..952ff090693 100644 --- a/config-model-api/src/main/java/com/yahoo/config/model/api/ModelContext.java +++ b/config-model-api/src/main/java/com/yahoo/config/model/api/ModelContext.java @@ -105,8 +105,10 @@ public interface ModelContext { @ModelFeatureFlag(owners = {"hmusum"}) default boolean failDeploymentWithInvalidJvmOptions() { return false; } @ModelFeatureFlag(owners = {"arnej", "andreer"}) default List<String> ignoredHttpUserAgents() { return List.of(); } @ModelFeatureFlag(owners = {"bjorncs"}) default boolean enableServerOcspStapling() { return false; } - @ModelFeatureFlag(owners = {"vekterli"}) default String persistenceAsyncThrottling() { throw new UnsupportedOperationException("TODO specify default value"); } - @ModelFeatureFlag(owners = {"vekterli"}) default String mergeThrottlingPolicy() { throw new UnsupportedOperationException("TODO specify default value"); } + @ModelFeatureFlag(owners = {"vekterli"}) default String persistenceAsyncThrottling() { throw new UnsupportedOperationException("TODO specify default value"); } + @ModelFeatureFlag(owners = {"vekterli"}) default String mergeThrottlingPolicy() { throw new UnsupportedOperationException("TODO specify default value"); } + @ModelFeatureFlag(owners = {"vekterli"}) default double persistenceThrottlingWsDecrementFactor() { throw new UnsupportedOperationException("TODO specify default value"); } + @ModelFeatureFlag(owners = {"vekterli"}) default double persistenceThrottlingWsBackoff() { throw new UnsupportedOperationException("TODO specify default value"); } @ModelFeatureFlag(owners = {"arnej"}) default boolean useQrserverServiceName() { return true; } } diff --git a/config-model/src/main/java/com/yahoo/config/model/deploy/TestProperties.java b/config-model/src/main/java/com/yahoo/config/model/deploy/TestProperties.java index 3aadf30e2f9..a492ee47030 100644 --- a/config-model/src/main/java/com/yahoo/config/model/deploy/TestProperties.java +++ b/config-model/src/main/java/com/yahoo/config/model/deploy/TestProperties.java @@ -72,6 +72,8 @@ public class TestProperties implements ModelContext.Properties, ModelContext.Fea private boolean failDeploymentWithInvalidJvmOptions = false; private String persistenceAsyncThrottling = "UNLIMITED"; private String mergeThrottlingPolicy = "STATIC"; + private double persistenceThrottlingWsDecrementFactor = 1.2; + private double persistenceThrottlingWsBackoff = 0.95; @Override public ModelContext.FeatureFlags featureFlags() { return this; } @Override public boolean multitenant() { return multitenant; } @@ -123,6 +125,8 @@ public class TestProperties implements ModelContext.Properties, ModelContext.Fea @Override public boolean failDeploymentWithInvalidJvmOptions() { return failDeploymentWithInvalidJvmOptions; } @Override public String persistenceAsyncThrottling() { return persistenceAsyncThrottling; } @Override public String mergeThrottlingPolicy() { return mergeThrottlingPolicy; } + @Override public double persistenceThrottlingWsDecrementFactor() { return persistenceThrottlingWsDecrementFactor; } + @Override public double persistenceThrottlingWsBackoff() { return persistenceThrottlingWsBackoff; } public TestProperties maxUnCommittedMemory(int maxUnCommittedMemory) { this.maxUnCommittedMemory = maxUnCommittedMemory; @@ -320,6 +324,16 @@ public class TestProperties implements ModelContext.Properties, ModelContext.Fea return this; } + public TestProperties setPersistenceThrottlingWsDecrementFactor(double factor) { + this.persistenceThrottlingWsDecrementFactor = factor; + return this; + } + + public TestProperties setPersistenceThrottlingWsBackoff(double backoff) { + this.persistenceThrottlingWsBackoff = backoff; + return this; + } + public static class Spec implements ConfigServerSpec { private final String hostName; diff --git a/config-model/src/main/java/com/yahoo/vespa/model/content/storagecluster/FileStorProducer.java b/config-model/src/main/java/com/yahoo/vespa/model/content/storagecluster/FileStorProducer.java index 5be06306f89..f3263658717 100644 --- a/config-model/src/main/java/com/yahoo/vespa/model/content/storagecluster/FileStorProducer.java +++ b/config-model/src/main/java/com/yahoo/vespa/model/content/storagecluster/FileStorProducer.java @@ -46,7 +46,9 @@ public class FileStorProducer implements StorFilestorConfig.Producer { private final ContentCluster cluster; private final int reponseNumThreads; private final StorFilestorConfig.Response_sequencer_type.Enum responseSequencerType; - private final StorFilestorConfig.Async_operation_throttler_type.Enum asyncOperationThrottlerType; + private final StorFilestorConfig.Async_operation_throttler.Type.Enum asyncOperationThrottlerType; + private final double persistenceThrottlingWsDecrementFactor; + private final double persistenceThrottlingWsBackoff; private final boolean useAsyncMessageHandlingOnSchedule; private static StorFilestorConfig.Response_sequencer_type.Enum convertResponseSequencerType(String sequencerType) { @@ -57,11 +59,11 @@ public class FileStorProducer implements StorFilestorConfig.Producer { } } - private static StorFilestorConfig.Async_operation_throttler_type.Enum toAsyncOperationThrottlerType(String throttlerType) { + private static StorFilestorConfig.Async_operation_throttler.Type.Enum toAsyncOperationThrottlerType(String throttlerType) { try { - return StorFilestorConfig.Async_operation_throttler_type.Enum.valueOf(throttlerType); + return StorFilestorConfig.Async_operation_throttler.Type.Enum.valueOf(throttlerType); } catch (Throwable t) { - return StorFilestorConfig.Async_operation_throttler_type.UNLIMITED; + return StorFilestorConfig.Async_operation_throttler.Type.UNLIMITED; } } @@ -71,7 +73,9 @@ public class FileStorProducer implements StorFilestorConfig.Producer { this.reponseNumThreads = featureFlags.defaultNumResponseThreads(); this.responseSequencerType = convertResponseSequencerType(featureFlags.responseSequencerType()); this.asyncOperationThrottlerType = toAsyncOperationThrottlerType(featureFlags.persistenceAsyncThrottling()); - useAsyncMessageHandlingOnSchedule = featureFlags.useAsyncMessageHandlingOnSchedule(); + this.persistenceThrottlingWsDecrementFactor = featureFlags.persistenceThrottlingWsDecrementFactor(); + this.persistenceThrottlingWsBackoff = featureFlags.persistenceThrottlingWsBackoff(); + this.useAsyncMessageHandlingOnSchedule = featureFlags.useAsyncMessageHandlingOnSchedule(); } @Override @@ -83,7 +87,16 @@ public class FileStorProducer implements StorFilestorConfig.Producer { builder.num_response_threads(reponseNumThreads); builder.response_sequencer_type(responseSequencerType); builder.use_async_message_handling_on_schedule(useAsyncMessageHandlingOnSchedule); - builder.async_operation_throttler_type(asyncOperationThrottlerType); + // TODO remove deprecated throttler type config + builder.async_operation_throttler_type((asyncOperationThrottlerType == StorFilestorConfig.Async_operation_throttler.Type.DYNAMIC) + ? StorFilestorConfig.Async_operation_throttler_type.Enum.DYNAMIC + : StorFilestorConfig.Async_operation_throttler_type.Enum.UNLIMITED); + + var throttleBuilder = new StorFilestorConfig.Async_operation_throttler.Builder(); + throttleBuilder.type(asyncOperationThrottlerType); + throttleBuilder.window_size_decrement_factor(persistenceThrottlingWsDecrementFactor); + throttleBuilder.window_size_backoff(persistenceThrottlingWsBackoff); + builder.async_operation_throttler(throttleBuilder); } } diff --git a/config-model/src/test/java/com/yahoo/vespa/model/content/StorageClusterTest.java b/config-model/src/test/java/com/yahoo/vespa/model/content/StorageClusterTest.java index 2953b0cb32d..509055df7f4 100644 --- a/config-model/src/test/java/com/yahoo/vespa/model/content/StorageClusterTest.java +++ b/config-model/src/test/java/com/yahoo/vespa/model/content/StorageClusterTest.java @@ -309,20 +309,40 @@ public class StorageClusterTest { @Test public void persistence_async_throttle_config_defaults_to_unlimited() { var config = filestorConfigFromProducer(simpleCluster(new TestProperties())); - assertEquals(StorFilestorConfig.Async_operation_throttler_type.UNLIMITED, config.async_operation_throttler_type()); + assertEquals(StorFilestorConfig.Async_operation_throttler_type.UNLIMITED, config.async_operation_throttler_type()); // TODO remove + assertEquals(StorFilestorConfig.Async_operation_throttler.Type.UNLIMITED, config.async_operation_throttler().type()); } @Test public void persistence_async_throttle_config_is_derived_from_flag() { var config = filestorConfigFromProducer(simpleCluster(new TestProperties().setPersistenceAsyncThrottling("UNLIMITED"))); - assertEquals(StorFilestorConfig.Async_operation_throttler_type.UNLIMITED, config.async_operation_throttler_type()); + assertEquals(StorFilestorConfig.Async_operation_throttler_type.UNLIMITED, config.async_operation_throttler_type()); // TODO remove + assertEquals(StorFilestorConfig.Async_operation_throttler.Type.UNLIMITED, config.async_operation_throttler().type()); config = filestorConfigFromProducer(simpleCluster(new TestProperties().setPersistenceAsyncThrottling("DYNAMIC"))); - assertEquals(StorFilestorConfig.Async_operation_throttler_type.DYNAMIC, config.async_operation_throttler_type()); + assertEquals(StorFilestorConfig.Async_operation_throttler_type.DYNAMIC, config.async_operation_throttler_type()); // TODO remove + assertEquals(StorFilestorConfig.Async_operation_throttler.Type.DYNAMIC, config.async_operation_throttler().type()); // Invalid enum values fall back to the default config = filestorConfigFromProducer(simpleCluster(new TestProperties().setPersistenceAsyncThrottling("BANANAS"))); - assertEquals(StorFilestorConfig.Async_operation_throttler_type.UNLIMITED, config.async_operation_throttler_type()); + assertEquals(StorFilestorConfig.Async_operation_throttler_type.UNLIMITED, config.async_operation_throttler_type()); // TODO remove + assertEquals(StorFilestorConfig.Async_operation_throttler.Type.UNLIMITED, config.async_operation_throttler().type()); + } + + @Test + public void persistence_dynamic_throttling_parameters_have_sane_defaults() { + var config = filestorConfigFromProducer(simpleCluster(new TestProperties())); + assertEquals(1.2, config.async_operation_throttler().window_size_decrement_factor(), 0.0001); + assertEquals(0.95, config.async_operation_throttler().window_size_backoff(), 0.0001); + } + + @Test + public void persistence_dynamic_throttling_parameters_can_be_set_through_feature_flags() { + var config = filestorConfigFromProducer(simpleCluster(new TestProperties() + .setPersistenceThrottlingWsDecrementFactor(1.5) + .setPersistenceThrottlingWsBackoff(0.8))); + assertEquals(1.5, config.async_operation_throttler().window_size_decrement_factor(), 0.0001); + assertEquals(0.8, config.async_operation_throttler().window_size_backoff(), 0.0001); } @Test diff --git a/configserver/src/main/java/com/yahoo/vespa/config/server/deploy/ModelContextImpl.java b/configserver/src/main/java/com/yahoo/vespa/config/server/deploy/ModelContextImpl.java index 89d3318d710..bc0f66d933c 100644 --- a/configserver/src/main/java/com/yahoo/vespa/config/server/deploy/ModelContextImpl.java +++ b/configserver/src/main/java/com/yahoo/vespa/config/server/deploy/ModelContextImpl.java @@ -202,6 +202,8 @@ public class ModelContextImpl implements ModelContext { private final boolean enableServerOcspStapling; private final String persistenceAsyncThrottling; private final String mergeThrottlingPolicy; + private final double persistenceThrottlingWsDecrementFactor; + private final double persistenceThrottlingWsBackoff; private final boolean useQrserverServiceName; public FeatureFlags(FlagSource source, ApplicationId appId) { @@ -243,6 +245,8 @@ public class ModelContextImpl implements ModelContext { this.enableServerOcspStapling = flagValue(source, appId, Flags.ENABLE_SERVER_OCSP_STAPLING); this.persistenceAsyncThrottling = flagValue(source, appId, Flags.PERSISTENCE_ASYNC_THROTTLING); this.mergeThrottlingPolicy = flagValue(source, appId, Flags.MERGE_THROTTLING_POLICY); + this.persistenceThrottlingWsDecrementFactor = flagValue(source, appId, Flags.PERSISTENCE_THROTTLING_WS_DECREMENT_FACTOR); + this.persistenceThrottlingWsBackoff = flagValue(source, appId, Flags.PERSISTENCE_THROTTLING_WS_BACKOFF); this.useQrserverServiceName = flagValue(source, appId, Flags.USE_QRSERVER_SERVICE_NAME); } @@ -286,6 +290,8 @@ public class ModelContextImpl implements ModelContext { @Override public boolean enableServerOcspStapling() { return enableServerOcspStapling; } @Override public String persistenceAsyncThrottling() { return persistenceAsyncThrottling; } @Override public String mergeThrottlingPolicy() { return mergeThrottlingPolicy; } + @Override public double persistenceThrottlingWsDecrementFactor() { return persistenceThrottlingWsDecrementFactor; } + @Override public double persistenceThrottlingWsBackoff() { return persistenceThrottlingWsBackoff; } @Override public boolean useQrserverServiceName() { return useQrserverServiceName; } private static <V> V flagValue(FlagSource source, ApplicationId appId, UnboundFlag<? extends V, ?, ?> flag) { diff --git a/flags/src/main/java/com/yahoo/vespa/flags/Flags.java b/flags/src/main/java/com/yahoo/vespa/flags/Flags.java index 470bf9a0c1c..e2c7d376a0d 100644 --- a/flags/src/main/java/com/yahoo/vespa/flags/Flags.java +++ b/flags/src/main/java/com/yahoo/vespa/flags/Flags.java @@ -365,6 +365,22 @@ public class Flags { "Takes effect at redeployment", ZONE_ID, APPLICATION_ID); + public static final UnboundDoubleFlag PERSISTENCE_THROTTLING_WS_DECREMENT_FACTOR = defineDoubleFlag( + "persistence-throttling-ws-decrement-factor", 1.2, + List.of("vekterli"), "2022-01-27", "2022-05-01", + "Sets the dynamic throttle policy window size decrement factor for persistence " + + "async throttling. Only applies if DYNAMIC policy is used.", + "Takes effect on redeployment", + ZONE_ID, APPLICATION_ID); + + public static final UnboundDoubleFlag PERSISTENCE_THROTTLING_WS_BACKOFF = defineDoubleFlag( + "persistence-throttling-ws-backoff", 0.95, + List.of("vekterli"), "2022-01-27", "2022-05-01", + "Sets the dynamic throttle policy window size backoff for persistence " + + "async throttling. Only applies if DYNAMIC policy is used. Valid range [0, 1]", + "Takes effect on redeployment", + ZONE_ID, APPLICATION_ID); + public static final UnboundBooleanFlag CHECK_CONFIG_CONVERGENCE_BEFORE_RESTARTING = defineFeatureFlag( "check-config-convergence-before-restart", false, List.of("hmusum"), "2022-01-16", "2022-02-16", |