This is an automated email from the ASF dual-hosted git repository.
blue pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/iceberg.git
The following commit(s) were added to refs/heads/master by this push:
new cd21f68e7b Core: Pass purgeRequested flag to REST server (#6073)
cd21f68e7b is described below
commit cd21f68e7bb62d3be76e98ac519849944e4dbedf
Author: Eduard Tudenhöfner <[email protected]>
AuthorDate: Tue Nov 8 17:40:50 2022 +0100
Core: Pass purgeRequested flag to REST server (#6073)
The motivation behind this change is that the REST server should know
whether a `purge` was requested or not, rather than having the REST
client throw an error.
---
.../java/org/apache/iceberg/rest/CatalogHandlers.java | 7 +++++++
.../main/java/org/apache/iceberg/rest/HTTPClient.java | 3 ++-
.../main/java/org/apache/iceberg/rest/RESTClient.java | 12 +++++++++++-
.../org/apache/iceberg/rest/RESTSessionCatalog.java | 16 ++++++++++++++--
.../java/org/apache/iceberg/catalog/CatalogTests.java | 18 ++++++++++++++++++
.../org/apache/iceberg/rest/RESTCatalogAdapter.java | 11 +++++++++--
.../java/org/apache/iceberg/rest/TestHTTPClient.java | 2 +-
7 files changed, 62 insertions(+), 7 deletions(-)
diff --git a/core/src/main/java/org/apache/iceberg/rest/CatalogHandlers.java
b/core/src/main/java/org/apache/iceberg/rest/CatalogHandlers.java
index e260bc313d..fc8384d48b 100644
--- a/core/src/main/java/org/apache/iceberg/rest/CatalogHandlers.java
+++ b/core/src/main/java/org/apache/iceberg/rest/CatalogHandlers.java
@@ -229,6 +229,13 @@ public class CatalogHandlers {
}
}
+ public static void purgeTable(Catalog catalog, TableIdentifier ident) {
+ boolean dropped = catalog.dropTable(ident, true);
+ if (!dropped) {
+ throw new NoSuchTableException("Table does not exist: %s", ident);
+ }
+ }
+
public static LoadTableResponse loadTable(Catalog catalog, TableIdentifier
ident) {
Table table = catalog.loadTable(ident);
diff --git a/core/src/main/java/org/apache/iceberg/rest/HTTPClient.java
b/core/src/main/java/org/apache/iceberg/rest/HTTPClient.java
index 162b57b99b..76f56d353e 100644
--- a/core/src/main/java/org/apache/iceberg/rest/HTTPClient.java
+++ b/core/src/main/java/org/apache/iceberg/rest/HTTPClient.java
@@ -272,10 +272,11 @@ public class HTTPClient implements RESTClient {
@Override
public <T extends RESTResponse> T delete(
String path,
+ Map<String, String> queryParams,
Class<T> responseType,
Map<String, String> headers,
Consumer<ErrorResponse> errorHandler) {
- return execute(Method.DELETE, path, null, null, responseType, headers,
errorHandler);
+ return execute(Method.DELETE, path, queryParams, null, responseType,
headers, errorHandler);
}
@Override
diff --git a/core/src/main/java/org/apache/iceberg/rest/RESTClient.java
b/core/src/main/java/org/apache/iceberg/rest/RESTClient.java
index 2057f23fc3..8e69858626 100644
--- a/core/src/main/java/org/apache/iceberg/rest/RESTClient.java
+++ b/core/src/main/java/org/apache/iceberg/rest/RESTClient.java
@@ -37,14 +37,24 @@ public interface RESTClient extends Closeable {
default <T extends RESTResponse> T delete(
String path,
+ Map<String, String> queryParams,
Class<T> responseType,
Supplier<Map<String, String>> headers,
Consumer<ErrorResponse> errorHandler) {
- return delete(path, responseType, headers.get(), errorHandler);
+ return delete(path, queryParams, responseType, headers.get(),
errorHandler);
+ }
+
+ default <T extends RESTResponse> T delete(
+ String path,
+ Class<T> responseType,
+ Supplier<Map<String, String>> headers,
+ Consumer<ErrorResponse> errorHandler) {
+ return delete(path, ImmutableMap.of(), responseType, headers.get(),
errorHandler);
}
<T extends RESTResponse> T delete(
String path,
+ Map<String, String> queryParams,
Class<T> responseType,
Map<String, String> headers,
Consumer<ErrorResponse> errorHandler);
diff --git a/core/src/main/java/org/apache/iceberg/rest/RESTSessionCatalog.java
b/core/src/main/java/org/apache/iceberg/rest/RESTSessionCatalog.java
index 55aca569f3..692ee7f3a0 100644
--- a/core/src/main/java/org/apache/iceberg/rest/RESTSessionCatalog.java
+++ b/core/src/main/java/org/apache/iceberg/rest/RESTSessionCatalog.java
@@ -223,8 +223,20 @@ public class RESTSessionCatalog extends BaseSessionCatalog
}
@Override
- public boolean purgeTable(SessionContext context, TableIdentifier ident) {
- throw new UnsupportedOperationException("Purge is not supported");
+ public boolean purgeTable(SessionContext context, TableIdentifier
identifier) {
+ checkIdentifierIsValid(identifier);
+
+ try {
+ client.delete(
+ paths.table(identifier),
+ ImmutableMap.of("purgeRequested", "true"),
+ null,
+ headers(context),
+ ErrorHandlers.tableErrorHandler());
+ return true;
+ } catch (NoSuchTableException e) {
+ return false;
+ }
}
@Override
diff --git a/core/src/test/java/org/apache/iceberg/catalog/CatalogTests.java
b/core/src/test/java/org/apache/iceberg/catalog/CatalogTests.java
index 0130dbdb6e..044f9870d9 100644
--- a/core/src/test/java/org/apache/iceberg/catalog/CatalogTests.java
+++ b/core/src/test/java/org/apache/iceberg/catalog/CatalogTests.java
@@ -799,6 +799,24 @@ public abstract class CatalogTests<C extends Catalog &
SupportsNamespaces> {
Assert.assertFalse("Table should not exist after drop",
catalog.tableExists(TABLE));
}
+ @Test
+ public void testDropTableWithPurge() {
+ C catalog = catalog();
+
+ if (requiresNamespaceCreate()) {
+ catalog.createNamespace(NS);
+ }
+
+ Assert.assertFalse("Table should not exist before create",
catalog.tableExists(TABLE));
+
+ catalog.buildTable(TABLE, SCHEMA).create();
+ Assert.assertTrue("Table should exist after create",
catalog.tableExists(TABLE));
+
+ boolean dropped = catalog.dropTable(TABLE, true);
+ Assert.assertTrue("Should drop a table that does exist", dropped);
+ Assert.assertFalse("Table should not exist after drop",
catalog.tableExists(TABLE));
+ }
+
@Test
public void testDropMissingTable() {
C catalog = catalog();
diff --git a/core/src/test/java/org/apache/iceberg/rest/RESTCatalogAdapter.java
b/core/src/test/java/org/apache/iceberg/rest/RESTCatalogAdapter.java
index 2a2267d85e..55623c0d9e 100644
--- a/core/src/test/java/org/apache/iceberg/rest/RESTCatalogAdapter.java
+++ b/core/src/test/java/org/apache/iceberg/rest/RESTCatalogAdapter.java
@@ -56,6 +56,7 @@ import org.apache.iceberg.rest.responses.LoadTableResponse;
import org.apache.iceberg.rest.responses.OAuthTokenResponse;
import org.apache.iceberg.rest.responses.UpdateNamespacePropertiesResponse;
import org.apache.iceberg.util.Pair;
+import org.apache.iceberg.util.PropertyUtil;
/** Adaptor class to translate REST requests into {@link Catalog} API calls. */
public class RESTCatalogAdapter implements RESTClient {
@@ -207,6 +208,7 @@ public class RESTCatalogAdapter implements RESTClient {
}
}
+ @SuppressWarnings("MethodLength")
public <T extends RESTResponse> T handleRequest(
Route route, Map<String, String> vars, Object body, Class<T>
responseType) {
switch (route) {
@@ -320,7 +322,11 @@ public class RESTCatalogAdapter implements RESTClient {
case DROP_TABLE:
{
- CatalogHandlers.dropTable(catalog, identFromPathVars(vars));
+ if (PropertyUtil.propertyAsBoolean(vars, "purgeRequested", false)) {
+ CatalogHandlers.purgeTable(catalog, identFromPathVars(vars));
+ } else {
+ CatalogHandlers.dropTable(catalog, identFromPathVars(vars));
+ }
return null;
}
@@ -398,10 +404,11 @@ public class RESTCatalogAdapter implements RESTClient {
@Override
public <T extends RESTResponse> T delete(
String path,
+ Map<String, String> queryParams,
Class<T> responseType,
Map<String, String> headers,
Consumer<ErrorResponse> errorHandler) {
- return execute(HTTPMethod.DELETE, path, null, null, responseType, headers,
errorHandler);
+ return execute(HTTPMethod.DELETE, path, queryParams, null, responseType,
headers, errorHandler);
}
@Override
diff --git a/core/src/test/java/org/apache/iceberg/rest/TestHTTPClient.java
b/core/src/test/java/org/apache/iceberg/rest/TestHTTPClient.java
index 044ca320f1..21a9ba5b9f 100644
--- a/core/src/test/java/org/apache/iceberg/rest/TestHTTPClient.java
+++ b/core/src/test/java/org/apache/iceberg/rest/TestHTTPClient.java
@@ -219,7 +219,7 @@ public class TestHTTPClient {
restClient.head(path, headers, onError);
return null;
case DELETE:
- return restClient.delete(path, Item.class, headers, onError);
+ return restClient.delete(path, Item.class, () -> headers, onError);
default:
throw new IllegalArgumentException(String.format("Invalid method: %s",
method));
}