Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
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
16 changes: 16 additions & 0 deletions conf/cassandra.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -1083,6 +1083,22 @@ native_transport_allow_older_protocols: true
# native_transport_rate_limiting_enabled: false
# native_transport_max_requests_per_second: 1000000

# When enabled, nodes will signal connected clients before shutting down,
# allowing in-flight requests to complete without client-visible timeouts.
# This applies to intentional shutdowns (nodetool drain, rolling restarts,
# controlled JVM shutdown). Clients must subscribe to the GRACEFUL_DISCONNECT
# event via REGISTER to benefit from this behavior.
#
# Requires driver support for the GRACEFUL_DISCONNECT event type.
# See: https://cwiki.apache.org/confluence/pages/viewpage.action?pageId=406619103

# Enable or disable graceful disconnect. When false, shutdown behavior is
# unchanged from previous versions.
# graceful_disconnect_enabled: true

# Time given to clients to stop sending new requests after the GRACEFUL_DISCONNECT event is emitted.
# graceful_disconnect_grace_period: 5000

# The address or interface to bind the native transport server to.
#
# Set rpc_address OR rpc_interface, not both.
Expand Down
16 changes: 16 additions & 0 deletions conf/cassandra_latest.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -1072,6 +1072,22 @@ native_transport_allow_older_protocols: true
# native_transport_rate_limiting_enabled: false
# native_transport_max_requests_per_second: 1000000

# When enabled, nodes will signal connected clients before shutting down,
# allowing in-flight requests to complete without client-visible timeouts.
# This applies to intentional shutdowns (nodetool drain, rolling restarts,
# controlled JVM shutdown). Clients must subscribe to the GRACEFUL_DISCONNECT
# event via REGISTER to benefit from this behavior.
#
# Requires driver support for the GRACEFUL_DISCONNECT event type.
# See: https://cwiki.apache.org/confluence/pages/viewpage.action?pageId=406619103

# Enable or disable graceful disconnect. When false, shutdown behavior is
# unchanged from previous versions.
graceful_disconnect_enabled: true

# Time given to clients to stop sending new requests after the GRACEFUL_DISCONNECT event is emitted.
graceful_disconnect_grace_period: 5000

# The address or interface to bind the native transport server to.
#
# Set rpc_address OR rpc_interface, not both.
Expand Down
4 changes: 4 additions & 0 deletions src/java/org/apache/cassandra/config/Config.java
Original file line number Diff line number Diff line change
Expand Up @@ -167,6 +167,10 @@ public static Set<String> splitCommaDelimited(String src)

public volatile DurationSpec.LongMillisecondsBound accord_preaccept_timeout = new DurationSpec.LongMillisecondsBound("1s");

public boolean graceful_disconnect_enabled = true;

public volatile DurationSpec.LongMillisecondsBound graceful_disconnect_grace_period = new DurationSpec.LongMillisecondsBound("5s");

@Replaces(oldName = "truncate_request_timeout_in_ms", converter = Converters.MILLIS_DURATION_LONG, deprecated = true)
public volatile DurationSpec.LongMillisecondsBound truncate_request_timeout = new DurationSpec.LongMillisecondsBound("60000ms");

Expand Down
15 changes: 15 additions & 0 deletions src/java/org/apache/cassandra/config/DatabaseDescriptor.java
Original file line number Diff line number Diff line change
Expand Up @@ -2598,6 +2598,21 @@ public static void setRpcTimeout(long timeOutInMillis)
conf.request_timeout = new DurationSpec.LongMillisecondsBound(timeOutInMillis);
}

public static long getGracefulDisconnectGracePeriod()
{
return conf.graceful_disconnect_grace_period.toMilliseconds();
}

public static void setGracefulDisconnectGracePeriod(long gracefulDisconnectGracePeriod)
{
conf.graceful_disconnect_grace_period = new DurationSpec.LongMillisecondsBound(gracefulDisconnectGracePeriod);
}

public static boolean getGracefulDisconnectEnabled()
{
return conf.graceful_disconnect_enabled;
}

