BigQuery: create() throws NullPointerException on a duplicate job id outside the US multi-region (java-bigquery#3034 not fixed by #3035)
Nobody has claimed this yet.
Assessment
- Difficulty
- 2/5
- Estimated time
- 1-3 hours
- Newbie friendliness
- 78/100
Research direction
Start in java-bigquery/google-cloud-bigquery/src/main/java/com/google/cloud/bigquery/BigQueryImpl.java around lines 609–611, then compare the fixed-id branch with the nearby idRandom null handling. Review testCreateJobTryGetNotRandom and add coverage for a null re-fetch; done means a regional duplicate produces the original Already Exists error instead of a NullPointerException.
Written by the indexing model from the issue text.
Description
Environment details
- API: BigQuery (
java-bigquery) - OS type and version: macOS 15 / Linux (not OS-specific)
- Java version: 17
- Version: google-cloud-bigquery 2.68.0, and present on current
main
(java-bigquery/google-cloud-bigquery/src/main/java/com/google/cloud/bigquery/BigQueryImpl.java
lines 609–611)
Summary
BigQuery.create(JobInfo) with an explicit job id throws
NullPointerException: Cannot invoke "com.google.cloud.bigquery.Job.getStatistics()" because "job" is null
when the id already exists and the job lives outside the US multi-region while the JobId carries
no location — masking the real Already Exists: Job project:location.id error.
This is the failure googleapis/java-bigquery#3034 reported. That issue was closed by
googleapis/java-bigquery#3035, which does not cover this path:
- #3035's production change narrows the re-fetch from
getJob(jobId)to
getJob(jobId, JobOption.fields(JobField.STATISTICS)). Narrowing the requested fields cannot
turn a null return into a job, and #3034's stack trace shows the receiverjobitself was null. - #3035's added test (
testCreateJobTryGetNotRandom) mocks the RPCgetJobreturning a job,
so only the found-job path is covered; the null return has no test.
The NPE therefore still reproduces, deterministically, on 2.68.0 — which contains #3035's change.
Root cause
jobs.get resolves a JobId that names no location against the US multi-region only. When the
duplicated job's location was inferred from the statement (a query or load touching a regional
dataset), the duplicate-id handler's re-fetch misses it, getJob returns null, and
job.getStatistics() throws. The idRandom branch a few lines below already handles exactly this
case with if (job == null) { throw createException; }; the fixed-id branch lacks the same guard.
Steps to reproduce
Run the code below against any project with a dataset outside the US multi-region (reproduced
against a us-central1 dataset). No location is set anywhere; the region comes from the query.
BigQuery bq = BigQueryOptions.newBuilder().setProjectId(project).build().getService();
String sql = "SELECT COUNT(*) FROM `" + project + "." + regionalDataset + ".INFORMATION_SCHEMA.TABLES`";
String id = "npe_repro_" + System.currentTimeMillis();
bq.create(JobInfo.of(JobId.newBuilder().setProject(project).setJob(id).build(),
QueryJobConfiguration.of(sql))); // ok — server infers us-central1
bq.create(JobInfo.of(JobId.newBuilder().setProject(project).setJob(id).build(),
QueryJobConfiguration.of(sql))); // NullPointerException
Control arm: setting the location on the second create's JobId makes the handler find the job
and return it — the intended duplicate-id behaviour — which isolates the defect to the
location-less re-fetch.
Stack trace
java.lang.NullPointerException: Cannot invoke "com.google.cloud.bigquery.Job.getStatistics()" because "job" is null
at com.google.cloud.bigquery.BigQueryImpl.create(BigQueryImpl.java:611)
at com.google.cloud.bigquery.BigQueryImpl.create(BigQueryImpl.java:511)
Expected behaviour and fix
When the re-fetch returns null, fall through to the original exception, as the idRandom branch
does. Verified against BigQuery with the guard patched in: the NPE becomes
BigQueryException: Already Exists: Job flink-gcp:us-central1.npe_repro_a_…, whose message names
the job's actual location. I can send the PR.
- Dominant language
- Java
- Stars
- 2.1k
- Forks
- 1.2k
- Avg merge
- 1d 21h
- Merged PRs (30d)
- 131
Contributor guide
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
More from googleapis/google-cloud-java
-
Difficulty 2/5 1-3 hours Newbie friendliness 65/100
googleapis/google-cloud-java#14132 · 1 comment ·
-
priority: p2 type: bug
Difficulty 2/5 1-3 hours Newbie friendliness 78/100
googleapis/google-cloud-java#13255 · 2 comments ·
-
priority: p3
Difficulty 2/5 1-3 hours Newbie friendliness 72/100
googleapis/google-cloud-java#13032 ·
-
priority: p3 type: feature request
Difficulty 2/5 1-3 hours Newbie friendliness 65/100
googleapis/google-cloud-java#12071 ·
-
api: bigquery priority: p3 type: feature request
Difficulty 2/5 1-3 hours Newbie friendliness 75/100
googleapis/google-cloud-java#12136 ·
All issues in googleapis/google-cloud-java
Similar issues
-
Difficulty 2/5 1-3 hours Newbie friendliness 65/100
-
Difficulty 1/5 Under an hour Newbie friendliness 88/100
checkstyle/test-configs#263 ·
-
bug
Difficulty 1/5 Under an hour Newbie friendliness 90/100
apache/cloudstack#14222 ·
-
[BUG]茶杯方块在取茶时会引发崩溃 Open
Difficulty 2/5 1-3 hours Newbie friendliness 88/100
-
1.0.0-alpha2 Type/Improvement
Difficulty 2/5 1-3 hours Newbie friendliness 68/100
wso2/dpdp-accelerator#272 ·