Skip to content

Commit e2cca4d

Browse files
fix(bigquery): support optional fields in BigLakeConfiguration to prevent NPE on Iceberg/Lakehouse tables (#13733)
b/534291682 This PR resolves a `NullPointerException` encountered when querying or retrieving metadata for 4-part PCNT (Project.Catalog.Namespace.Table) Apache Iceberg tables governed by external REST catalogs. #### Changes * Annotated all 4 fields (`connectionId`, `fileFormat`, `storageUri`, `tableFormat`) and their corresponding setters in `@AutoValue.Builder` with `@Nullable` in `BigLakeConfiguration.java`. * Cleaned up the Javadoc comments for the builder setters in `BigLakeConfiguration.java` to remove incorrect `[Required]` notations and updated `getTableFormat()` Javadoc to reflect the correct table format reference (e.g., Iceberg) instead of file format. * Added unit test coverage to `BigLakeConfigurationTest.java` (`testNullFields`, `testFromPbWithNullFields`) to verify that constructing the configuration or mapping it from API models works successfully when properties are null.
1 parent 94f7404 commit e2cca4d

2 files changed

Lines changed: 39 additions & 13 deletions

File tree

java-bigquery/google-cloud-bigquery/src/main/java/com/google/cloud/bigquery/BigLakeConfiguration.java

Lines changed: 18 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@
1818

1919
import com.google.auto.value.AutoValue;
2020
import java.io.Serializable;
21+
import org.jspecify.annotations.Nullable;
2122

2223
@AutoValue
2324
public abstract class BigLakeConfiguration implements Serializable {
@@ -30,13 +31,15 @@ public abstract class BigLakeConfiguration implements Serializable {
3031
*
3132
* @return value or {@code null} for none
3233
*/
34+
@Nullable
3335
public abstract String getConnectionId();
3436

3537
/**
3638
* Open source file format that the table data is stored in. Currently only PARQUET is supported.
3739
*
3840
* @return value or {@code null} for none
3941
*/
42+
@Nullable
4043
public abstract String getFileFormat();
4144

4245
/**
@@ -45,13 +48,15 @@ public abstract class BigLakeConfiguration implements Serializable {
4548
*
4649
* @return value or {@code null} for none
4750
*/
51+
@Nullable
4852
public abstract String getStorageUri();
4953

5054
/**
51-
* Open source file format that the table data is stored in. Currently only PARQUET is supported.
55+
* Open source table format that the table data is stored in. Currently only ICEBERG is supported.
5256
*
5357
* @return value or {@code null} for none
5458
*/
59+
@Nullable
5560
public abstract String getTableFormat();
5661

5762
public static Builder newBuilder() {
@@ -63,36 +68,36 @@ public static Builder newBuilder() {
6368
@AutoValue.Builder
6469
public abstract static class Builder {
6570
/**
66-
* [Required] Required and immutable. Credential reference for accessing external storage
67-
* system. Normalized as project_id.location_id.connection_id.
71+
* Credential reference for accessing external storage system. Normalized as
72+
* project_id.location_id.connection_id.
6873
*
6974
* @param connectionId connectionId or {@code null} for none
7075
*/
71-
public abstract Builder setConnectionId(String connectionId);
76+
public abstract Builder setConnectionId(@Nullable String connectionId);
7277

7378
/**
74-
* [Required] Required and immutable. Open source file format that the table data is stored in.
75-
* Currently only PARQUET is supported.
79+
* Open source file format that the table data is stored in. Currently only PARQUET is
80+
* supported.
7681
*
7782
* @param fileFormat fileFormat or {@code null} for none
7883
*/
79-
public abstract Builder setFileFormat(String fileFormat);
84+
public abstract Builder setFileFormat(@Nullable String fileFormat);
8085

8186
/**
82-
* [Required] Required and immutable. Fully qualified location prefix of the external folder
83-
* where data is stored. Starts with "gs://" and ends with "/". Does not contain "*".
87+
* Fully qualified location prefix of the external folder where data is stored. Starts with
88+
* "gs://" and ends with "/". Does not contain "*".
8489
*
8590
* @param storageUri storageUri or {@code null} for none
8691
*/
87-
public abstract Builder setStorageUri(String storageUri);
92+
public abstract Builder setStorageUri(@Nullable String storageUri);
8893

8994
/**
90-
* [Required] Required and immutable. Open source file format that the table data is stored in.
91-
* Currently only PARQUET is supported.
95+
* Open source table format that the table data is stored in. Currently only ICEBERG is
96+
* supported.
9297
*
9398
* @param tableFormat tableFormat or {@code null} for none
9499
*/
95-
public abstract Builder setTableFormat(String tableFormat);
100+
public abstract Builder setTableFormat(@Nullable String tableFormat);
96101

97102
public abstract BigLakeConfiguration build();
98103
}

java-bigquery/google-cloud-bigquery/src/test/java/com/google/cloud/bigquery/BigLakeConfigurationTest.java

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@
1717
package com.google.cloud.bigquery;
1818

1919
import static org.junit.jupiter.api.Assertions.assertEquals;
20+
import static org.junit.jupiter.api.Assertions.assertNull;
2021

2122
import org.junit.jupiter.api.Test;
2223

@@ -61,6 +62,26 @@ void testFromPb() {
6162
BIG_LAKE_CONFIGURATION, BigLakeConfiguration.fromPb(BIG_LAKE_CONFIGURATION_PB));
6263
}
6364

65+
@Test
66+
void testNullFields() {
67+
BigLakeConfiguration configuration = BigLakeConfiguration.newBuilder().build();
68+
assertNull(configuration.getConnectionId());
69+
assertNull(configuration.getFileFormat());
70+
assertNull(configuration.getStorageUri());
71+
assertNull(configuration.getTableFormat());
72+
}
73+
74+
@Test
75+
void testFromPbWithNullFields() {
76+
com.google.api.services.bigquery.model.BigLakeConfiguration pb =
77+
new com.google.api.services.bigquery.model.BigLakeConfiguration();
78+
BigLakeConfiguration configuration = BigLakeConfiguration.fromPb(pb);
79+
assertNull(configuration.getConnectionId());
80+
assertNull(configuration.getFileFormat());
81+
assertNull(configuration.getStorageUri());
82+
assertNull(configuration.getTableFormat());
83+
}
84+
6485
private static void assertBigLakeConfiguration(
6586
BigLakeConfiguration expected, BigLakeConfiguration actual) {
6687
assertEquals(expected.getConnectionId(), actual.getConnectionId());

0 commit comments

Comments
 (0)