diff --git a/core/src/test/scala/org/apache/spark/sql/BaseTiSparkSuite.scala b/core/src/test/scala/org/apache/spark/sql/BaseTiSparkSuite.scala index a068da848d..c563147f2b 100644 --- a/core/src/test/scala/org/apache/spark/sql/BaseTiSparkSuite.scala +++ b/core/src/test/scala/org/apache/spark/sql/BaseTiSparkSuite.scala @@ -114,6 +114,7 @@ class BaseTiSparkSuite extends QueryTest with SharedSQLContext { .option(JDBCOptions.JDBC_DRIVER_CLASS, "com.mysql.jdbc.Driver") .load() .filter(s"table_schema = '$dbName'") + .filter(s"TABLE_TYPE='BASE TABLE'") .select("TABLE_NAME") val tables = tableDF.collect().map((row: Row) => row.get(0).toString) tables.foreach(createOrReplaceTempView(dbName, _)) diff --git a/core/src/test/scala/org/apache/spark/sql/ViewTestSuite.scala b/core/src/test/scala/org/apache/spark/sql/ViewTestSuite.scala new file mode 100644 index 0000000000..df49f043de --- /dev/null +++ b/core/src/test/scala/org/apache/spark/sql/ViewTestSuite.scala @@ -0,0 +1,24 @@ +package org.apache.spark.sql + +class ViewTestSuite extends BaseTiSparkSuite { + private val table = "test_view" + + test("Test View") { + tidbStmt.execute(s"drop table if exists $table") + try { + tidbStmt.execute("drop view if exists v") + } catch { + case _: Exception => cancel + } + + tidbStmt.execute(s"create table $table(qty INT, price INT);") + + tidbStmt.execute(s"INSERT INTO $table VALUES(3, 50);") + tidbStmt.execute(s"CREATE VIEW v AS SELECT qty, price, qty*price AS value FROM $table;") + + refreshConnections() + + judge(s"select * from $table") + intercept[AnalysisException](spark.sql("select * from v")) + } +} diff --git a/tikv-client/src/main/java/com/pingcap/tikv/catalog/Catalog.java b/tikv-client/src/main/java/com/pingcap/tikv/catalog/Catalog.java index 5f54cb2408..a9c5b9b341 100644 --- a/tikv-client/src/main/java/com/pingcap/tikv/catalog/Catalog.java +++ b/tikv-client/src/main/java/com/pingcap/tikv/catalog/Catalog.java @@ -88,7 +88,9 @@ public List listTables(TiDBInfo db) { if (tableMap == null) { tableMap = loadTables(db); } - return ImmutableList.copyOf(tableMap.values()); + Collection tables = tableMap.values(); + tables.removeIf(TiTableInfo::isView); + return ImmutableList.copyOf(tables); } public TiTableInfo getTable(TiDBInfo db, String tableName) { @@ -96,7 +98,11 @@ public TiTableInfo getTable(TiDBInfo db, String tableName) { if (tableMap == null) { tableMap = loadTables(db); } - return tableMap.get(tableName.toLowerCase()); + TiTableInfo tbl = tableMap.get(tableName.toLowerCase()); + // https://github.com/pingcap/tispark/issues/961 + // TODO: support reading from view table in the future. + if (tbl != null && tbl.isView()) return null; + return tbl; } private Map loadTables(TiDBInfo db) { diff --git a/tikv-client/src/main/java/com/pingcap/tikv/meta/TiTableInfo.java b/tikv-client/src/main/java/com/pingcap/tikv/meta/TiTableInfo.java index d1d630eca1..095d31334d 100644 --- a/tikv-client/src/main/java/com/pingcap/tikv/meta/TiTableInfo.java +++ b/tikv-client/src/main/java/com/pingcap/tikv/meta/TiTableInfo.java @@ -46,8 +46,10 @@ public class TiTableInfo implements Serializable { private final long oldSchemaId; private final long columnSize; // estimated column size private final TiPartitionInfo partitionInfo; + private final TiViewInfo viewInfo; @JsonCreator + @JsonIgnoreProperties(ignoreUnknown = true) public TiTableInfo( @JsonProperty("id") long id, @JsonProperty("name") CIStr name, @@ -61,7 +63,8 @@ public TiTableInfo( @JsonProperty("max_col_id") long maxColumnId, @JsonProperty("max_idx_id") long maxIndexId, @JsonProperty("old_schema_id") long oldSchemaId, - @JsonProperty("partition") TiPartitionInfo partitionInfo) { + @JsonProperty("partition") TiPartitionInfo partitionInfo, + @JsonProperty("view") TiViewInfo viewInfo) { this.id = id; this.name = name.getL(); this.charset = charset; @@ -78,6 +81,11 @@ public TiTableInfo( this.maxIndexId = maxIndexId; this.oldSchemaId = oldSchemaId; this.partitionInfo = partitionInfo; + this.viewInfo = viewInfo; + } + + public boolean isView() { + return this.viewInfo != null; } public long getId() { @@ -199,7 +207,8 @@ public TiTableInfo copyTableWithRowId() { getMaxColumnId(), getMaxIndexId(), getOldSchemaId(), - partitionInfo); + partitionInfo, + null); } else { return this; } diff --git a/tikv-client/src/main/java/com/pingcap/tikv/meta/TiUserIdentity.java b/tikv-client/src/main/java/com/pingcap/tikv/meta/TiUserIdentity.java new file mode 100644 index 0000000000..73b65c149c --- /dev/null +++ b/tikv-client/src/main/java/com/pingcap/tikv/meta/TiUserIdentity.java @@ -0,0 +1,28 @@ +package com.pingcap.tikv.meta; + +import com.fasterxml.jackson.annotation.JsonCreator; +import com.fasterxml.jackson.annotation.JsonProperty; +import java.io.Serializable; + +// TiUserIdentity represents username and hostname. +public class TiUserIdentity implements Serializable { + private String username; + private String hostname; + private boolean currentUser; + private String authUsername; + private String authHostname; + + @JsonCreator + public TiUserIdentity( + @JsonProperty("Username") String userName, + @JsonProperty("Hostname") String hostName, + @JsonProperty("CurrentUser") boolean currentUser, + @JsonProperty("AuthUsername") String authUserName, + @JsonProperty("AuthHostname") String authHostName) { + this.authHostname = authHostName; + this.authUsername = authUserName; + this.hostname = hostName; + this.username = userName; + this.currentUser = currentUser; + } +} diff --git a/tikv-client/src/main/java/com/pingcap/tikv/meta/TiViewInfo.java b/tikv-client/src/main/java/com/pingcap/tikv/meta/TiViewInfo.java new file mode 100644 index 0000000000..d0aaad4079 --- /dev/null +++ b/tikv-client/src/main/java/com/pingcap/tikv/meta/TiViewInfo.java @@ -0,0 +1,38 @@ +package com.pingcap.tikv.meta; + +import com.fasterxml.jackson.annotation.JsonCreator; +import com.fasterxml.jackson.annotation.JsonProperty; +import java.io.Serializable; +import java.util.List; +import java.util.stream.Collectors; + +public class TiViewInfo implements Serializable { + // ViewAlgorithm is VIEW's SQL AlGORITHM characteristic. + // See https://dev.mysql.com/doc/refman/5.7/en/view-algorithms.html + private final long viewAlgorithm; + private final TiUserIdentity userIdentity; + // ViewSecurity is VIEW's SQL SECURITY characteristic. + // See https://dev.mysql.com/doc/refman/5.7/en/create-view.html + private final long viewSecurity; + private final String viewSelect; + // ViewCheckOption is VIEW's WITH CHECK OPTION clause part. + // See https://dev.mysql.com/doc/refman/5.7/en/view-check-option.html + private final long viewCheckOpt; + private final List viewCols; + + @JsonCreator + public TiViewInfo( + @JsonProperty("view_algorithm") long viewAlgorithm, + @JsonProperty("view_definer") TiUserIdentity userIdentity, + @JsonProperty("view_security") long viewSecurity, + @JsonProperty("view_select") String viewSelect, + @JsonProperty("view_checkoption") long viewCheckOpt, + @JsonProperty("view_cols") List viewCols) { + this.viewAlgorithm = viewAlgorithm; + this.userIdentity = userIdentity; + this.viewSecurity = viewSecurity; + this.viewSelect = viewSelect; + this.viewCheckOpt = viewCheckOpt; + this.viewCols = viewCols.stream().map(CIStr::getO).collect(Collectors.toList()); + } +} diff --git a/tikv-client/src/main/java/com/pingcap/tikv/types/DecimalType.java b/tikv-client/src/main/java/com/pingcap/tikv/types/DecimalType.java index 04ed8969fa..e11989aa4b 100644 --- a/tikv-client/src/main/java/com/pingcap/tikv/types/DecimalType.java +++ b/tikv-client/src/main/java/com/pingcap/tikv/types/DecimalType.java @@ -28,7 +28,8 @@ public class DecimalType extends DataType { public static final DecimalType DECIMAL = new DecimalType(MySQLType.TypeNewDecimal); - public static final MySQLType[] subTypes = new MySQLType[] {MySQLType.TypeNewDecimal}; + public static final MySQLType[] subTypes = + new MySQLType[] {MySQLType.TypeNewDecimal, MySQLType.TypeDecimal}; private DecimalType(MySQLType tp) { super(tp); diff --git a/tikv-client/src/test/java/com/pingcap/tikv/meta/MetaUtils.java b/tikv-client/src/test/java/com/pingcap/tikv/meta/MetaUtils.java index f51e97dfdf..3057b6038e 100644 --- a/tikv-client/src/test/java/com/pingcap/tikv/meta/MetaUtils.java +++ b/tikv-client/src/test/java/com/pingcap/tikv/meta/MetaUtils.java @@ -130,7 +130,20 @@ public TiTableInfo build() { name = "Table" + tid; } return new TiTableInfo( - tid, CIStr.newCIStr(name), "", "", pkHandle, columns, indices, "", 0, 0, 0, 0, partInfo); + tid, + CIStr.newCIStr(name), + "", + "", + pkHandle, + columns, + indices, + "", + 0, + 0, + 0, + 0, + partInfo, + null); } }