Skip to content

Commit 80fe966

Browse files
committed
Add a timeout for the backend stats collection query.
Default the stats collection query to use EXECUTE IMMEDIATE by default, with the option to use explicit PREPARE if desired
1 parent c88c50f commit 80fe966

File tree

3 files changed

+41
-1
lines changed

3 files changed

+41
-1
lines changed

gateway-ha/src/main/java/io/trino/gateway/ha/clustermonitor/ClusterStatsJdbcMonitor.java

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@
1515

1616
import com.google.common.util.concurrent.SimpleTimeLimiter;
1717
import io.airlift.log.Logger;
18+
import io.airlift.units.Duration;
1819
import io.trino.gateway.ha.config.BackendStateConfiguration;
1920
import io.trino.gateway.ha.config.MonitorConfiguration;
2021
import io.trino.gateway.ha.config.ProxyBackendConfiguration;
@@ -39,6 +40,7 @@ public class ClusterStatsJdbcMonitor
3940
private static final Logger log = Logger.get(ClusterStatsJdbcMonitor.class);
4041

4142
private final Properties properties; // TODO Avoid using a mutable field
43+
private final Duration queryTimeout;
4244

4345
private static final String STATE_QUERY = "SELECT state, COUNT(*) as count "
4446
+ "FROM runtime.queries "
@@ -51,6 +53,12 @@ public ClusterStatsJdbcMonitor(BackendStateConfiguration backendStateConfigurati
5153
properties.setProperty("user", backendStateConfiguration.getUsername());
5254
properties.setProperty("password", backendStateConfiguration.getPassword());
5355
properties.setProperty("SSL", String.valueOf(backendStateConfiguration.getSsl()));
56+
// explicitPrepare is a valid property for Trino versions >= 431. To avoid compatibility
57+
// issues with versions < 431, this property is left unset when explicitPrepare=true, which is the default
58+
if (!monitorConfiguration.isExplicitPrepare()) {
59+
properties.setProperty("explicitPrepare", "false");
60+
}
61+
queryTimeout = monitorConfiguration.getQueryTimeout();
5462
log.info("state check configured");
5563
}
5664

@@ -78,6 +86,7 @@ public ClusterStats monitor(ProxyBackendConfiguration backend)
7886
PreparedStatement statement = SimpleTimeLimiter.create(Executors.newSingleThreadExecutor()).callWithTimeout(
7987
() -> conn.prepareStatement(STATE_QUERY), 10, SECONDS)) {
8088
statement.setString(1, (String) properties.get("user"));
89+
statement.setQueryTimeout((int) queryTimeout.roundTo(SECONDS));
8190
Map<String, Integer> partialState = new HashMap<>();
8291
ResultSet rs = statement.executeQuery();
8392
while (rs.next()) {

gateway-ha/src/main/java/io/trino/gateway/ha/config/MonitorConfiguration.java

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,14 +13,21 @@
1313
*/
1414
package io.trino.gateway.ha.config;
1515

16+
import io.airlift.units.Duration;
1617
import io.trino.gateway.ha.clustermonitor.ActiveClusterMonitor;
1718

19+
import static java.util.concurrent.TimeUnit.SECONDS;
20+
1821
public class MonitorConfiguration
1922
{
2023
private int taskDelaySeconds = ActiveClusterMonitor.MONITOR_TASK_DELAY_SECONDS;
2124

2225
private int retries;
2326

27+
private Duration queryTimeout = new Duration(10, SECONDS);
28+
29+
private boolean explicitPrepare;
30+
2431
public MonitorConfiguration() {}
2532

2633
public int getTaskDelaySeconds()
@@ -42,4 +49,24 @@ public void setRetries(int retries)
4249
{
4350
this.retries = retries;
4451
}
52+
53+
public Duration getQueryTimeout()
54+
{
55+
return queryTimeout;
56+
}
57+
58+
public void setQueryTimeout(Duration queryTimeout)
59+
{
60+
this.queryTimeout = queryTimeout;
61+
}
62+
63+
public boolean isExplicitPrepare()
64+
{
65+
return explicitPrepare;
66+
}
67+
68+
public void setExplicitPrepare(boolean explicitPrepare)
69+
{
70+
this.explicitPrepare = explicitPrepare;
71+
}
4572
}

gateway-ha/src/test/java/io/trino/gateway/ha/clustermonitor/TestClusterStatsMonitor.java

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@
1515

1616
import io.airlift.http.client.HttpClientConfig;
1717
import io.airlift.http.client.jetty.JettyHttpClient;
18+
import io.airlift.units.Duration;
1819
import io.trino.gateway.ha.config.BackendStateConfiguration;
1920
import io.trino.gateway.ha.config.MonitorConfiguration;
2021
import io.trino.gateway.ha.config.ProxyBackendConfiguration;
@@ -26,6 +27,7 @@
2627

2728
import java.util.function.Function;
2829

30+
import static java.util.concurrent.TimeUnit.SECONDS;
2931
import static org.assertj.core.api.Assertions.assertThat;
3032
import static org.junit.jupiter.api.TestInstance.Lifecycle.PER_CLASS;
3133
import static org.testcontainers.utility.MountableFile.forClasspathResource;
@@ -58,7 +60,9 @@ void testHttpMonitor()
5860
@Test
5961
void testJdbcMonitor()
6062
{
61-
testClusterStatsMonitor(backendStateConfiguration -> new ClusterStatsJdbcMonitor(backendStateConfiguration, new MonitorConfiguration()));
63+
MonitorConfiguration monitorConfigurationWithTimeout = new MonitorConfiguration();
64+
monitorConfigurationWithTimeout.setQueryTimeout(new Duration(30, SECONDS));
65+
testClusterStatsMonitor(backendStateConfiguration -> new ClusterStatsJdbcMonitor(backendStateConfiguration, monitorConfigurationWithTimeout));
6266
}
6367

6468
@Test

0 commit comments

Comments
 (0)