Author: namit
Date: Wed Feb 20 12:56:38 2013
New Revision: 1448138

URL: http://svn.apache.org/r1448138
Log:
HIVE-4027 Thrift alter_table api doesnt validate column type
(Gang Tim Liu via namit)


Modified:
    
hive/trunk/metastore/src/java/org/apache/hadoop/hive/metastore/HiveAlterHandler.java
    
hive/trunk/metastore/src/java/org/apache/hadoop/hive/metastore/HiveMetaStore.java
    
hive/trunk/metastore/src/java/org/apache/hadoop/hive/metastore/MetaStoreUtils.java
    
hive/trunk/metastore/src/test/org/apache/hadoop/hive/metastore/TestHiveMetaStore.java

Modified: 
hive/trunk/metastore/src/java/org/apache/hadoop/hive/metastore/HiveAlterHandler.java
URL: 
http://svn.apache.org/viewvc/hive/trunk/metastore/src/java/org/apache/hadoop/hive/metastore/HiveAlterHandler.java?rev=1448138&r1=1448137&r2=1448138&view=diff
==============================================================================
--- 
hive/trunk/metastore/src/java/org/apache/hadoop/hive/metastore/HiveAlterHandler.java
 (original)
+++ 
hive/trunk/metastore/src/java/org/apache/hadoop/hive/metastore/HiveAlterHandler.java
 Wed Feb 20 12:56:38 2013
@@ -64,7 +64,7 @@ public class HiveAlterHandler implements
     }
 
     if (!MetaStoreUtils.validateName(newt.getTableName())
-        || !MetaStoreUtils.validateColNames(newt.getSd().getCols())) {
+        || !MetaStoreUtils.validateTblColumns(newt.getSd().getCols())) {
       throw new InvalidOperationException(newt.getTableName()
           + " is not a valid object name");
     }

Modified: 
hive/trunk/metastore/src/java/org/apache/hadoop/hive/metastore/HiveMetaStore.java
URL: 
http://svn.apache.org/viewvc/hive/trunk/metastore/src/java/org/apache/hadoop/hive/metastore/HiveMetaStore.java?rev=1448138&r1=1448137&r2=1448138&view=diff
==============================================================================
--- 
hive/trunk/metastore/src/java/org/apache/hadoop/hive/metastore/HiveMetaStore.java
 (original)
+++ 
hive/trunk/metastore/src/java/org/apache/hadoop/hive/metastore/HiveMetaStore.java
 Wed Feb 20 12:56:38 2013
