Class IcebergCatalogHandler
- All Implemented Interfaces:
AutoCloseable
We must make authorization decisions based on entity resolution at this layer instead of the underlying PolarisIcebergCatalog layer, because this REST-adjacent layer captures intent of different REST calls that share underlying catalog calls (e.g. updateTable will call loadTable under the hood), and some features of the REST API aren't expressed at all in the underlying Catalog interfaces (e.g. credential-vending in createTable/loadTable).
We also want this layer to be independent of API-endpoint-specific idioms, such as dealing with jakarta.ws.rs.core.Response objects, and other implementations that expose different HTTP stubs or even tunnel the protocol over something like gRPC can still normalize on the Iceberg model objects used in this layer to still benefit from the shared implementation of authorization-aware catalog protocols.
-
Field Summary
Fields inherited from class org.apache.polaris.service.catalog.common.CatalogHandler
resolutionManifest -
Constructor Summary
Constructors -
Method Summary
Modifier and TypeMethodDescriptionprotected abstract AccessDelegationModeResolvervoidauthorizeCreateTableDirect(org.apache.iceberg.catalog.Namespace namespace, org.apache.iceberg.rest.requests.CreateTableRequest request, boolean delegationRequested) protected abstract CatalogHandlerUtilsprotected abstract Clockclock()voidclose()voidcommitTransaction(org.apache.iceberg.rest.requests.CommitTransactionRequest commitTransactionRequest) org.apache.iceberg.rest.responses.CreateNamespaceResponsecreateNamespace(org.apache.iceberg.rest.requests.CreateNamespaceRequest request) org.apache.iceberg.rest.responses.LoadTableResponsecreateTableDirect(org.apache.iceberg.catalog.Namespace namespace, org.apache.iceberg.rest.requests.CreateTableRequest request) Create a table.org.apache.iceberg.rest.responses.LoadTableResponsecreateTableDirect(org.apache.iceberg.catalog.Namespace namespace, org.apache.iceberg.rest.requests.CreateTableRequest request, EnumSet<AccessDelegationMode> delegationModes, Optional<String> refreshCredentialsEndpoint) createTableDirectwith entity-property idempotency support.org.apache.iceberg.rest.responses.LoadTableResponsecreateTableStaged(org.apache.iceberg.catalog.Namespace namespace, org.apache.iceberg.rest.requests.CreateTableRequest request) org.apache.iceberg.rest.responses.LoadTableResponsecreateTableStaged(org.apache.iceberg.catalog.Namespace namespace, org.apache.iceberg.rest.requests.CreateTableRequest request, EnumSet<AccessDelegationMode> delegationModes, Optional<String> refreshCredentialsEndpoint) org.apache.iceberg.rest.responses.LoadTableResponsecreateTableStagedWithWriteDelegation(org.apache.iceberg.catalog.Namespace namespace, org.apache.iceberg.rest.requests.CreateTableRequest request, Optional<String> refreshCredentialsEndpoint) org.apache.iceberg.rest.responses.LoadViewResponsecreateView(org.apache.iceberg.catalog.Namespace namespace, org.apache.iceberg.rest.requests.CreateViewRequest request) protected abstract org.apache.polaris.core.credentials.PolarisCredentialManagerprotected abstract org.apache.polaris.core.PolarisDiagnosticsvoiddropNamespace(org.apache.iceberg.catalog.Namespace namespace) voiddropTableWithoutPurge(org.apache.iceberg.catalog.TableIdentifier tableIdentifier) voiddropTableWithPurge(org.apache.iceberg.catalog.TableIdentifier tableIdentifier) voiddropView(org.apache.iceberg.catalog.TableIdentifier viewIdentifier) protected abstract EventAttributeMapprotected abstract jakarta.enterprise.inject.Instance<org.apache.polaris.core.catalog.FederatedCatalogFactory> protected abstract IdempotencyRequestContextprotected voidInitialize the catalog once authorized.org.apache.iceberg.rest.responses.ListNamespacesResponselistNamespaces(org.apache.iceberg.catalog.Namespace parent) org.apache.iceberg.rest.responses.ListNamespacesResponselistNamespaces(org.apache.iceberg.catalog.Namespace parent, String pageToken, Integer pageSize) org.apache.iceberg.rest.responses.ListTablesResponselistTables(org.apache.iceberg.catalog.Namespace namespace) org.apache.iceberg.rest.responses.ListTablesResponselistTables(org.apache.iceberg.catalog.Namespace namespace, String pageToken, Integer pageSize) org.apache.iceberg.rest.responses.ListTablesResponselistViews(org.apache.iceberg.catalog.Namespace namespace) org.apache.iceberg.rest.responses.ListTablesResponseorg.apache.iceberg.rest.responses.ImmutableLoadCredentialsResponseloadCredentials(org.apache.iceberg.catalog.TableIdentifier tableIdentifier, Optional<String> refreshCredentialsEndpoint) Vend credentials for a table using location data from entity internal properties, avoiding a full table metadata read from object storage.org.apache.iceberg.rest.responses.GetNamespaceResponseloadNamespaceMetadata(org.apache.iceberg.catalog.Namespace namespace) org.apache.iceberg.rest.responses.LoadTableResponseOptional<org.apache.iceberg.rest.responses.LoadTableResponse> loadTable(org.apache.iceberg.catalog.TableIdentifier tableIdentifier, String snapshots, IfNoneMatch ifNoneMatch, EnumSet<AccessDelegationMode> delegationModes, Optional<String> refreshCredentialsEndpoint) Optional<org.apache.iceberg.rest.responses.LoadTableResponse> loadTableIfStale(org.apache.iceberg.catalog.TableIdentifier tableIdentifier, IfNoneMatch ifNoneMatch, String snapshots) Attempt to perform a loadTable operation only when the specified set of eTags do not match the current state of the table metadata.org.apache.iceberg.rest.responses.LoadTableResponseloadTableWithAccessDelegation(org.apache.iceberg.catalog.TableIdentifier tableIdentifier, String snapshots, Optional<String> refreshCredentialsEndpoint) Optional<org.apache.iceberg.rest.responses.LoadTableResponse> loadTableWithAccessDelegationIfStale(org.apache.iceberg.catalog.TableIdentifier tableIdentifier, IfNoneMatch ifNoneMatch, String snapshots, Optional<String> refreshCredentialsEndpoint) Attempt to perform a loadTable operation with access delegation only when the if none of the provided eTags match the current state of the table metadata.org.apache.iceberg.rest.responses.LoadViewResponseloadView(org.apache.iceberg.catalog.TableIdentifier viewIdentifier) protected abstract org.apache.polaris.core.catalog.LocalCatalogFactoryprotected abstract IcebergMetricsReportervoidnamespaceExists(org.apache.iceberg.catalog.Namespace namespace) protected abstract CatalogPrefixParserorg.apache.iceberg.rest.responses.LoadTableResponseregisterTable(org.apache.iceberg.catalog.Namespace namespace, org.apache.iceberg.rest.requests.RegisterTableRequest request, EnumSet<AccessDelegationMode> delegationModes, Optional<String> refreshCredentialsEndpoint) Register a table.org.apache.iceberg.rest.responses.LoadViewResponseregisterView(org.apache.iceberg.catalog.Namespace namespace, org.apache.iceberg.rest.requests.RegisterViewRequest request) voidrenameTable(org.apache.iceberg.rest.requests.RenameTableRequest request) voidrenameView(org.apache.iceberg.rest.requests.RenameTableRequest request) org.apache.iceberg.rest.responses.LoadViewResponsereplaceView(org.apache.iceberg.catalog.TableIdentifier viewIdentifier, org.apache.iceberg.rest.requests.UpdateTableRequest request) voidreportMetrics(org.apache.iceberg.catalog.TableIdentifier identifier, org.apache.iceberg.rest.requests.ReportMetricsRequest request) protected abstract ReservedPropertiesprotected Optional<AccessDelegationMode> resolveAccessDelegationModes(EnumSet<AccessDelegationMode> requestedModes) Resolves the access delegation mode by delegating to the configuredAccessDelegationModeResolver.protected abstract org.apache.polaris.core.persistence.resolver.ResolverFactorybooleansendNotification(org.apache.iceberg.catalog.TableIdentifier identifier, org.apache.polaris.service.types.NotificationRequest request) protected abstract StorageAccessConfigProvidervoidtableExists(org.apache.iceberg.catalog.TableIdentifier tableIdentifier) org.apache.iceberg.rest.responses.UpdateNamespacePropertiesResponseupdateNamespaceProperties(org.apache.iceberg.catalog.Namespace namespace, org.apache.iceberg.rest.requests.UpdateNamespacePropertiesRequest request) org.apache.iceberg.rest.responses.LoadTableResponseupdateTable(org.apache.iceberg.catalog.TableIdentifier tableIdentifier, org.apache.iceberg.rest.requests.UpdateTableRequest request) org.apache.iceberg.rest.responses.LoadTableResponseupdateTableForStagedCreate(org.apache.iceberg.catalog.TableIdentifier tableIdentifier, org.apache.iceberg.rest.requests.UpdateTableRequest request) voidviewExists(org.apache.iceberg.catalog.TableIdentifier viewIdentifier) Methods inherited from class org.apache.polaris.service.catalog.common.CatalogHandler
authorizeBasicNamespaceOperationOrThrow, authorizeBasicNamespaceOperationOrThrow, authorizeBasicTableLikeOperationsOrThrow, authorizeCollectionOfTableLikeOperationOrThrow, authorizeCreateNamespaceUnderNamespaceOperationOrThrow, authorizeCreateTableLikeUnderNamespaceOperationOrThrow, authorizer, authorizeRegisterTableOverwriteOrThrow, authorizeRenameTableLikeOperationOrThrow, authorizeResolvedBasicTableLikeOperationOrThrow, authorizeResolvedCreateTableLikeUnderNamespaceOperationOrThrow, authorizeResolvedRegisterTableOverwriteOrThrow, callContext, catalogName, ensureResolutionManifestForTable, metaStoreManager, newResolutionManifest, polarisPrincipal, realmConfig, realmContext, resolutionManifestFactory, resolveAndAuthorizeBasicTableLikeOperationOrThrow, resolveBasicTableLikeTargetOrThrow
-
Constructor Details
-
IcebergCatalogHandler
public IcebergCatalogHandler()
-
-
Method Details
-
diagnostics
protected abstract org.apache.polaris.core.PolarisDiagnostics diagnostics() -
credentialManager
protected abstract org.apache.polaris.core.credentials.PolarisCredentialManager credentialManager() -
federatedCatalogFactories
protected abstract jakarta.enterprise.inject.Instance<org.apache.polaris.core.catalog.FederatedCatalogFactory> federatedCatalogFactories() -
prefixParser
-
resolverFactory
protected abstract org.apache.polaris.core.persistence.resolver.ResolverFactory resolverFactory() -
localCatalogFactory
protected abstract org.apache.polaris.core.catalog.LocalCatalogFactory localCatalogFactory() -
reservedProperties
-
catalogHandlerUtils
-
storageAccessConfigProvider
-
eventAttributeMap
-
metricsReporter
-
clock
-
accessDelegationModeResolver
-
idempotencyRequestContext
-
initializeCatalog
protected void initializeCatalog()Description copied from class:CatalogHandlerInitialize the catalog once authorized. Called after all `authorize...` methods.- Specified by:
initializeCatalogin classCatalogHandler
-
listNamespaces
public org.apache.iceberg.rest.responses.ListNamespacesResponse listNamespaces(org.apache.iceberg.catalog.Namespace parent) -
listNamespaces
-
createNamespace
public org.apache.iceberg.rest.responses.CreateNamespaceResponse createNamespace(org.apache.iceberg.rest.requests.CreateNamespaceRequest request) -
loadNamespaceMetadata
public org.apache.iceberg.rest.responses.GetNamespaceResponse loadNamespaceMetadata(org.apache.iceberg.catalog.Namespace namespace) -
namespaceExists
public void namespaceExists(org.apache.iceberg.catalog.Namespace namespace) -
dropNamespace
public void dropNamespace(org.apache.iceberg.catalog.Namespace namespace) -
updateNamespaceProperties
public org.apache.iceberg.rest.responses.UpdateNamespacePropertiesResponse updateNamespaceProperties(org.apache.iceberg.catalog.Namespace namespace, org.apache.iceberg.rest.requests.UpdateNamespacePropertiesRequest request) -
listTables
-
listTables
public org.apache.iceberg.rest.responses.ListTablesResponse listTables(org.apache.iceberg.catalog.Namespace namespace) -
createTableDirect
public org.apache.iceberg.rest.responses.LoadTableResponse createTableDirect(org.apache.iceberg.catalog.Namespace namespace, org.apache.iceberg.rest.requests.CreateTableRequest request) Create a table.- Parameters:
namespace- the namespace to create the table inrequest- the table creation request- Returns:
- ETagged
LoadTableResponseto uniquely identify the table metadata
-
authorizeCreateTableDirect
public void authorizeCreateTableDirect(org.apache.iceberg.catalog.Namespace namespace, org.apache.iceberg.rest.requests.CreateTableRequest request, boolean delegationRequested) -
createTableDirect
public org.apache.iceberg.rest.responses.LoadTableResponse createTableDirect(org.apache.iceberg.catalog.Namespace namespace, org.apache.iceberg.rest.requests.CreateTableRequest request, EnumSet<AccessDelegationMode> delegationModes, Optional<String> refreshCredentialsEndpoint) createTableDirectwith entity-property idempotency support. When idempotency is active for the request (IdempotencyRequestContext.isActive()), the key is embedded into the new table entity's internal properties within the same transaction as the create (expiry comes fromIdempotencyRequestContext). A subsequent retry that arrives while the key is still live replays the original success (rebuilding the load response from current catalog state) instead of returning a 409 conflict. -
createTableStaged
public org.apache.iceberg.rest.responses.LoadTableResponse createTableStaged(org.apache.iceberg.catalog.Namespace namespace, org.apache.iceberg.rest.requests.CreateTableRequest request) -
createTableStagedWithWriteDelegation
-
createTableStaged
public org.apache.iceberg.rest.responses.LoadTableResponse createTableStaged(org.apache.iceberg.catalog.Namespace namespace, org.apache.iceberg.rest.requests.CreateTableRequest request, EnumSet<AccessDelegationMode> delegationModes, Optional<String> refreshCredentialsEndpoint) -
registerTable
public org.apache.iceberg.rest.responses.LoadTableResponse registerTable(org.apache.iceberg.catalog.Namespace namespace, org.apache.iceberg.rest.requests.RegisterTableRequest request, EnumSet<AccessDelegationMode> delegationModes, Optional<String> refreshCredentialsEndpoint) Register a table.- Parameters:
namespace- The namespace to register the table inrequest- the register table requestdelegationModes- the access delegation modes to userefreshCredentialsEndpoint- the refresh credentials endpoint to use- Returns:
- ETagged
LoadTableResponseto uniquely identify the table metadata
-
sendNotification
public boolean sendNotification(org.apache.iceberg.catalog.TableIdentifier identifier, org.apache.polaris.service.types.NotificationRequest request) -
reportMetrics
public void reportMetrics(org.apache.iceberg.catalog.TableIdentifier identifier, org.apache.iceberg.rest.requests.ReportMetricsRequest request) -
loadTable
public org.apache.iceberg.rest.responses.LoadTableResponse loadTable(org.apache.iceberg.catalog.TableIdentifier tableIdentifier, String snapshots) -
loadTableIfStale
public Optional<org.apache.iceberg.rest.responses.LoadTableResponse> loadTableIfStale(org.apache.iceberg.catalog.TableIdentifier tableIdentifier, IfNoneMatch ifNoneMatch, String snapshots) Attempt to perform a loadTable operation only when the specified set of eTags do not match the current state of the table metadata.- Parameters:
tableIdentifier- The identifier of the table to loadifNoneMatch- set of entity-tags to check the metadata against for stalenesssnapshots-- Returns:
Optional.empty()if the ETag is current, anOptionalcontaining the load table response, otherwise
-
loadTableWithAccessDelegation
-
loadTableWithAccessDelegationIfStale
public Optional<org.apache.iceberg.rest.responses.LoadTableResponse> loadTableWithAccessDelegationIfStale(org.apache.iceberg.catalog.TableIdentifier tableIdentifier, IfNoneMatch ifNoneMatch, String snapshots, Optional<String> refreshCredentialsEndpoint) Attempt to perform a loadTable operation with access delegation only when the if none of the provided eTags match the current state of the table metadata.- Parameters:
tableIdentifier- The identifier of the table to loadifNoneMatch- set of entity-tags to check the metadata against for stalenesssnapshots-- Returns:
Optional.empty()if the ETag is current, anOptionalcontaining the load table response, otherwise
-
loadCredentials
public org.apache.iceberg.rest.responses.ImmutableLoadCredentialsResponse loadCredentials(org.apache.iceberg.catalog.TableIdentifier tableIdentifier, Optional<String> refreshCredentialsEndpoint) Vend credentials for a table using location data from entity internal properties, avoiding a full table metadata read from object storage. Falls back to the standard loadTableWithAccessDelegation path if the entity lacks the required location properties. -
loadTable
public Optional<org.apache.iceberg.rest.responses.LoadTableResponse> loadTable(org.apache.iceberg.catalog.TableIdentifier tableIdentifier, String snapshots, IfNoneMatch ifNoneMatch, EnumSet<AccessDelegationMode> delegationModes, Optional<String> refreshCredentialsEndpoint) -
updateTable
public org.apache.iceberg.rest.responses.LoadTableResponse updateTable(org.apache.iceberg.catalog.TableIdentifier tableIdentifier, org.apache.iceberg.rest.requests.UpdateTableRequest request) -
updateTableForStagedCreate
public org.apache.iceberg.rest.responses.LoadTableResponse updateTableForStagedCreate(org.apache.iceberg.catalog.TableIdentifier tableIdentifier, org.apache.iceberg.rest.requests.UpdateTableRequest request) -
dropTableWithoutPurge
public void dropTableWithoutPurge(org.apache.iceberg.catalog.TableIdentifier tableIdentifier) -
dropTableWithPurge
public void dropTableWithPurge(org.apache.iceberg.catalog.TableIdentifier tableIdentifier) -
tableExists
public void tableExists(org.apache.iceberg.catalog.TableIdentifier tableIdentifier) -
renameTable
public void renameTable(org.apache.iceberg.rest.requests.RenameTableRequest request) -
commitTransaction
public void commitTransaction(org.apache.iceberg.rest.requests.CommitTransactionRequest commitTransactionRequest) -
listViews
-
listViews
public org.apache.iceberg.rest.responses.ListTablesResponse listViews(org.apache.iceberg.catalog.Namespace namespace) -
createView
public org.apache.iceberg.rest.responses.LoadViewResponse createView(org.apache.iceberg.catalog.Namespace namespace, org.apache.iceberg.rest.requests.CreateViewRequest request) -
registerView
public org.apache.iceberg.rest.responses.LoadViewResponse registerView(org.apache.iceberg.catalog.Namespace namespace, org.apache.iceberg.rest.requests.RegisterViewRequest request) -
loadView
public org.apache.iceberg.rest.responses.LoadViewResponse loadView(org.apache.iceberg.catalog.TableIdentifier viewIdentifier) -
replaceView
public org.apache.iceberg.rest.responses.LoadViewResponse replaceView(org.apache.iceberg.catalog.TableIdentifier viewIdentifier, org.apache.iceberg.rest.requests.UpdateTableRequest request) -
dropView
public void dropView(org.apache.iceberg.catalog.TableIdentifier viewIdentifier) -
viewExists
public void viewExists(org.apache.iceberg.catalog.TableIdentifier viewIdentifier) -
renameView
public void renameView(org.apache.iceberg.rest.requests.RenameTableRequest request) -
resolveAccessDelegationModes
protected Optional<AccessDelegationMode> resolveAccessDelegationModes(EnumSet<AccessDelegationMode> requestedModes) Resolves the access delegation mode by delegating to the configuredAccessDelegationModeResolver.- Parameters:
requestedModes- The non-empty set of delegation modes requested by the client- Returns:
- The resolved access delegation mode, or empty if no delegation mode was resolved
-
close
- Specified by:
closein interfaceAutoCloseable- Throws:
Exception
-