public static long getReadRpcTimeout(TimeUnit unit)
{
return conf.read_request_timeout.to(unit);
Expand Down
21 changes: 21 additions & 0 deletions src/java/org/apache/cassandra/service/StorageService.java
Original file line number Diff line number Diff line change
Expand Up @@ -1197,6 +1197,27 @@ public long getRpcTimeout()
return DatabaseDescriptor.getRpcTimeout(MILLISECONDS);
}


@Override
public boolean getGracefulDisconnectEnabled()
{
return DatabaseDescriptor.getGracefulDisconnectEnabled();
}

@Override
public void setGracefulDisconnectGracePeriod(long value)
{
if (value <= 0 && DatabaseDescriptor.getGracefulDisconnectEnabled())
throw new IllegalArgumentException("Graceful disconnect grace period must be positive when graceful disconnect is enabled. Got " + value);
DatabaseDescriptor.setGracefulDisconnectGracePeriod(value);
}

@Override
public long getGracefulDisconnectGracePeriod()
{
return DatabaseDescriptor.getGracefulDisconnectGracePeriod();
}

public void setReadRpcTimeout(long value)
{
DatabaseDescriptor.setReadRpcTimeout(value);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -773,6 +773,11 @@ default int upgradeSSTables(String keyspaceName, boolean excludeCurrentVersion,
public void setRpcTimeout(long value);
public long getRpcTimeout();

public void setGracefulDisconnectGracePeriod(long value);
public long getGracefulDisconnectGracePeriod();

public boolean getGracefulDisconnectEnabled();

public void setReadRpcTimeout(long value);
public long getReadRpcTimeout();

Expand Down
18 changes: 18 additions & 0 deletions test/unit/org/apache/cassandra/config/DatabaseDescriptorTest.java
Original file line number Diff line number Diff line change
Expand Up @@ -791,6 +791,24 @@ public void testRowIndexSizeWarnEnabledAbortDisabled()
DatabaseDescriptor.applyThresholdsValidations(conf);
}

@Test
public void testGracefulDisconnectEnabled()
{
Config config = new Config();
boolean originalValue = config.graceful_disconnect_enabled;
Assert.assertTrue("Default value of graceful_disconnect_enabled must be true", originalValue);
}

@Test
public void testGracefulDisconnectGracePeriod()
{
long originalValue = DatabaseDescriptor.getGracefulDisconnectGracePeriod();
Assert.assertEquals("Default value of graceful_disconnect_grace_period must be 5000", 5000, originalValue);
DatabaseDescriptor.setGracefulDisconnectGracePeriod(3000);
Assert.assertEquals("graceful_disconnect_grace_period should be updated to 3000", 3000, DatabaseDescriptor.getGracefulDisconnectGracePeriod());
DatabaseDescriptor.setGracefulDisconnectGracePeriod(originalValue);
}

@Test
public void testRowIndexSizeAbortEnabledWarnDisabled()
{
Expand Down
32 changes: 32 additions & 0 deletions test/unit/org/apache/cassandra/service/StorageServiceTest.java
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@
import org.junit.Before;
import org.junit.BeforeClass;
import org.junit.Test;
import org.junit.jupiter.api.Assertions;

import org.apache.cassandra.ServerTestUtils;
import org.apache.cassandra.concurrent.ScheduledExecutors;
Expand Down Expand Up @@ -201,6 +202,37 @@ public void testColumnIndexSizeInKiB()
}
}

@Test
public void testGracefulDisconnectGracePeriod()
{
StorageService storageService = StorageService.instance;
long originalGracePeriod = storageService.getGracefulDisconnectGracePeriod();
try
{
storageService.setGracefulDisconnectGracePeriod(3000);
Assertions.assertEquals(3000, storageService.getGracefulDisconnectGracePeriod());

try
{
Assertions.assertThrows(IllegalArgumentException.class, () -> storageService.setGracefulDisconnectGracePeriod(-1));
}
catch (IllegalArgumentException ignored) {}

Assertions.assertEquals(3000, storageService.getGracefulDisconnectGracePeriod());
}
finally
{
storageService.setGracefulDisconnectGracePeriod(originalGracePeriod);
}
}

@Test
public void testGracefulDisconnectEnabled()
{
Assertions.assertFalse(StorageService.instance.getGracefulDisconnectEnabled(),
"Default value of graceful_disconnect_enabled must be false");
}

@Test
public void testColumnIndexCacheSizeInKiB()
{
Expand Down