@@ -995,9 +995,9 @@ public class HiveMetaStore extends Thrif
         InvalidObjectException, NoSuchObjectException {
 
       if (!MetaStoreUtils.validateName(tbl.getTableName())
-          || !MetaStoreUtils.validateColNames(tbl.getSd().getCols())
+          || !MetaStoreUtils.validateTblColumns(tbl.getSd().getCols())
           || (tbl.getPartitionKeys() != null && !MetaStoreUtils
-              .validateColNames(tbl.getPartitionKeys()))
+              .validateTblColumns(tbl.getPartitionKeys()))
           || !MetaStoreUtils.validateSkewedColNames(
               (null == tbl.getSd().getSkewedInfo()) ?
                   null : tbl.getSd().getSkewedInfo().getSkewedColNames())

Modified: 
hive/trunk/metastore/src/java/org/apache/hadoop/hive/metastore/MetaStoreUtils.java
URL: 
http://svn.apache.org/viewvc/hive/trunk/metastore/src/java/org/apache/hadoop/hive/metastore/MetaStoreUtils.java?rev=1448138&r1=1448137&r2=1448138&view=diff
==============================================================================
--- 
hive/trunk/metastore/src/java/org/apache/hadoop/hive/metastore/MetaStoreUtils.java
 (original)
+++ 
hive/trunk/metastore/src/java/org/apache/hadoop/hive/metastore/MetaStoreUtils.java
 Wed Feb 20 12:56:38 2013
@@ -27,11 +27,13 @@ import java.net.ServerSocket;
 import java.net.Socket;
 import java.util.ArrayList;
 import java.util.HashMap;
+import java.util.HashSet;
 import java.util.Iterator;
 import java.util.List;
 import java.util.Map;
 import java.util.Map.Entry;
 import java.util.Properties;
+import java.util.Set;
 import java.util.regex.Matcher;
 import java.util.regex.Pattern;
 
@@ -326,11 +328,38 @@ public class MetaStoreUtils {
     return false;
   }
 
-  static public boolean validateColNames(List<FieldSchema> cols) {
+  static public boolean validateTblColumns(List<FieldSchema> cols) {
     for (FieldSchema fieldSchema : cols) {
       if (!validateName(fieldSchema.getName())) {
         return false;
       }
+      if (!validateColumnType(fieldSchema.getType())) {
+        return false;
+      }
+    }
+    return true;
+  }
+
+  /**
+   * validate column type
+   *
+   * if it is predefined, yes. otherwise no
+   * @param name
+   * @return
+   */
+  static public boolean validateColumnType(String type) {
+    int last = 0;
+    boolean lastAlphaDigit = Character.isLetterOrDigit(type.charAt(last));
+    for (int i = 1; i <= type.length(); i++) {
+      if (i == type.length()
+          || Character.isLetterOrDigit(type.charAt(i)) != lastAlphaDigit) {
+        String token = type.substring(last, i);
+        last = i;
+        if (!hiveThriftTypeMap.contains(token)) {
+          return false;
+        }
+        break;
+      }
     }
     return true;
   }
@@ -419,6 +448,15 @@ public class MetaStoreUtils {
         org.apache.hadoop.hive.serde.serdeConstants.DECIMAL_TYPE_NAME, 
"decimal");
   }
 
+  static Set<String> hiveThriftTypeMap; //for validation
+  static {
+    hiveThriftTypeMap = new HashSet<String>();
+    
hiveThriftTypeMap.addAll(org.apache.hadoop.hive.serde.serdeConstants.PrimitiveTypes);
+    
hiveThriftTypeMap.addAll(org.apache.hadoop.hive.serde.serdeConstants.CollectionTypes);
+    
hiveThriftTypeMap.add(org.apache.hadoop.hive.serde.serdeConstants.UNION_TYPE_NAME);
+    
hiveThriftTypeMap.add(org.apache.hadoop.hive.serde.serdeConstants.STRUCT_TYPE_NAME);
+  }
+
   /**
    * Convert type to ThriftType. We do that by tokenizing the type and convert
    * each token.

Modified: 
hive/trunk/metastore/src/test/org/apache/hadoop/hive/metastore/TestHiveMetaStore.java
URL: 
http://svn.apache.org/viewvc/hive/trunk/metastore/src/test/org/apache/hadoop/hive/metastore/TestHiveMetaStore.java?rev=1448138&r1=1448137&r2=1448138&view=diff
==============================================================================
--- 
hive/trunk/metastore/src/test/org/apache/hadoop/hive/metastore/TestHiveMetaStore.java
 (original)
+++ 
hive/trunk/metastore/src/test/org/apache/hadoop/hive/metastore/TestHiveMetaStore.java
 Wed Feb 20 12:56:38 2013
@@ -854,8 +854,8 @@ public abstract class TestHiveMetaStore 
 
   public void testDatabaseLocationWithPermissionProblems() throws Exception {
 
-    // Note: The following test will fail if you are running this test as 
root. Setting 
-    // permission to '0' on the database folder will not preclude root from 
being able 
+    // Note: The following test will fail if you are running this test as 
root. Setting
+    // permission to '0' on the database folder will not preclude root from 
being able
     // to create the necessary files.
 
     if (System.getProperty("user.name").equals("root")) {
@@ -1482,6 +1482,24 @@ public abstract class TestHiveMetaStore 
         assertTrue("Able to create table with invalid name: " + invTblName,
             false);
       }
+
+      // create an invalid table which has wrong column type
+      ArrayList<FieldSchema> invColsInvType = new ArrayList<FieldSchema>(2);
+      invColsInvType.add(new FieldSchema("name", 
serdeConstants.STRING_TYPE_NAME, ""));
+      invColsInvType.add(new FieldSchema("income", "xyz", ""));
+      tbl.setTableName(tblName);
+      tbl.getSd().setCols(invColsInvType);
+      boolean failChecker = false;
+      try {
+        client.createTable(tbl);
+      } catch (InvalidObjectException ex) {
+        failChecker = true;
+      }
+      if (!failChecker) {
+        assertTrue("Able to create table with invalid column type: " + 
invTblName,
+            false);
+      }
+
       ArrayList<FieldSchema> cols = new ArrayList<FieldSchema>(2);
       cols.add(new FieldSchema("name", serdeConstants.STRING_TYPE_NAME, ""));
       cols.add(new FieldSchema("income", serdeConstants.INT_TYPE_NAME, ""));
@@ -1561,6 +1579,17 @@ public abstract class TestHiveMetaStore 
         assertEquals("alter table didn't move data correct location", tbl3
             .getSd().getLocation(), tbl2.getSd().getLocation());
       }
+
+      // alter table with invalid column type
+      tbl_pk.getSd().setCols(invColsInvType);
+      failed = false;
+      try {
+        client.alter_table(dbName, tbl2.getTableName(), tbl_pk);
+      } catch (InvalidOperationException ex) {
+        failed = true;
+      }
+      assertTrue("Should not have succeeded in altering column", failed);
+
     } catch (Exception e) {
       System.err.println(StringUtils.stringifyException(e));
       System.err.println("testSimpleTable() failed.");
@@ -1757,7 +1786,7 @@ public abstract class TestHiveMetaStore 
     } catch (TException e) {
       e.printStackTrace();
       assert (false);
-    } 
+    }
     assert (threwException);
   }
 
@@ -2106,7 +2135,7 @@ public abstract class TestHiveMetaStore 
    * at least works correctly.
    */
   public void testSynchronized() throws Exception {
-    int currentNumberOfDbs = client.getAllDatabases().size(); 
+    int currentNumberOfDbs = client.getAllDatabases().size();
 
     IMetaStoreClient synchronizedClient =
       HiveMetaStoreClient.newSynchronizedClient(client);


Reply via email to