Skip to content

Make gcs.json-key-file-path optional for Iceberg REST catalog#29101

Open
laserninja wants to merge 1 commit intotrinodb:masterfrom
laserninja:fix/29084-google-security-optional-json-key
Open

Make gcs.json-key-file-path optional for Iceberg REST catalog#29101
laserninja wants to merge 1 commit intotrinodb:masterfrom
laserninja:fix/29084-google-security-optional-json-key

Conversation

@laserninja
Copy link
Copy Markdown
Contributor

@laserninja laserninja commented Apr 14, 2026

Description

When using iceberg.rest-catalog.security=GOOGLE, the gcs.json-key-file-path property was validated as mandatory by GoogleSecurityConfig, causing the server to fail at startup when the property was omitted. This prevented use of GKE Workload Identity or environment-based Application Default Credentials (ADC), forcing users to provision and mount physical Service Account JSON key files — contrary to GCP security best practices.

The underlying Iceberg library (GoogleAuthManager) already handles a null/absent credentials path by falling through to GoogleCredentials.getApplicationDefault(). The fix:

  • Replaces @NotNull with @Nullable on getJsonKeyFilePath() in GoogleSecurityConfig (retaining @FileExists so the path is still validated when provided — consistent with the @Nullable @FileExists pattern used in GcsServiceAccountAuthConfig)
  • Conditionally adds GCP_CREDENTIALS_PATH_PROPERTY to the REST catalog auth properties map only when a key file path is provided
  • Adds TestGoogleAuthProperties covering both the ADC path and the explicit key file path

Additional context and related issues

Release notes

( ) This is not user-visible or is docs only, and no release notes are required.
( ) Release notes are required. Please propose a release note for me.
(x) Release notes are required, with the following suggested text:

## Iceberg
* Add support for Workload Identity or Application Default Credentials in BigLake metastore. ({issue}`29084`)

When using iceberg.rest-catalog.security=GOOGLE, the
gcs.json-key-file-path property was validated as mandatory, preventing
use of GKE Workload Identity or Application Default Credentials (ADC).

The underlying GoogleAuthManager already supports ADC: when the
credentials path is null/absent, it calls
GoogleCredentials.getApplicationDefault(). Replace @NotNull with
@nullable on getJsonKeyFilePath() and conditionally add the credentials
property to the REST catalog auth map only when a path is provided.

Fixes trinodb#29084
@cla-bot cla-bot Bot added the cla-signed label Apr 14, 2026
@github-actions github-actions Bot added the iceberg Iceberg connector label Apr 14, 2026
@laserninja laserninja requested a review from ebyhr April 14, 2026 06:33
}

@NotNull
@Nullable
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Revert and return Optional type instead.

.buildOrThrow();
.put("header.x-goog-user-project", config.getProjectId());
if (config.getJsonKeyFilePath() != null) {
builder.put(GCP_CREDENTIALS_PATH_PROPERTY, config.getJsonKeyFilePath());
Copy link
Copy Markdown
Member

@ebyhr ebyhr Apr 14, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please update metastores.md to mention that gcs.json-key-file-path is optional.

{
GoogleSecurityConfig config = new GoogleSecurityConfig()
.setProjectId("my-project");
// jsonKeyFilePath intentionally omitted to use Workload Identity / ADC
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Move this comment above GoogleSecurityConfig config ...


assertThat(properties).containsEntry(AUTH_TYPE, AUTH_TYPE_GOOGLE);
assertThat(properties).containsEntry("header.x-goog-user-project", "my-project");
assertThat(properties).doesNotContainKey(GCP_CREDENTIALS_PATH_PROPERTY);
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No need to repeat assertThat:

Suggested change
assertThat(properties).doesNotContainKey(GCP_CREDENTIALS_PATH_PROPERTY);
assertThat(new GoogleAuthProperties(config).get())
.containsEntry(AUTH_TYPE, AUTH_TYPE_GOOGLE)
.containsEntry("header.x-goog-user-project", "my-project")
.doesNotContainKey(GCP_CREDENTIALS_PATH_PROPERTY);

Same for testServiceAccountJsonKeyFile.

assertThat(properties).containsEntry("header.x-goog-user-project", "my-project");
assertThat(properties).containsEntry(GCP_CREDENTIALS_PATH_PROPERTY, keyFile.toString());
}
}
Copy link
Copy Markdown
Member

@ebyhr ebyhr Apr 14, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This test class doesn't currently provide much value. You can remove and update TestIcebergPlugin instead.

@github-actions
Copy link
Copy Markdown

github-actions Bot commented May 5, 2026

This pull request has gone a while without any activity. Ask for help on #core-dev on Trino slack.

@github-actions github-actions Bot added the stale label May 5, 2026
@laserninja laserninja removed the stale label May 6, 2026
@laserninja
Copy link
Copy Markdown
Contributor Author

Waiting for #29098

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

cla-signed iceberg Iceberg connector

Development

Successfully merging this pull request may close these issues.

Iceberg REST Catalog requires gcs.json-key-file-path even when using Workload Identity

2 participants