Skip to content

Commit

Permalink
API, Core: Add sqlFor API to views to handle resolving a representati…
Browse files Browse the repository at this point in the history
…on for a dialect(#9247)
  • Loading branch information
amogh-jahagirdar authored Dec 15, 2023
1 parent d56dd63 commit 8181f84
Show file tree
Hide file tree
Showing 3 changed files with 84 additions and 0 deletions.
11 changes: 11 additions & 0 deletions api/src/main/java/org/apache/iceberg/view/View.java
Original file line number Diff line number Diff line change
Expand Up @@ -121,4 +121,15 @@ default UpdateLocation updateLocation() {
default UUID uuid() {
throw new UnsupportedOperationException("Retrieving a view's uuid is not supported");
}

/**
* Returns the view representation for the given SQL dialect
*
* @return the view representation for the given SQL dialect, or null if no representation could
* be resolved
*/
default SQLViewRepresentation sqlFor(String dialect) {
throw new UnsupportedOperationException(
"Resolving a sql with a given dialect is not supported");
}
}
25 changes: 25 additions & 0 deletions core/src/main/java/org/apache/iceberg/view/BaseView.java
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@
import java.util.UUID;
import org.apache.iceberg.Schema;
import org.apache.iceberg.UpdateLocation;
import org.apache.iceberg.relocated.com.google.common.base.Preconditions;

public class BaseView implements View, Serializable {

Expand Down Expand Up @@ -103,4 +104,28 @@ public UpdateLocation updateLocation() {
public UUID uuid() {
return UUID.fromString(ops.current().uuid());
}

/**
* This implementation of sqlFor will resolve what is considered the "closest" dialect. If an
* exact match is found, then that is returned. Otherwise, the first representation would be
* returned. If no SQL representation is found, null is returned.
*/
@Override
public SQLViewRepresentation sqlFor(String dialect) {
Preconditions.checkArgument(dialect != null, "Invalid dialect: null");
Preconditions.checkArgument(!dialect.isEmpty(), "Invalid dialect: (empty string)");
SQLViewRepresentation closest = null;
for (ViewRepresentation representation : currentVersion().representations()) {
if (representation instanceof SQLViewRepresentation) {
SQLViewRepresentation sqlViewRepresentation = (SQLViewRepresentation) representation;
if (sqlViewRepresentation.dialect().equals(dialect)) {
return sqlViewRepresentation;
} else if (closest == null) {
closest = sqlViewRepresentation;
}
}
}

return closest;
}
}
48 changes: 48 additions & 0 deletions core/src/test/java/org/apache/iceberg/view/ViewCatalogTests.java
Original file line number Diff line number Diff line change
Expand Up @@ -1669,4 +1669,52 @@ public void concurrentReplaceViewVersion() {
.build());
}
}

@Test
public void testSqlForMultipleDialects() {
TableIdentifier identifier = TableIdentifier.of("ns", "view");

if (requiresNamespaceCreate()) {
catalog().createNamespace(identifier.namespace());
}

View view =
catalog()
.buildView(identifier)
.withSchema(SCHEMA)
.withDefaultNamespace(identifier.namespace())
.withDefaultCatalog(catalog().name())
.withQuery("spark", "select * from ns.tbl")
.withQuery("trino", "select * from ns.tbl using X")
.create();

assertThat(view.sqlFor("spark").sql()).isEqualTo("select * from ns.tbl");
assertThat(view.sqlFor("trino").sql()).isEqualTo("select * from ns.tbl using X");
assertThat(view.sqlFor("unknown-dialect").sql()).isEqualTo("select * from ns.tbl");
}

@Test
public void testSqlForInvalidArguments() {
TableIdentifier identifier = TableIdentifier.of("ns", "view");

if (requiresNamespaceCreate()) {
catalog().createNamespace(identifier.namespace());
}

View view =
catalog()
.buildView(identifier)
.withSchema(SCHEMA)
.withDefaultNamespace(identifier.namespace())
.withDefaultCatalog(catalog().name())
.withQuery("spark", "select * from ns.tbl")
.create();

assertThatThrownBy(() -> view.sqlFor(null))
.isInstanceOf(IllegalArgumentException.class)
.hasMessage("Invalid dialect: null");
assertThatThrownBy(() -> view.sqlFor(""))
.isInstanceOf(IllegalArgumentException.class)
.hasMessage("Invalid dialect: (empty string)");
}
}

0 comments on commit 8181f84

Please sign in to comment.