-
Notifications
You must be signed in to change notification settings - Fork 129
Description
Testing executeSelect on Java 21 on MacOS Sonoma 14.7.6, I found a concerning issue. If your process or thread attempts to end after creating a connection and calling executeSelect() without iterating over the entire ResultSet until next() returns false, it will hang forever.
Steps to reproduce
- Go through the usual steps of instantiating a BigQuery client, creating ConnectionSettings, calling
createConnectionon said client, and then callexecuteSelect()to get your BigQueryResult. - Either let the process end, or don't iterate over the entire ResultSet contained in the BigQueryResult. It will hang.
Code example
import com.google.cloud.bigquery.BigQuery;
import com.google.cloud.bigquery.BigQueryResult;
import com.google.cloud.bigquery.BigQueryOptions;
import com.google.cloud.bigquery.BigQueryException;
import com.google.cloud.bigquery.Connection;
import com.google.cloud.bigquery.ConnectionSettings;
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.util.stream.Collectors;
import java.sql.ResultSet;
import java.sql.SQLException;
public class BQExecuteSelectTest {
public static void main(String[] args) {
try {
if(args.length != 2)
throw new IllegalArgumentException("Usage: BQExecuteSelectTest <project_id> <location>\n - Accepts SQL on STDIN");
BigQuery bq = BigQueryOptions.newBuilder()
.setProjectId(args[0])
.setLocation(args[1]).build().getService();
ConnectionSettings settings = ConnectionSettings.newBuilder()
.setCreateSession(true)
.setMaxResultPerPage(100)
.setMaxResults(100L).build();
Connection conn = bq.createConnection(settings);
BufferedReader reader = new BufferedReader(new InputStreamReader(System.in));
BigQueryResult res = conn.executeSelect(reader.lines().collect(Collectors.joining("\n")));
// Do nothing, or just don't finish iterating over res.getResultSet()
} catch(IllegalArgumentException e) {
System.out.println(e.getMessage());
} catch(Exception e) {
System.out.println("Something went wrong: " + e.getMessage());
}
}
}Output
user@host bq_test % java -cp deps.jar:. BQExecuteSelectTest my-project us-east4 < test.sql
Jul 10, 2025 12:37:30 PM com.google.cloud.bigquery.ConnectionImpl getExecuteSelectResponse
INFO:
Using Fast Query Path
^C% <-- Hit Ctrl-C here after waiting for several minutes.
user@host bq_test %
External references such as API reference guides
Any additional information below
When running a single command like this, you can simply Ctrl-C to end the process. But in a server environment where this could be running in different threads, it's very problematic. If a system (like mine) can allow interruption of ResultSet iteration (which can be necessary for very large result sets in specific scenarios), it can cause client threads to hang forever and never return, or background workers to wait forever and never become available to process other jobs.