You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@sentry.apache.org by pr...@apache.org on 2014/09/06 01:49:17 UTC

git commit: SENTRY-331: Add more granular privileges to the DBModel (Sravya Tirukkovalur via Prasad Mujumdar)

Repository: incubator-sentry
Updated Branches:
  refs/heads/master 416ca0644 -> 05a239dad


SENTRY-331: Add more granular privileges to the DBModel (Sravya Tirukkovalur via Prasad Mujumdar)


Project: http://git-wip-us.apache.org/repos/asf/incubator-sentry/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-sentry/commit/05a239da
Tree: http://git-wip-us.apache.org/repos/asf/incubator-sentry/tree/05a239da
Diff: http://git-wip-us.apache.org/repos/asf/incubator-sentry/diff/05a239da

Branch: refs/heads/master
Commit: 05a239dadf27fd066a9ae1e2fdf961c2d7ee56e1
Parents: 416ca06
Author: Prasad Mujumdar <pr...@cloudera.com>
Authored: Fri Sep 5 16:49:09 2014 -0700
Committer: Prasad Mujumdar <pr...@cloudera.com>
Committed: Fri Sep 5 16:49:09 2014 -0700

----------------------------------------------------------------------
 .../apache/hadoop/hive/SentryHiveConstants.java |   3 +-
 .../hive/ql/exec/SentryGrantRevokeTask.java     |  24 +-
 .../binding/hive/HiveAuthzBindingHook.java      |   4 +
 .../hive/authz/HiveAuthzPrivilegesMap.java      | 179 +++---
 .../binding/hive/authz/SentryConfigTool.java    |   2 +-
 .../sentry/core/model/db/AccessConstants.java   |   6 +
 .../sentry/core/model/db/DBModelAction.java     |   5 +
 .../policy/db/TestDBWildcardPrivilege.java      |  52 ++
 .../thrift/SentryPolicyServiceClient.java       |   8 +-
 .../sentry/tests/e2e/hive/TestOperations.java   | 636 ++++++++++++++-----
 .../metastore/SentryPolicyProviderForDb.java    |   2 +-
 .../e2e/metastore/TestMetastoreEndToEnd.java    |   2 +-
 12 files changed, 664 insertions(+), 259 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/incubator-sentry/blob/05a239da/sentry-binding/sentry-binding-hive/src/main/java/org/apache/hadoop/hive/SentryHiveConstants.java
----------------------------------------------------------------------
diff --git a/sentry-binding/sentry-binding-hive/src/main/java/org/apache/hadoop/hive/SentryHiveConstants.java b/sentry-binding/sentry-binding-hive/src/main/java/org/apache/hadoop/hive/SentryHiveConstants.java
index 49922f9..6f83cc6 100644
--- a/sentry-binding/sentry-binding-hive/src/main/java/org/apache/hadoop/hive/SentryHiveConstants.java
+++ b/sentry-binding/sentry-binding-hive/src/main/java/org/apache/hadoop/hive/SentryHiveConstants.java
@@ -23,7 +23,8 @@ import org.apache.hadoop.hive.ql.security.authorization.PrivilegeType;
 
 public class SentryHiveConstants {
   public static final EnumSet<PrivilegeType> ALLOWED_PRIVS = EnumSet.of(
-      PrivilegeType.ALL, PrivilegeType.SELECT, PrivilegeType.INSERT);
+      PrivilegeType.ALL, PrivilegeType.SELECT, PrivilegeType.INSERT, PrivilegeType.CREATE, PrivilegeType.DROP,
+      PrivilegeType.ALTER_METADATA, PrivilegeType.INDEX, PrivilegeType.LOCK);
 
   public static final String PRIVILEGE_NOT_SUPPORTED = "Sentry does not support privilege: ";
   public static final String COLUMN_PRIVS_NOT_SUPPORTED = "Sentry users should use views to grant privileges on columns";

http://git-wip-us.apache.org/repos/asf/incubator-sentry/blob/05a239da/sentry-binding/sentry-binding-hive/src/main/java/org/apache/hadoop/hive/ql/exec/SentryGrantRevokeTask.java
----------------------------------------------------------------------
diff --git a/sentry-binding/sentry-binding-hive/src/main/java/org/apache/hadoop/hive/ql/exec/SentryGrantRevokeTask.java b/sentry-binding/sentry-binding-hive/src/main/java/org/apache/hadoop/hive/ql/exec/SentryGrantRevokeTask.java
index 0b26806..4f34de6 100644
--- a/sentry-binding/sentry-binding-hive/src/main/java/org/apache/hadoop/hive/ql/exec/SentryGrantRevokeTask.java
+++ b/sentry-binding/sentry-binding-hive/src/main/java/org/apache/hadoop/hive/ql/exec/SentryGrantRevokeTask.java
@@ -536,7 +536,8 @@ public class SentryGrantRevokeTask extends Task<DDLWork> implements Serializable
         for (PrivilegeDesc privDesc : privileges) {
           if (isGrant) {
             if (serverName != null) {
-              sentryClient.grantServerPrivilege(subject, princ.getName(), serverName, grantOption);
+              sentryClient.grantServerPrivilege(subject, princ.getName(), serverName,
+                  toSentryAction(privDesc.getPrivilege().getPriv()), grantOption);
             } else if (uriPath != null) {
               sentryClient.grantURIPrivilege(subject, princ.getName(), server, uriPath, grantOption);
             } else if (tableName == null) {
@@ -570,7 +571,7 @@ public class SentryGrantRevokeTask extends Task<DDLWork> implements Serializable
     }
   }
 
-  private static String toDbSentryAction(PrivilegeType privilegeType) {
+  private static String toDbSentryAction(PrivilegeType privilegeType) throws SentryUserException{
     if (PrivilegeType.ALL.equals(privilegeType)) {
       return AccessConstants.ALL;
     } else {
@@ -578,13 +579,18 @@ public class SentryGrantRevokeTask extends Task<DDLWork> implements Serializable
         return AccessConstants.SELECT;
       } else if (PrivilegeType.INSERT.equals(privilegeType)) {
         return AccessConstants.INSERT;
+      } else if (PrivilegeType.CREATE.equals(privilegeType)){
+        return AccessConstants.CREATE;
+      } else if (PrivilegeType.DROP.equals(privilegeType)){
+        return AccessConstants.DROP;
+      } else if (PrivilegeType.ALTER_METADATA.equals(privilegeType)){
+        return AccessConstants.ALTER;
+      } else if (PrivilegeType.INDEX.equals(privilegeType)){
+        return AccessConstants.INDEX;
+      } else if (PrivilegeType.LOCK.equals(privilegeType)){
+        return AccessConstants.LOCK;
       } else {
-        // Should we throw an Exception here ?
-        // On second thought... I don't think we should..
-        // Earlier, we were sending everything as ALL..
-        // So with the patch, it should default to old
-        // behavior for something other than INSERT or SELECT
-        return AccessConstants.ALL;
+        throw new SentryUserException(privilegeType + " not handled correctly");
       }
     }
   }
@@ -602,7 +608,7 @@ public class SentryGrantRevokeTask extends Task<DDLWork> implements Serializable
     if (PrivilegeType.ALL.equals(privilegeType)) {
       return AccessConstants.ALL;
     } else {
-      return privilegeType.name();
+      return privilegeType.toString();
     }
   }
 

http://git-wip-us.apache.org/repos/asf/incubator-sentry/blob/05a239da/sentry-binding/sentry-binding-hive/src/main/java/org/apache/sentry/binding/hive/HiveAuthzBindingHook.java
----------------------------------------------------------------------
diff --git a/sentry-binding/sentry-binding-hive/src/main/java/org/apache/sentry/binding/hive/HiveAuthzBindingHook.java b/sentry-binding/sentry-binding-hive/src/main/java/org/apache/sentry/binding/hive/HiveAuthzBindingHook.java
index 2df741c..e9c9c0d 100644
--- a/sentry-binding/sentry-binding-hive/src/main/java/org/apache/sentry/binding/hive/HiveAuthzBindingHook.java
+++ b/sentry-binding/sentry-binding-hive/src/main/java/org/apache/sentry/binding/hive/HiveAuthzBindingHook.java
@@ -163,6 +163,10 @@ public class HiveAuthzBindingHook extends AbstractSemanticAnalyzerHook {
         currTab = extractTable((ASTNode)ast.getFirstChildWithType(HiveParser.TOK_TABNAME));
         currDB = extractDatabase((ASTNode) ast.getChild(0));
         break;
+      case HiveParser.TOK_ALTERINDEX_REBUILD:
+        currTab = extractTable((ASTNode)ast.getChild(0)); //type is not TOK_TABNAME
+        currDB = extractDatabase((ASTNode) ast.getChild(0));
+        break;
       case HiveParser.TOK_ALTERTABLE_RENAME:
       case HiveParser.TOK_ALTERTABLE_PROPERTIES:
       case HiveParser.TOK_ALTERTABLE_DROPPARTS:

http://git-wip-us.apache.org/repos/asf/incubator-sentry/blob/05a239da/sentry-binding/sentry-binding-hive/src/main/java/org/apache/sentry/binding/hive/authz/HiveAuthzPrivilegesMap.java
----------------------------------------------------------------------
diff --git a/sentry-binding/sentry-binding-hive/src/main/java/org/apache/sentry/binding/hive/authz/HiveAuthzPrivilegesMap.java b/sentry-binding/sentry-binding-hive/src/main/java/org/apache/sentry/binding/hive/authz/HiveAuthzPrivilegesMap.java
index 9498a28..2f97e30 100644
--- a/sentry-binding/sentry-binding-hive/src/main/java/org/apache/sentry/binding/hive/authz/HiveAuthzPrivilegesMap.java
+++ b/sentry-binding/sentry-binding-hive/src/main/java/org/apache/sentry/binding/hive/authz/HiveAuthzPrivilegesMap.java
@@ -33,27 +33,80 @@ public class HiveAuthzPrivilegesMap {
   private static final Map <HiveExtendedOperation, HiveAuthzPrivileges> hiveAuthzExtendedPrivMap =
     new HashMap<HiveExtendedOperation, HiveAuthzPrivileges>();
   static {
-    HiveAuthzPrivileges tableDDLPrivilege = new HiveAuthzPrivileges.AuthzPrivilegeBuilder().
-        addInputObjectPriviledge(AuthorizableType.Table, EnumSet.of(DBModelAction.ALL)).
+    HiveAuthzPrivileges serverPrivilege = new HiveAuthzPrivileges.AuthzPrivilegeBuilder().
+        addInputObjectPriviledge(AuthorizableType.Server, EnumSet.of(DBModelAction.ALL)).
+        setOperationScope(HiveOperationScope.SERVER).
+        setOperationType(HiveOperationType.DDL).
+        build();
+
+    HiveAuthzPrivileges createServerPrivilege = new HiveAuthzPrivileges.AuthzPrivilegeBuilder().
+        addInputObjectPriviledge(AuthorizableType.Server, EnumSet.of(DBModelAction.CREATE)).
+        setOperationScope(HiveOperationScope.SERVER).
+        setOperationType(HiveOperationType.DDL).
+        build();
+
+    HiveAuthzPrivileges tableCreatePrivilege = new HiveAuthzPrivileges.AuthzPrivilegeBuilder().
+        addInputObjectPriviledge(AuthorizableType.Db, EnumSet.of(DBModelAction.CREATE)).
+        addInputObjectPriviledge(AuthorizableType.URI, EnumSet.of(DBModelAction.ALL)).//TODO: make it optional
+        setOperationScope(HiveOperationScope.DATABASE).
+        setOperationType(HiveOperationType.DDL).
+        build();
+    HiveAuthzPrivileges dropDbPrivilege = new HiveAuthzPrivileges.AuthzPrivilegeBuilder().
+        addInputObjectPriviledge(AuthorizableType.Db, EnumSet.of(DBModelAction.DROP)).
+        setOperationScope(HiveOperationScope.DATABASE).
+        setOperationType(HiveOperationType.DDL).
+        build();
+    HiveAuthzPrivileges alterDbPrivilege = new HiveAuthzPrivileges.AuthzPrivilegeBuilder().
+        addInputObjectPriviledge(AuthorizableType.Db, EnumSet.of(DBModelAction.ALTER)).
+        setOperationScope(HiveOperationScope.DATABASE).
+        setOperationType(HiveOperationType.DDL).
+        build();
+
+    HiveAuthzPrivileges alterTablePrivilege = new HiveAuthzPrivileges.AuthzPrivilegeBuilder().
+        addInputObjectPriviledge(AuthorizableType.Table, EnumSet.of(DBModelAction.ALTER)).
+        setOperationScope(HiveOperationScope.TABLE).
+        setOperationType(HiveOperationType.DDL).
+        build();
+    HiveAuthzPrivileges dropTablePrivilege = new HiveAuthzPrivileges.AuthzPrivilegeBuilder().
+        addInputObjectPriviledge(AuthorizableType.Table, EnumSet.of(DBModelAction.DROP)).
+        setOperationScope(HiveOperationScope.TABLE).
+        setOperationType(HiveOperationType.DDL).
+        build();
+    HiveAuthzPrivileges indexTablePrivilege = new HiveAuthzPrivileges.AuthzPrivilegeBuilder().
+        addInputObjectPriviledge(AuthorizableType.Table, EnumSet.of(DBModelAction.INDEX)).
         setOperationScope(HiveOperationScope.TABLE).
         setOperationType(HiveOperationType.DDL).
         build();
-    HiveAuthzPrivileges tableDDLAndUriPrivilege = new HiveAuthzPrivileges.AuthzPrivilegeBuilder().
-        addInputObjectPriviledge(AuthorizableType.Table, EnumSet.of(DBModelAction.ALL)).
+
+    HiveAuthzPrivileges alterTableAndUriPrivilege = new HiveAuthzPrivileges.AuthzPrivilegeBuilder().
+        addInputObjectPriviledge(AuthorizableType.Table, EnumSet.of(DBModelAction.ALTER)).
         addOutputObjectPriviledge(AuthorizableType.URI, EnumSet.of(DBModelAction.ALL)).
         setOperationScope(HiveOperationScope.TABLE).
         setOperationType(HiveOperationType.DDL).
         build();
-    HiveAuthzPrivileges tableDDLAndOptionalUriPrivilege = new HiveAuthzPrivileges.AuthzPrivilegeBuilder().
-        addInputObjectPriviledge(AuthorizableType.Table, EnumSet.of(DBModelAction.ALL)).
+    HiveAuthzPrivileges addPartitionPrivilege = new HiveAuthzPrivileges.AuthzPrivilegeBuilder().
+        addInputObjectPriviledge(AuthorizableType.Table, EnumSet.of(DBModelAction.ALTER)).
+        //TODO: Uncomment this if we want to make it more restrictive
+        //addInputObjectPriviledge(AuthorizableType.Table, EnumSet.of(DBModelAction.CREATE)).
         addInputObjectPriviledge(AuthorizableType.URI, EnumSet.of(DBModelAction.SELECT)).//TODO: make it optional
-        addOutputObjectPriviledge(AuthorizableType.URI,
-            EnumSet.of(DBModelAction.ALL))
-        .
+        addOutputObjectPriviledge(AuthorizableType.URI, EnumSet.of(DBModelAction.ALL)).
+        setOperationScope(HiveOperationScope.TABLE).
+        setOperationType(HiveOperationType.DDL).
+        build();
+    HiveAuthzPrivileges dropPartitionPrivilege = new HiveAuthzPrivileges.AuthzPrivilegeBuilder().
+        addInputObjectPriviledge(AuthorizableType.Table, EnumSet.of(DBModelAction.ALTER)).
+        addInputObjectPriviledge(AuthorizableType.Table, EnumSet.of(DBModelAction.DROP)).
         setOperationScope(HiveOperationScope.TABLE).
         setOperationType(HiveOperationType.DDL).
         build();
 
+    HiveAuthzPrivileges alterTableRenamePrivilege = new HiveAuthzPrivileges.AuthzPrivilegeBuilder().
+        addInputObjectPriviledge(AuthorizableType.Table, EnumSet.of(DBModelAction.ALTER)).
+        addInputObjectPriviledge(AuthorizableType.Db, EnumSet.of(DBModelAction.CREATE)).
+        setOperationScope(HiveOperationScope.DATABASE).
+        setOperationType(HiveOperationType.DDL).
+        build();
+
     /* Currently Hive treats select/insert/analyze as Query
      * select = select on table
      * insert = insert on table /all on uri
@@ -87,28 +140,15 @@ public class HiveAuthzPrivilegesMap {
         setOperationType(HiveOperationType.INFO).
         build();
 
-    HiveAuthzPrivileges dbDDLPrivilege = new HiveAuthzPrivileges.AuthzPrivilegeBuilder().
-        addInputObjectPriviledge(AuthorizableType.Db, EnumSet.of(DBModelAction.ALL)).
-        setOperationScope(HiveOperationScope.DATABASE).
-        setOperationType(HiveOperationType.DDL).
-        build();
-
-    HiveAuthzPrivileges createTablePrivilege = new HiveAuthzPrivileges.AuthzPrivilegeBuilder().
-        addInputObjectPriviledge(AuthorizableType.Db, EnumSet.of(DBModelAction.ALL)).
-        addInputObjectPriviledge(AuthorizableType.URI, EnumSet.of(DBModelAction.ALL)).//TODO: make it optional
-        setOperationScope(HiveOperationScope.DATABASE).
-        setOperationType(HiveOperationType.DDL).
-        build();
-
     HiveAuthzPrivileges dbImportPrivilege = new HiveAuthzPrivileges.AuthzPrivilegeBuilder().
-        addOutputObjectPriviledge(AuthorizableType.Db, EnumSet.of(DBModelAction.ALL)).
+        addOutputObjectPriviledge(AuthorizableType.Db, EnumSet.of(DBModelAction.CREATE)).
         addInputObjectPriviledge(AuthorizableType.URI, EnumSet.of(DBModelAction.ALL)).
         setOperationScope(HiveOperationScope.DATABASE).
         setOperationType(HiveOperationType.DDL).
         build();
 
     HiveAuthzPrivileges createViewPrivilege = new HiveAuthzPrivileges.AuthzPrivilegeBuilder().
-    addOutputObjectPriviledge(AuthorizableType.Db, EnumSet.of(DBModelAction.ALL)).
+    addOutputObjectPriviledge(AuthorizableType.Db, EnumSet.of(DBModelAction.CREATE)).
     addInputObjectPriviledge(AuthorizableType.Table, EnumSet.of(DBModelAction.SELECT)).
     addInputObjectPriviledge(AuthorizableType.URI, EnumSet.of(DBModelAction.ALL)).//TODO: This should not be required
     setOperationScope(HiveOperationScope.DATABASE).
@@ -126,68 +166,65 @@ public class HiveAuthzPrivilegesMap {
         setOperationScope(HiveOperationScope.TABLE).
         setOperationType(HiveOperationType.DML).
         build();
-    HiveAuthzPrivileges serverPrivilege = new HiveAuthzPrivileges.AuthzPrivilegeBuilder().
-        addInputObjectPriviledge(AuthorizableType.Server, EnumSet.of(DBModelAction.ALL)).
-        setOperationScope(HiveOperationScope.SERVER).
-        setOperationType(HiveOperationType.DDL).
-        build();
-
 
     HiveAuthzPrivileges anyPrivilege = new HiveAuthzPrivileges.AuthzPrivilegeBuilder().
-        addInputObjectPriviledge(AuthorizableType.Table, EnumSet.of(DBModelAction.SELECT, DBModelAction.INSERT)).
+        addInputObjectPriviledge(AuthorizableType.Table, EnumSet.of(DBModelAction.SELECT, DBModelAction.INSERT,
+            DBModelAction.ALTER, DBModelAction.CREATE, DBModelAction.DROP, DBModelAction.DROP,
+            DBModelAction.INDEX, DBModelAction.LOCK)).
         addInputObjectPriviledge(AuthorizableType.URI, EnumSet.of(DBModelAction.ALL)). //TODO: make them ||
         setOperationScope(HiveOperationScope.CONNECT).
         setOperationType(HiveOperationType.QUERY).
         build();
 
-    hiveAuthzStmtPrivMap.put(HiveOperation.CREATEDATABASE, serverPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.DROPDATABASE, dbDDLPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.CREATETABLE, createTablePrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.DROPTABLE, tableDDLPrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.CREATEDATABASE, createServerPrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.DROPDATABASE, dropDbPrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.CREATETABLE, tableCreatePrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERDATABASE, alterDbPrivilege);
+
+    hiveAuthzStmtPrivMap.put(HiveOperation.DROPTABLE, dropTablePrivilege);
     hiveAuthzStmtPrivMap.put(HiveOperation.CREATEVIEW, createViewPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.DROPVIEW, tableDDLPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.CREATEINDEX, tableDDLPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.DROPINDEX, tableDDLPrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.DROPVIEW, dropTablePrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.CREATEINDEX, indexTablePrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.DROPINDEX, indexTablePrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERINDEX_PROPS, indexTablePrivilege);//TODO: Needs test case
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERINDEX_REBUILD, indexTablePrivilege);
 
 
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_RENAME, tableDDLPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_PROPERTIES, tableDDLPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_SERDEPROPERTIES, tableDDLPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_CLUSTER_SORT, tableDDLPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_FILEFORMAT, tableDDLPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_TOUCH, tableDDLPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_PROTECTMODE, tableDDLPrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_PROPERTIES, alterTablePrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_SERDEPROPERTIES, alterTablePrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_CLUSTER_SORT, alterTablePrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_FILEFORMAT, alterTablePrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_TOUCH, alterTablePrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_PROTECTMODE, alterTablePrivilege);
 
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_RENAMECOL, tableDDLPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_ADDCOLS, tableDDLPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_REPLACECOLS, tableDDLPrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_RENAMECOL, alterTablePrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_ADDCOLS, alterTablePrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_REPLACECOLS, alterTablePrivilege);
 
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_ADDPARTS, tableDDLAndOptionalUriPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_RENAMEPART, tableDDLPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_DROPPARTS, tableDDLPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_ARCHIVE, tableDDLPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_UNARCHIVE, tableDDLPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERPARTITION_FILEFORMAT, tableDDLPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERPARTITION_PROTECTMODE, tableDDLPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERPARTITION_SERDEPROPERTIES, tableDDLPrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_RENAMEPART, alterTablePrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_ARCHIVE, alterTablePrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_UNARCHIVE, alterTablePrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERPARTITION_FILEFORMAT, alterTablePrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERPARTITION_PROTECTMODE, alterTablePrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERPARTITION_SERDEPROPERTIES, alterTablePrivilege);
 
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_SERIALIZER, tableDDLPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_MERGEFILES, tableDDLPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_SKEWED, tableDDLPrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_SERIALIZER, alterTablePrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_MERGEFILES, alterTablePrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_SKEWED, alterTablePrivilege);
 
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERPARTITION_SERIALIZER, tableDDLPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERPARTITION_MERGEFILES, tableDDLPrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERPARTITION_SERIALIZER, alterTablePrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERPARTITION_MERGEFILES, alterTablePrivilege);
 
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERINDEX_PROPS, tableDDLPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERINDEX_REBUILD, tableDDLPrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERVIEW_PROPERTIES, alterTablePrivilege);
 
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERVIEW_PROPERTIES, tableDDLPrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_DROPPARTS, dropPartitionPrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_ADDPARTS, addPartitionPrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_RENAME, alterTableRenamePrivilege);
 
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_LOCATION, tableDDLAndUriPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERPARTITION_LOCATION, tableDDLAndUriPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTBLPART_SKEWED_LOCATION, tableDDLAndUriPrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTABLE_LOCATION, alterTableAndUriPrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERPARTITION_LOCATION, alterTableAndUriPrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERTBLPART_SKEWED_LOCATION, alterTableAndUriPrivilege);//TODO: Needs test case
 
-    hiveAuthzStmtPrivMap.put(HiveOperation.ALTERDATABASE, dbDDLPrivilege);
 
     hiveAuthzStmtPrivMap.put(HiveOperation.ANALYZE_TABLE, tableQueryPrivilege);
 
@@ -208,8 +245,8 @@ public class HiveAuthzPrivilegesMap {
     hiveAuthzStmtPrivMap.put(HiveOperation.EXPORT, tableExportPrivilege);
     hiveAuthzStmtPrivMap.put(HiveOperation.IMPORT, dbImportPrivilege);
     hiveAuthzStmtPrivMap.put(HiveOperation.LOAD, tableLoadPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.LOCKTABLE, tableDMLPrivilege);
-    hiveAuthzStmtPrivMap.put(HiveOperation.UNLOCKTABLE, tableDMLPrivilege);
+    hiveAuthzStmtPrivMap.put(HiveOperation.LOCKTABLE, tableDMLPrivilege);//TODO: Needs test case
+    hiveAuthzStmtPrivMap.put(HiveOperation.UNLOCKTABLE, tableDMLPrivilege);//TODO: Needs test case
     // CREATEROLE
     // DROPROLE
     // GRANT_PRIVILEGE
@@ -221,7 +258,7 @@ public class HiveAuthzPrivilegesMap {
     hiveAuthzStmtPrivMap.put(HiveOperation.CREATETABLE_AS_SELECT,
         new HiveAuthzPrivileges.AuthzPrivilegeBuilder().
         addInputObjectPriviledge(AuthorizableType.Table, EnumSet.of(DBModelAction.SELECT)).
-        addOutputObjectPriviledge(AuthorizableType.Db, EnumSet.of(DBModelAction.ALL)).
+        addOutputObjectPriviledge(AuthorizableType.Db, EnumSet.of(DBModelAction.CREATE)).
         setOperationScope(HiveOperationScope.DATABASE).
         setOperationType(HiveOperationType.DDL).
         build());

http://git-wip-us.apache.org/repos/asf/incubator-sentry/blob/05a239da/sentry-binding/sentry-binding-hive/src/main/java/org/apache/sentry/binding/hive/authz/SentryConfigTool.java
----------------------------------------------------------------------
diff --git a/sentry-binding/sentry-binding-hive/src/main/java/org/apache/sentry/binding/hive/authz/SentryConfigTool.java b/sentry-binding/sentry-binding-hive/src/main/java/org/apache/sentry/binding/hive/authz/SentryConfigTool.java
index dcd2b8a..2b978d5 100644
--- a/sentry-binding/sentry-binding-hive/src/main/java/org/apache/sentry/binding/hive/authz/SentryConfigTool.java
+++ b/sentry-binding/sentry-binding-hive/src/main/java/org/apache/sentry/binding/hive/authz/SentryConfigTool.java
@@ -355,7 +355,7 @@ public class SentryConfigTool {
             System.out.println(String.format("GRANT ALL ON SERVER %s TO ROLE %s;",
                 server, roleName));
 
-            client.grantServerPrivilege(requestorUserName, roleName, server);
+            client.grantServerPrivilege(requestorUserName, roleName, server, action);
           } else {
             System.out.println(String.format("No grant for permission %s",
                 permission));

http://git-wip-us.apache.org/repos/asf/incubator-sentry/blob/05a239da/sentry-core/sentry-core-model-db/src/main/java/org/apache/sentry/core/model/db/AccessConstants.java
----------------------------------------------------------------------
diff --git a/sentry-core/sentry-core-model-db/src/main/java/org/apache/sentry/core/model/db/AccessConstants.java b/sentry-core/sentry-core-model-db/src/main/java/org/apache/sentry/core/model/db/AccessConstants.java
index 4e89f68..26007d9 100644
--- a/sentry-core/sentry-core-model-db/src/main/java/org/apache/sentry/core/model/db/AccessConstants.java
+++ b/sentry-core/sentry-core-model-db/src/main/java/org/apache/sentry/core/model/db/AccessConstants.java
@@ -30,6 +30,12 @@ public class AccessConstants {
   public static final String SELECT = "select";
   public static final String INSERT = "insert";
 
+  public static final String ALTER = "alter";
+  public static final String CREATE = "create";
+  public static final String DROP = "drop";
+  public static final String INDEX = "index";
+  public static final String LOCK = "lock";
+
   public static final String ALL_ROLE = "ALL", DEFAULT_ROLE = "DEFAULT", NONE_ROLE = "NONE",
       SUPERUSER_ROLE = "SUPERUSER", PUBLIC_ROLE = "PUBLIC";
   public static final ImmutableSet<String> RESERVED_ROLE_NAMES = ImmutableSet.of(ALL_ROLE,

http://git-wip-us.apache.org/repos/asf/incubator-sentry/blob/05a239da/sentry-core/sentry-core-model-db/src/main/java/org/apache/sentry/core/model/db/DBModelAction.java
----------------------------------------------------------------------
diff --git a/sentry-core/sentry-core-model-db/src/main/java/org/apache/sentry/core/model/db/DBModelAction.java b/sentry-core/sentry-core-model-db/src/main/java/org/apache/sentry/core/model/db/DBModelAction.java
index a4f3a87..209fb89 100644
--- a/sentry-core/sentry-core-model-db/src/main/java/org/apache/sentry/core/model/db/DBModelAction.java
+++ b/sentry-core/sentry-core-model-db/src/main/java/org/apache/sentry/core/model/db/DBModelAction.java
@@ -25,6 +25,11 @@ public enum DBModelAction implements Action {
 
   INSERT(AccessConstants.INSERT),
   SELECT(AccessConstants.SELECT),
+  ALTER(AccessConstants.ALTER),
+  CREATE(AccessConstants.CREATE),
+  DROP(AccessConstants.DROP),
+  INDEX(AccessConstants.INDEX),
+  LOCK(AccessConstants.LOCK),
   ALL(AccessConstants.ALL);
 
   private final String value;

http://git-wip-us.apache.org/repos/asf/incubator-sentry/blob/05a239da/sentry-policy/sentry-policy-db/src/test/java/org/apache/sentry/policy/db/TestDBWildcardPrivilege.java
----------------------------------------------------------------------
diff --git a/sentry-policy/sentry-policy-db/src/test/java/org/apache/sentry/policy/db/TestDBWildcardPrivilege.java b/sentry-policy/sentry-policy-db/src/test/java/org/apache/sentry/policy/db/TestDBWildcardPrivilege.java
index f4862e0..bc1194e 100644
--- a/sentry-policy/sentry-policy-db/src/test/java/org/apache/sentry/policy/db/TestDBWildcardPrivilege.java
+++ b/sentry-policy/sentry-policy-db/src/test/java/org/apache/sentry/policy/db/TestDBWildcardPrivilege.java
@@ -276,6 +276,58 @@ public class TestDBWildcardPrivilege {
     assertTrue(DBWildcardPrivilege.impliesURI("hdfs://namenode:8020/path/",
         "hdfs://namenode:8020/path/FooBar"));
   }
+  @Test
+  public void testActionHierarchy() throws Exception {
+    String dbName = "db1";
+    DBWildcardPrivilege dbAll = create(new KeyValue("server", "server1"),
+        new KeyValue("db", dbName), new KeyValue("action", "ALL"));
+
+    DBWildcardPrivilege dbSelect = create(new KeyValue("server", "server1"),
+        new KeyValue("db", dbName), new KeyValue("action", "SELECT"));
+    DBWildcardPrivilege dbInsert = create(new KeyValue("server", "server1"),
+        new KeyValue("db", dbName), new KeyValue("action", "INSERT"));
+    DBWildcardPrivilege dbAlter = create(new KeyValue("server", "server1"),
+        new KeyValue("db", dbName), new KeyValue("action", "ALTER"));
+    DBWildcardPrivilege dbCreate = create(new KeyValue("server", "server1"),
+        new KeyValue("db", dbName), new KeyValue("action", "CREATE"));
+    DBWildcardPrivilege dbDrop = create(new KeyValue("server", "server1"),
+        new KeyValue("db", dbName), new KeyValue("action", "DROP"));
+    DBWildcardPrivilege dbIndex = create(new KeyValue("server", "server1"),
+        new KeyValue("db", dbName), new KeyValue("action", "INDEX"));
+    DBWildcardPrivilege dbLock = create(new KeyValue("server", "server1"),
+        new KeyValue("db", dbName), new KeyValue("action", "LOCK"));
+
+    assertTrue(dbAll.implies(dbSelect));
+    assertTrue(dbAll.implies(dbInsert));
+    assertTrue(dbAll.implies(dbAlter));
+    assertTrue(dbAll.implies(dbCreate));
+    assertTrue(dbAll.implies(dbDrop));
+    assertTrue(dbAll.implies(dbIndex));
+    assertTrue(dbAll.implies(dbLock));
+
+    dbAll = create(new KeyValue("server", "server1"),
+        new KeyValue("db", dbName), new KeyValue("action", "*"));
+
+    assertTrue(dbAll.implies(dbSelect));
+    assertTrue(dbAll.implies(dbInsert));
+    assertTrue(dbAll.implies(dbAlter));
+    assertTrue(dbAll.implies(dbCreate));
+    assertTrue(dbAll.implies(dbDrop));
+    assertTrue(dbAll.implies(dbIndex));
+    assertTrue(dbAll.implies(dbLock));
+
+    dbAll = create(new KeyValue("server", "server1"),
+        new KeyValue("db", dbName));
+
+    assertTrue(dbAll.implies(dbSelect));
+    assertTrue(dbAll.implies(dbInsert));
+    assertTrue(dbAll.implies(dbAlter));
+    assertTrue(dbAll.implies(dbCreate));
+    assertTrue(dbAll.implies(dbDrop));
+    assertTrue(dbAll.implies(dbIndex));
+    assertTrue(dbAll.implies(dbLock));
+
+  }
   static DBWildcardPrivilege create(KeyValue... keyValues) {
     return create(AUTHORIZABLE_JOINER.join(keyValues));
 

http://git-wip-us.apache.org/repos/asf/incubator-sentry/blob/05a239da/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/service/thrift/SentryPolicyServiceClient.java
----------------------------------------------------------------------
diff --git a/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/service/thrift/SentryPolicyServiceClient.java b/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/service/thrift/SentryPolicyServiceClient.java
index d4c5806..6895927 100644
--- a/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/service/thrift/SentryPolicyServiceClient.java
+++ b/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/service/thrift/SentryPolicyServiceClient.java
@@ -289,17 +289,17 @@ public class SentryPolicyServiceClient {
   }
 
   public void grantServerPrivilege(String requestorUserName,
-      String roleName, String server)
+      String roleName, String server, String action)
   throws SentryUserException {
     grantPrivilege(requestorUserName, roleName,
-        PrivilegeScope.SERVER, server, null, null, null, AccessConstants.ALL);
+        PrivilegeScope.SERVER, server, null, null, null, action);
   }
 
   public void grantServerPrivilege(String requestorUserName,
-      String roleName, String server, Boolean grantOption)
+      String roleName, String server, String action, Boolean grantOption)
   throws SentryUserException {
     grantPrivilege(requestorUserName, roleName,
-        PrivilegeScope.SERVER, server, null, null, null, AccessConstants.ALL, grantOption);
+        PrivilegeScope.SERVER, server, null, null, null, action, grantOption);
   }
 
   public void grantDatabasePrivilege(String requestorUserName,

http://git-wip-us.apache.org/repos/asf/incubator-sentry/blob/05a239da/sentry-tests/sentry-tests-hive/src/test/java/org/apache/sentry/tests/e2e/hive/TestOperations.java
----------------------------------------------------------------------
diff --git a/sentry-tests/sentry-tests-hive/src/test/java/org/apache/sentry/tests/e2e/hive/TestOperations.java b/sentry-tests/sentry-tests-hive/src/test/java/org/apache/sentry/tests/e2e/hive/TestOperations.java
index 30cbb0d..c59b2db 100644
--- a/sentry-tests/sentry-tests-hive/src/test/java/org/apache/sentry/tests/e2e/hive/TestOperations.java
+++ b/sentry-tests/sentry-tests-hive/src/test/java/org/apache/sentry/tests/e2e/hive/TestOperations.java
@@ -27,8 +27,9 @@ import java.util.HashMap;
 import java.util.Map;
 
 import org.apache.sentry.provider.file.PolicyFile;
-import org.apache.sentry.tests.e2e.hive.hiveserver.HiveServerFactory;
+import static org.junit.Assert.assertTrue;
 import org.junit.Before;
+import org.junit.Ignore;
 import org.junit.Test;
 
 import com.google.common.io.Resources;
@@ -40,13 +41,22 @@ public class TestOperations extends AbstractTestWithStaticConfiguration {
   static Map<String, String> privileges = new HashMap<String, String>();
   static {
     privileges.put("all_server", "server=server1->action=all");
+    privileges.put("create_server", "server=server1->action=create");
     privileges.put("all_db1", "server=server1->db=" + DB1 + "->action=all");
     privileges.put("select_db1", "server=server1->db=" + DB1 + "->action=select");
     privileges.put("insert_db1", "server=server1->db=" + DB1 + "->action=insert");
-    privileges.put("all_db2", "server=server1->db=" + DB2 + "->action=all");
+    privileges.put("create_db1", "server=server1->db=" + DB1 + "->action=create");
+    privileges.put("drop_db1", "server=server1->db=" + DB1 + "->action=drop");
+    privileges.put("alter_db1", "server=server1->db=" + DB1 + "->action=alter");
+    privileges.put("create_db2", "server=server1->db=" + DB2 + "->action=create");
+
     privileges.put("all_db1_tb1", "server=server1->db=" + DB1 + "->table=tb1->action=all");
     privileges.put("select_db1_tb1", "server=server1->db=" + DB1 + "->table=tb1->action=select");
     privileges.put("insert_db1_tb1", "server=server1->db=" + DB1 + "->table=tb1->action=insert");
+    privileges.put("alter_db1_tb1", "server=server1->db=" + DB1 + "->table=tb1->action=alter");
+    privileges.put("index_db1_tb1", "server=server1->db=" + DB1 + "->table=tb1->action=index");
+    privileges.put("lock_db1_tb1", "server=server1->db=" + DB1 + "->table=tb1->action=lock");
+    privileges.put("drop_db1_tb1", "server=server1->db=" + DB1 + "->table=tb1->action=drop");
     privileges.put("insert_db2_tb2", "server=server1->db=" + DB2 + "->table=tb2->action=insert");
     privileges.put("select_db1_view1", "server=server1->db=" + DB1 + "->table=view1->action=select");
 
@@ -90,226 +100,202 @@ public class TestOperations extends AbstractTestWithStaticConfiguration {
     connection.close();
   }
 
-  /* Test all operations that require all on Database alone
-  1. Create table : HiveOperation.CREATETABLE
-  2. Alter database : HiveOperation.ALTERDATABASE
-  3. Drop database : HiveOperation.DROPDATABASE
+  /* Test all operations that require create on Server
+  1. Create database : HiveOperation.CREATEDATABASE
    */
   @Test
-  public void testAllOnDatabase() throws Exception{
-    adminCreate(DB1, null);
+  public void testCreateOnServer() throws Exception{
     policyFile
-        .addPermissionsToRole("all_db1", privileges.get("all_db1"))
-        .addRolesToGroup(USERGROUP1, "all_db1");
+        .addPermissionsToRole("create_server", privileges.get("create_server"))
+        .addRolesToGroup(USERGROUP1, "create_server");
 
     writePolicyFile(policyFile);
 
     Connection connection = context.createConnection(USER1_1);
     Statement statement = context.createStatement(connection);
-    statement.execute("CREATE TABLE " + DB1 + ".tb1(a int)");
-    statement.execute("ALTER DATABASE " + DB1 + " SET DBPROPERTIES ('comment'='comment')");
-    statement.execute("DROP database " + DB1 + " cascade");
+    statement.execute("Create database " + DB2);
     statement.close();
     connection.close();
 
     //Negative case
-    adminCreate(DB1, null);
     policyFile
-        .addPermissionsToRole("select_db1", privileges.get("select_db1"))
-        .addRolesToGroup(USERGROUP2, "select_db1");
+        .addPermissionsToRole("create_db1", privileges.get("create_db1"))
+        .addRolesToGroup(USERGROUP2, "create_db1");
     writePolicyFile(policyFile);
 
     connection = context.createConnection(USER2_1);
     statement = context.createStatement(connection);
-    context.assertSentrySemanticException(statement, "CREATE TABLE " + DB1 + ".tb1(a int)", semanticException);
-    context.assertSentrySemanticException(statement, "ALTER DATABASE " + DB1 + " SET DBPROPERTIES ('comment'='comment')", semanticException);
-    context.assertSentrySemanticException(statement, "DROP database " + DB1 + " cascade", semanticException);
+    context.assertSentrySemanticException(statement, "CREATE database " + DB1, semanticException);
     statement.close();
     connection.close();
 
   }
-  /* SELECT/INSERT on DATABASE
-   1. HiveOperation.DESCDATABASE
-   */
+
+  /* Test all operations that require create on Database alone
+  1. Create table : HiveOperation.CREATETABLE
+  */
   @Test
-  public void testDescDB() throws Exception {
+  public void testCreateOnDatabase() throws Exception{
     adminCreate(DB1, null);
     policyFile
-        .addPermissionsToRole("select_db1", privileges.get("select_db1"))
-        .addPermissionsToRole("insert_db1", privileges.get("insert_db1"))
-        .addRolesToGroup(USERGROUP1, "select_db1")
-        .addRolesToGroup(USERGROUP2, "insert_db1");
+        .addPermissionsToRole("create_db1", privileges.get("create_db1"))
+        .addPermissionsToRole("all_db1", privileges.get("all_db1"))
+        .addRolesToGroup(USERGROUP1, "create_db1")
+        .addRolesToGroup(USERGROUP2, "all_db1");
+
     writePolicyFile(policyFile);
 
     Connection connection = context.createConnection(USER1_1);
     Statement statement = context.createStatement(connection);
-    statement.execute("describe database " + DB1);
+    statement.execute("CREATE TABLE " + DB1 + ".tb2(a int)");
     statement.close();
     connection.close();
 
     connection = context.createConnection(USER2_1);
     statement = context.createStatement(connection);
-    statement.execute("describe database " + DB1);
+    statement.execute("CREATE TABLE " + DB1 + ".tb3(a int)");
+
     statement.close();
     connection.close();
 
     //Negative case
     policyFile
-        .addPermissionsToRole("all_db1_tb1", privileges.get("all_db1_tb1"))
+        .addPermissionsToRole("all_db1_tb1", privileges.get("select_db1"))
         .addRolesToGroup(USERGROUP3, "all_db1_tb1");
     writePolicyFile(policyFile);
+
     connection = context.createConnection(USER3_1);
     statement = context.createStatement(connection);
-    context.assertSentrySemanticException(statement, "describe database " + DB1, semanticException);
+    context.assertSentrySemanticException(statement, "CREATE TABLE " + DB1 + ".tb1(a int)", semanticException);
     statement.close();
     connection.close();
-
   }
 
-  private void assertSemanticException(Statement stmt, String command) throws SQLException{
-    context.assertSentrySemanticException(stmt,command, semanticException);
-  }
-  /* Test all operations that require all on table alone
-  1. Create index : HiveOperation.CREATEINDEX
-  2. Drop index : HiveOperation.DROPINDEX
-  3. Alter table add partition : HiveOperation.ALTERTABLE_ADDPARTS
-  4. HiveOperation.ALTERTABLE_PROPERTIES
-  5. HiveOperation.ALTERTABLE_SERDEPROPERTIES
-  6. HiveOperation.ALTERTABLE_CLUSTER_SORT
-  7. HiveOperation.ALTERTABLE_TOUCH
-  8. HiveOperation.ALTERTABLE_PROTECTMODE
-  9. HiveOperation.ALTERTABLE_FILEFORMAT
-  10. HiveOperation.ALTERTABLE_RENAMEPART
-  11. HiveOperation.ALTERPARTITION_SERDEPROPERTIES
-  12. TODO: archive partition
-  13. TODO: unarchive partition
-  14. HiveOperation.ALTERPARTITION_FILEFORMAT
-  15. TODO: partition touch (is it same as  HiveOperation.ALTERTABLE_TOUCH?)
-  16. HiveOperation.ALTERPARTITION_PROTECTMODE
-  17. HiveOperation.ALTERTABLE_DROPPARTS
-  18. HiveOperation.ALTERTABLE_RENAMECOL
-  19. HiveOperation.ALTERTABLE_ADDCOLS
-  20. HiveOperation.ALTERTABLE_REPLACECOLS
-  21. TODO: HiveOperation.ALTERVIEW_PROPERTIES
-  22. HiveOperation.CREATEINDEX
-  23. TODO: HiveOperation.ALTERINDEX_REBUILD
-  21. HiveOperation.ALTERTABLE_RENAME
-  22. HiveOperation.DROPTABLE
-  23. TODO: HiveOperation.ALTERTABLE_SERIALIZER
-  24. TODO: HiveOperation.ALTERPARTITION_SERIALIZER
-  25. TODO: HiveOperation.ALTERINDEX_PROPS
+  /* Test all operations that require drop on Database alone
+  1. Drop database : HiveOperation.DROPDATABASE
   */
   @Test
-  public void testAllOnTable() throws Exception{
-    adminCreate(DB1, tableName, true);
+  public void testDropOnDatabase() throws Exception{
+    adminCreate(DB1, null);
     policyFile
-        .addPermissionsToRole("all_db1_tb1", privileges.get("all_db1_tb1"))
-        .addRolesToGroup(USERGROUP1, "all_db1_tb1")
-        .addPermissionsToRole("insert_db1_tb1", privileges.get("insert_db1_tb1"))
-        .addRolesToGroup(USERGROUP2, "insert_db1_tb1");
+        .addPermissionsToRole("drop_db1", privileges.get("drop_db1"))
+        .addRolesToGroup(USERGROUP1, "drop_db1");
+
     writePolicyFile(policyFile);
 
-    Connection connection;
-    Statement statement;
-    //Negative test cases
-    connection = context.createConnection(USER2_1);
-    statement = context.createStatement(connection);
-    statement.execute("Use " + DB1);
-    assertSemanticException(statement, "CREATE INDEX table01_index ON TABLE tb1 (a) AS 'COMPACT' WITH DEFERRED REBUILD");
-    assertSemanticException(statement, "DROP INDEX table01_index ON tb1");
-    assertSemanticException(statement, "ALTER TABLE tb1 ADD IF NOT EXISTS PARTITION (b = '1') ");
-    assertSemanticException(statement, "ALTER TABLE tb1 SET TBLPROPERTIES ('comment' = 'new_comment')");
-    assertSemanticException(statement, "ALTER TABLE tb1 SET SERDEPROPERTIES ('field.delim' = ',')");
-    assertSemanticException(statement, "ALTER TABLE tb1 CLUSTERED BY (a) SORTED BY (a) INTO 1 BUCKETS");
-    assertSemanticException(statement, "ALTER TABLE tb1 TOUCH");
-    assertSemanticException(statement, "ALTER TABLE tb1 ENABLE NO_DROP");
-    assertSemanticException(statement, "ALTER TABLE tb1 DISABLE OFFLINE");
-    assertSemanticException(statement, "ALTER TABLE tb1 SET FILEFORMAT RCFILE");
+    Connection connection = context.createConnection(USER1_1);
+    Statement statement = context.createStatement(connection);
+    statement.execute("DROP DATABASE " + DB1);
+    statement.close();
+    connection.close();
 
-    //Setup
-    connection = context.createConnection(USER1_1);
-    statement = context.createStatement(connection);
-    statement.execute("Use " + DB1);
-    statement.execute("ALTER TABLE tb1 ADD IF NOT EXISTS PARTITION (b = '10') ");
+    policyFile
+        .addPermissionsToRole("all_db1", privileges.get("all_db1"))
+        .addRolesToGroup(USERGROUP2, "all_db1");
+    writePolicyFile(policyFile);
+
+    adminCreate(DB1, null);
 
-    //Negative test cases
     connection = context.createConnection(USER2_1);
     statement = context.createStatement(connection);
-    statement.execute("Use " + DB1);
-    assertSemanticException(statement, "ALTER TABLE tb1 PARTITION (b = 10) RENAME TO PARTITION (b = 2)");
-    assertSemanticException(statement, "ALTER TABLE tb1 PARTITION (b = 10) SET SERDEPROPERTIES ('field.delim' = ',')");
-    //assertSemanticException(statement, "ALTER TABLE tb1 ARCHIVE PARTITION (b = 2)");
-    //assertSemanticException(statement, "ALTER TABLE tb1 UNARCHIVE PARTITION (b = 2)");
-    assertSemanticException(statement, "ALTER TABLE tb1 PARTITION (b = 10) SET FILEFORMAT RCFILE");
-    assertSemanticException(statement, "ALTER TABLE tb1 TOUCH PARTITION (b = 10)");
-    assertSemanticException(statement, "ALTER TABLE tb1 PARTITION (b = 10) DISABLE NO_DROP");
-    assertSemanticException(statement, "ALTER TABLE tb1 PARTITION (b = 10) DISABLE OFFLINE");
-    assertSemanticException(statement, "ALTER TABLE tb1 DROP PARTITION (b = 10)");
+    statement.execute("DROP DATABASE " + DB1);
 
-    assertSemanticException(statement, "ALTER TABLE tb1 CHANGE COLUMN a c int");
-    assertSemanticException(statement, "ALTER TABLE tb1 ADD COLUMNS (a int)");
-    // TODO: fix alter table replace column testcase for Hive 0.13
-    // assertSemanticException(statement,
-    // "ALTER TABLE tb1 REPLACE COLUMNS (a int, c int)");
+    statement.close();
+    connection.close();
 
-    //assertSemanticException(statement, "ALTER VIEW view1 SET TBLPROPERTIES ('comment' = 'new_comment')");
+    //Negative case
+    adminCreate(DB1, null);
+    policyFile
+        .addPermissionsToRole("select_db1", privileges.get("select_db1"))
+        .addRolesToGroup(USERGROUP3, "select_db1");
+    writePolicyFile(policyFile);
 
-    assertSemanticException(statement, "CREATE INDEX tb1_index ON TABLE tb1 (a) AS 'COMPACT' WITH DEFERRED REBUILD");
-    //assertSemanticException(statement, "ALTER INDEX tb1_index ON tb1 REBUILD");
-    assertSemanticException(statement, "ALTER TABLE tb1 RENAME TO tb2");
+    connection = context.createConnection(USER3_1);
+    statement = context.createStatement(connection);
+    context.assertSentrySemanticException(statement, "drop database " + DB1, semanticException);
+    statement.close();
+    connection.close();
+  }
 
-    assertSemanticException(statement, "DROP TABLE " + DB1 + ".tb1");
+  /* Test all operations that require alter on Database alone
+  1. Alter database : HiveOperation.ALTERDATABASE
+   */
+  @Test
+  public void testAlterOnDatabase() throws Exception{
+    adminCreate(DB1, null);
+    policyFile
+        .addPermissionsToRole("alter_db1", privileges.get("alter_db1"))
+        .addPermissionsToRole("all_db1", privileges.get("all_db1"))
+        .addRolesToGroup(USERGROUP2, "all_db1")
+        .addRolesToGroup(USERGROUP1, "alter_db1");
+    writePolicyFile(policyFile);
 
-    //Positive cases
-    connection = context.createConnection(USER1_1);
+    Connection connection = context.createConnection(USER1_1);
+    Statement statement = context.createStatement(connection);
+    statement.execute("ALTER DATABASE " + DB1 + " SET DBPROPERTIES ('comment'='comment')");
+
+    connection = context.createConnection(USER2_1);
     statement = context.createStatement(connection);
-    statement.execute("Use " + DB1);
-    statement.execute("CREATE INDEX table01_index ON TABLE tb1 (a) AS 'COMPACT' WITH DEFERRED REBUILD");
-    statement.execute("DROP INDEX table01_index ON tb1");
-    statement.execute("ALTER TABLE tb1 ADD IF NOT EXISTS PARTITION (b = '1') ");
-    statement.execute("ALTER TABLE tb1 SET TBLPROPERTIES ('comment' = 'new_comment')");
-    statement.execute("ALTER TABLE tb1 SET SERDEPROPERTIES ('field.delim' = ',')");
-    statement.execute("ALTER TABLE tb1 CLUSTERED BY (a) SORTED BY (a) INTO 1 BUCKETS");
-    statement.execute("ALTER TABLE tb1 TOUCH");
-    statement.execute("ALTER TABLE tb1 ENABLE NO_DROP");
-    statement.execute("ALTER TABLE tb1 DISABLE NO_DROP");
-    statement.execute("ALTER TABLE tb1 DISABLE OFFLINE");
-    statement.execute("ALTER TABLE tb1 SET FILEFORMAT RCFILE");
+    statement.execute("ALTER DATABASE " + DB1 + " SET DBPROPERTIES ('comment'='comment')");
+    statement.close();
+    connection.close();
 
-    statement.execute("ALTER TABLE tb1 PARTITION (b = 1) RENAME TO PARTITION (b = 2)");
-    statement.execute("ALTER TABLE tb1 PARTITION (b = 2) SET SERDEPROPERTIES ('field.delim' = ',')");
-    //statement.execute("ALTER TABLE tb1 ARCHIVE PARTITION (b = 2)");
-    //statement.execute("ALTER TABLE tb1 UNARCHIVE PARTITION (b = 2)");
-    statement.execute("ALTER TABLE tb1 PARTITION (b = 2) SET FILEFORMAT RCFILE");
-    statement.execute("ALTER TABLE tb1 TOUCH PARTITION (b = 2)");
-    statement.execute("ALTER TABLE tb1 PARTITION (b = 2) DISABLE NO_DROP");
-    statement.execute("ALTER TABLE tb1 PARTITION (b = 2) DISABLE OFFLINE");
-    statement.execute("ALTER TABLE tb1 DROP PARTITION (b = 2)");
+    //Negative case
+    adminCreate(DB1, null);
+    policyFile
+        .addPermissionsToRole("select_db1", privileges.get("select_db1"))
+        .addRolesToGroup(USERGROUP3, "select_db1");
+    writePolicyFile(policyFile);
 
-    statement.execute("ALTER TABLE tb1 CHANGE COLUMN a c int");
-    statement.execute("ALTER TABLE tb1 ADD COLUMNS (a int)");
-    // TODO: fix alter table replace column testcase for Hive 0.13
-    // statement.execute("ALTER TABLE tb1 REPLACE COLUMNS (a int, c int)");
+    connection = context.createConnection(USER3_1);
+    statement = context.createStatement(connection);
+    context.assertSentrySemanticException(statement, "ALTER DATABASE " + DB1 + " SET DBPROPERTIES ('comment'='comment')", semanticException);
+    statement.close();
+    connection.close();
+  }
 
-    //statement.execute("ALTER VIEW view1 SET TBLPROPERTIES ('comment' = 'new_comment')");
+  /* SELECT/INSERT on DATABASE
+   1. HiveOperation.DESCDATABASE
+   */
+  @Test
+  public void testDescDB() throws Exception {
+    adminCreate(DB1, null);
+    policyFile
+        .addPermissionsToRole("select_db1", privileges.get("select_db1"))
+        .addPermissionsToRole("insert_db1", privileges.get("insert_db1"))
+        .addRolesToGroup(USERGROUP1, "select_db1")
+        .addRolesToGroup(USERGROUP2, "insert_db1");
+    writePolicyFile(policyFile);
 
-    statement.execute("CREATE INDEX tb1_index ON TABLE tb1 (a) AS 'COMPACT' WITH DEFERRED REBUILD");
-    //statement.execute("ALTER INDEX tb1_index ON tb1 REBUILD");
-    statement.execute("ALTER TABLE tb1 RENAME TO tb2");
+    Connection connection = context.createConnection(USER1_1);
+    Statement statement = context.createStatement(connection);
+    statement.execute("describe database " + DB1);
+    statement.close();
+    connection.close();
 
-    //Drop of the new tablename works only when Hive meta store syncs the alters with the sentry privileges.
-    //This is currently not set for pseudo cluster runs
-    if( hiveServer2Type.equals(HiveServerFactory.HiveServer2Type.UnmanagedHiveServer2)) {
-      statement.execute("DROP TABLE " + DB1 + ".tb2");
-    } else {
-      statement.execute("DROP TABLE " + DB1 + ".tb1");
-    }
+    connection = context.createConnection(USER2_1);
+    statement = context.createStatement(connection);
+    statement.execute("describe database " + DB1);
+    statement.close();
+    connection.close();
 
+    //Negative case
+    policyFile
+        .addPermissionsToRole("all_db1_tb1", privileges.get("all_db1_tb1"))
+        .addRolesToGroup(USERGROUP3, "all_db1_tb1");
+    writePolicyFile(policyFile);
+    connection = context.createConnection(USER3_1);
+    statement = context.createStatement(connection);
+    context.assertSentrySemanticException(statement, "describe database " + DB1, semanticException);
     statement.close();
     connection.close();
 
   }
 
+  private void assertSemanticException(Statement stmt, String command) throws SQLException{
+    context.assertSentrySemanticException(stmt,command, semanticException);
+  }
+
   /*
   1. Analyze table (HiveOperation.QUERY) : select + insert on table
    */
@@ -428,29 +414,307 @@ public class TestOperations extends AbstractTestWithStaticConfiguration {
     connection.close();
   }
 
-  /* Test all operations which require all on table + all on URI
+  /* Test all operations that require alter on table
+  1. HiveOperation.ALTERTABLE_PROPERTIES
+  2. HiveOperation.ALTERTABLE_SERDEPROPERTIES
+  3. HiveOperation.ALTERTABLE_CLUSTER_SORT
+  4. HiveOperation.ALTERTABLE_TOUCH
+  5. HiveOperation.ALTERTABLE_PROTECTMODE
+  6. HiveOperation.ALTERTABLE_FILEFORMAT
+  7. HiveOperation.ALTERTABLE_RENAMEPART
+  8. HiveOperation.ALTERPARTITION_SERDEPROPERTIES
+  9. TODO: archive partition
+  10. TODO: unarchive partition
+  11. HiveOperation.ALTERPARTITION_FILEFORMAT
+  12. TODO: partition touch (is it same as  HiveOperation.ALTERTABLE_TOUCH?)
+  13. HiveOperation.ALTERPARTITION_PROTECTMODE
+  14. HiveOperation.ALTERTABLE_RENAMECOL
+  15. HiveOperation.ALTERTABLE_ADDCOLS
+  16. HiveOperation.ALTERTABLE_REPLACECOLS
+  17. TODO: HiveOperation.ALTERVIEW_PROPERTIES
+  18. TODO: HiveOperation.ALTERTABLE_SERIALIZER
+  19. TODO: HiveOperation.ALTERPARTITION_SERIALIZER
+   */
+  @Test
+  public void testAlterTable() throws Exception {
+    adminCreate(DB1, tableName, true);
+    policyFile
+        .addPermissionsToRole("alter_db1_tb1", privileges.get("alter_db1_tb1"))
+        .addRolesToGroup(USERGROUP1, "alter_db1_tb1")
+        .addPermissionsToRole("insert_db1_tb1", privileges.get("insert_db1_tb1"))
+        .addRolesToGroup(USERGROUP2, "insert_db1_tb1");
+    writePolicyFile(policyFile);
+
+    Connection connection;
+    Statement statement;
+    //Setup
+    connection = context.createConnection(ADMIN1);
+    statement = context.createStatement(connection);
+    statement.execute("Use " + DB1);
+    statement.execute("ALTER TABLE tb1 ADD IF NOT EXISTS PARTITION (b = '10') ");
+    statement.execute("ALTER TABLE tb1 ADD IF NOT EXISTS PARTITION (b = '1') ");
+
+    //Negative test cases
+    connection = context.createConnection(USER2_1);
+    statement = context.createStatement(connection);
+    statement.execute("Use " + DB1);
+    assertSemanticException(statement, "ALTER TABLE tb1 SET TBLPROPERTIES ('comment' = 'new_comment')");
+    assertSemanticException(statement, "ALTER TABLE tb1 SET SERDEPROPERTIES ('field.delim' = ',')");
+    assertSemanticException(statement, "ALTER TABLE tb1 CLUSTERED BY (a) SORTED BY (a) INTO 1 BUCKETS");
+    assertSemanticException(statement, "ALTER TABLE tb1 TOUCH");
+    assertSemanticException(statement, "ALTER TABLE tb1 ENABLE NO_DROP");
+    assertSemanticException(statement, "ALTER TABLE tb1 DISABLE OFFLINE");
+    assertSemanticException(statement, "ALTER TABLE tb1 SET FILEFORMAT RCFILE");
+
+    assertSemanticException(statement, "ALTER TABLE tb1 PARTITION (b = 10) RENAME TO PARTITION (b = 2)");
+    assertSemanticException(statement, "ALTER TABLE tb1 PARTITION (b = 10) SET SERDEPROPERTIES ('field.delim' = ',')");
+    //assertSemanticException(statement, "ALTER TABLE tb1 ARCHIVE PARTITION (b = 2)");
+    //assertSemanticException(statement, "ALTER TABLE tb1 UNARCHIVE PARTITION (b = 2)");
+    assertSemanticException(statement, "ALTER TABLE tb1 PARTITION (b = 10) SET FILEFORMAT RCFILE");
+    assertSemanticException(statement, "ALTER TABLE tb1 TOUCH PARTITION (b = 10)");
+    assertSemanticException(statement, "ALTER TABLE tb1 PARTITION (b = 10) DISABLE NO_DROP");
+    assertSemanticException(statement, "ALTER TABLE tb1 PARTITION (b = 10) DISABLE OFFLINE");
+
+    assertSemanticException(statement, "ALTER TABLE tb1 CHANGE COLUMN a c int");
+    assertSemanticException(statement, "ALTER TABLE tb1 ADD COLUMNS (a int)");
+    assertSemanticException(statement, "ALTER TABLE tb1 REPLACE COLUMNS (a int, c int)");
+
+    //assertSemanticException(statement, "ALTER VIEW view1 SET TBLPROPERTIES ('comment' = 'new_comment')");
+
+
+    statement.close();
+    connection.close();
+
+    //Positive cases
+    connection = context.createConnection(USER1_1);
+    statement = context.createStatement(connection);
+    statement.execute("Use " + DB1);
+    statement.execute("ALTER TABLE tb1 SET TBLPROPERTIES ('comment' = 'new_comment')");
+    statement.execute("ALTER TABLE tb1 SET SERDEPROPERTIES ('field.delim' = ',')");
+    statement.execute("ALTER TABLE tb1 CLUSTERED BY (a) SORTED BY (a) INTO 1 BUCKETS");
+    statement.execute("ALTER TABLE tb1 TOUCH");
+    statement.execute("ALTER TABLE tb1 ENABLE NO_DROP");
+    statement.execute("ALTER TABLE tb1 DISABLE OFFLINE");
+    statement.execute("ALTER TABLE tb1 SET FILEFORMAT RCFILE");
+
+    statement.execute("ALTER TABLE tb1 PARTITION (b = 1) RENAME TO PARTITION (b = 2)");
+    statement.execute("ALTER TABLE tb1 PARTITION (b = 2) SET SERDEPROPERTIES ('field.delim' = ',')");
+    //statement.execute("ALTER TABLE tb1 ARCHIVE PARTITION (b = 2)");
+    //statement.execute("ALTER TABLE tb1 UNARCHIVE PARTITION (b = 2)");
+    statement.execute("ALTER TABLE tb1 PARTITION (b = 2) SET FILEFORMAT RCFILE");
+    statement.execute("ALTER TABLE tb1 TOUCH PARTITION (b = 2)");
+    statement.execute("ALTER TABLE tb1 PARTITION (b = 2) DISABLE NO_DROP");
+    statement.execute("ALTER TABLE tb1 PARTITION (b = 2) DISABLE OFFLINE");
+
+    statement.execute("ALTER TABLE tb1 CHANGE COLUMN a c int");
+    statement.execute("ALTER TABLE tb1 ADD COLUMNS (a int)");
+    statement.execute("ALTER TABLE tb1 REPLACE COLUMNS (a int, c int)");
+
+    //statement.execute("ALTER VIEW view1 SET TBLPROPERTIES ('comment' = 'new_comment')");
+
+    statement.close();
+    connection.close();
+  }
+
+  /* Test all operations that require index on table alone
+  1. Create index : HiveOperation.CREATEINDEX
+  2. Drop index : HiveOperation.DROPINDEX
+  3. HiveOperation.ALTERINDEX_REBUILD
+  4. TODO: HiveOperation.ALTERINDEX_PROPS
+  */
+  @Test
+  public void testIndexTable() throws Exception {
+    adminCreate(DB1, tableName, true);
+    policyFile
+        .addPermissionsToRole("index_db1_tb1", privileges.get("index_db1_tb1"))
+        .addRolesToGroup(USERGROUP1, "index_db1_tb1")
+        .addPermissionsToRole("insert_db1_tb1", privileges.get("insert_db1_tb1"))
+        .addRolesToGroup(USERGROUP2, "insert_db1_tb1");
+    writePolicyFile(policyFile);
+
+    Connection connection;
+    Statement statement;
+
+    //Positive cases
+    connection = context.createConnection(USER1_1);
+    statement = context.createStatement(connection);
+    statement.execute("Use " + DB1);
+    statement.execute("CREATE INDEX table01_index ON TABLE tb1 (a) AS 'COMPACT' WITH DEFERRED REBUILD");
+    statement.execute("ALTER INDEX table01_index ON tb1 REBUILD");
+    statement.close();
+    connection.close();
+
+    //Negative case
+    connection = context.createConnection(USER2_1);
+    statement = context.createStatement(connection);
+    statement.execute("Use " + DB1);
+    assertSemanticException(statement, "CREATE INDEX table02_index ON TABLE tb1 (a) AS 'COMPACT' WITH DEFERRED REBUILD");
+    assertSemanticException(statement, "ALTER INDEX table01_index ON tb1 REBUILD");
+    assertSemanticException(statement, "DROP INDEX table01_index ON tb1");
+    statement.close();
+    connection.close();
+
+    //Positive cases
+    connection = context.createConnection(USER1_1);
+    statement = context.createStatement(connection);
+    statement.execute("Use " + DB1);
+    statement.execute("DROP INDEX table01_index ON tb1");
+    statement.close();
+    connection.close();
+  }
+
+  /* Test all operations that require drop on table alone
+  1. Create index : HiveOperation.DROPTABLE
+  */
+  @Test
+  public void testDropTable() throws Exception {
+    adminCreate(DB1, tableName, true);
+    policyFile
+        .addPermissionsToRole("drop_db1_tb1", privileges.get("drop_db1_tb1"))
+        .addRolesToGroup(USERGROUP1, "drop_db1_tb1")
+        .addPermissionsToRole("insert_db1_tb1", privileges.get("insert_db1_tb1"))
+        .addRolesToGroup(USERGROUP2, "insert_db1_tb1");
+    writePolicyFile(policyFile);
+
+    Connection connection;
+    Statement statement;
+
+    //Negative case
+    connection = context.createConnection(USER2_1);
+    statement = context.createStatement(connection);
+    statement.execute("Use " + DB1);
+    assertSemanticException(statement, "drop table " + tableName);
+
+    statement.close();
+    connection.close();
+
+    //Positive cases
+    connection = context.createConnection(USER1_1);
+    statement = context.createStatement(connection);
+    statement.execute("Use " + DB1);
+    statement.execute("drop table " + tableName);
+
+    statement.close();
+    connection.close();
+  }
+
+  @Ignore
+  @Test
+  public void testLockTable() throws Exception {
+   //TODO
+  }
+
+  /* Operations that require alter + drop on table
+    1. HiveOperation.ALTERTABLE_DROPPARTS
+  */
+  @Test
+  public void dropPartition() throws Exception {
+    adminCreate(DB1, tableName, true);
+    policyFile
+        .addPermissionsToRole("alter_db1_tb1", privileges.get("alter_db1_tb1"))
+        .addPermissionsToRole("drop_db1_tb1", privileges.get("drop_db1_tb1"))
+        .addRolesToGroup(USERGROUP1, "alter_db1_tb1", "drop_db1_tb1")
+        .addRolesToGroup(USERGROUP2, "alter_db1_tb1");
+
+    writePolicyFile(policyFile);
+
+    Connection connection;
+    Statement statement;
+    //Setup
+    connection = context.createConnection(ADMIN1);
+    statement = context.createStatement(connection);
+    statement.execute("Use " + DB1);
+    statement.execute("ALTER TABLE tb1 ADD IF NOT EXISTS PARTITION (b = '10') ");
+
+    //Negative case
+    connection = context.createConnection(USER2_1);
+    statement = context.createStatement(connection);
+    statement.execute("USE " + DB1);
+    assertSemanticException(statement, "ALTER TABLE tb1 DROP PARTITION (b = 10)");
+
+    //Positive case
+    connection = context.createConnection(USER1_1);
+    statement = context.createStatement(connection);
+    statement.execute("Use " + DB1);
+    statement.execute("ALTER TABLE tb1 DROP PARTITION (b = 10)");
+    statement.close();
+    connection.close();
+  }
+
+  /*
+   1. HiveOperation.ALTERTABLE_RENAME
+   */
+  @Test
+  public void renameTable() throws Exception {
+    adminCreate(DB1, tableName);
+    policyFile
+        .addPermissionsToRole("alter_db1_tb1", privileges.get("alter_db1_tb1"))
+        .addPermissionsToRole("create_db1", privileges.get("create_db1"))
+        .addRolesToGroup(USERGROUP1, "alter_db1_tb1", "create_db1")
+        .addRolesToGroup(USERGROUP2, "create_db1")
+        .addRolesToGroup(USERGROUP3, "alter_db1_tb1");
+
+    writePolicyFile(policyFile);
+
+    Connection connection;
+    Statement statement;
+
+    //Negative cases
+    connection = context.createConnection(USER2_1);
+    statement = context.createStatement(connection);
+    statement.execute("Use " + DB1);
+    assertSemanticException(statement, "ALTER TABLE tb1 RENAME TO tb2");
+    statement.close();
+    connection.close();
+
+    connection = context.createConnection(USER3_1);
+    statement = context.createStatement(connection);
+    statement.execute("Use " + DB1);
+    assertSemanticException(statement, "ALTER TABLE tb1 RENAME TO tb2");
+    statement.close();
+    connection.close();
+
+    //Positive case
+    connection = context.createConnection(USER1_1);
+    statement = context.createStatement(connection);
+    statement.execute("Use " + DB1);
+    statement.execute("ALTER TABLE tb1 RENAME TO tb2");
+    statement.close();
+    connection.close();
+  }
+
+  /* Test all operations which require alter on table (+ all on URI)
    1. HiveOperation.ALTERTABLE_LOCATION
    2. HiveOperation.ALTERTABLE_ADDPARTS
    3. TODO: HiveOperation.ALTERPARTITION_LOCATION
    4. TODO: HiveOperation.ALTERTBLPART_SKEWED_LOCATION
    */
   @Test
-  public void testAlterAllOnTableAndURI() throws Exception {
+  public void testAlterOnTableAndURI() throws Exception {
     adminCreate(DB1, tableName, true);
     String tabLocation = dfs.getBaseDir() + "/" + Math.random();
     policyFile
-        .addPermissionsToRole("all_db1_tb1", privileges.get("all_db1_tb1"))
+        .addPermissionsToRole("alter_db1_tb1", privileges.get("alter_db1_tb1"))
         .addPermissionsToRole("all_uri", "server=server1->uri=" + tabLocation)
-        .addRolesToGroup(USERGROUP1, "all_db1_tb1", "all_uri")
-        .addRolesToGroup(USERGROUP2, "all_db1_tb1");
+        .addRolesToGroup(USERGROUP1, "alter_db1_tb1", "all_uri")
+        .addRolesToGroup(USERGROUP2, "alter_db1_tb1");
 
     writePolicyFile(policyFile);
 
-    Connection connection = context.createConnection(USER1_1);
+    //Case with out uri
+    Connection connection = context.createConnection(USER2_1);
     Statement statement = context.createStatement(connection);
+    statement.execute("USE " + DB1);
+    assertSemanticException(statement, "ALTER TABLE tb1 SET LOCATION '" + tabLocation + "'");
+    assertSemanticException(statement, "ALTER TABLE tb1 ADD IF NOT EXISTS PARTITION (b = '3') LOCATION '" + tabLocation + "/part'");
+    statement.execute("ALTER TABLE tb1 ADD IF NOT EXISTS PARTITION (b = '1') ");
+
+    connection = context.createConnection(USER1_1);
+    statement = context.createStatement(connection);
     statement.execute("Use " + DB1);
     statement.execute("ALTER TABLE tb1 SET LOCATION '" + tabLocation + "'");
     statement.execute("ALTER TABLE tb1 ADD IF NOT EXISTS PARTITION (b = '3') LOCATION '" + tabLocation + "/part'");
+    statement.execute("ALTER TABLE tb1 ADD IF NOT EXISTS PARTITION (b = '10') ");
     statement.close();
     connection.close();
 
@@ -475,17 +739,18 @@ public class TestOperations extends AbstractTestWithStaticConfiguration {
     connection = context.createConnection(USER3_1);
     statement = context.createStatement(connection);
     statement.execute("Use " + DB1);
-    context.assertSentrySemanticException(statement, "ALTER TABLE tb1 SET LOCATION '" + tabLocation + "'",
-        semanticException);
-    context.assertSentrySemanticException(statement, "ALTER TABLE tb1 ADD IF NOT EXISTS PARTITION (b = '3') LOCATION '"
-        + tabLocation + "/part'", semanticException);
+    assertSemanticException(statement, "ALTER TABLE tb1 ADD IF NOT EXISTS PARTITION (b = '2') ");
+    assertSemanticException(statement, "ALTER TABLE tb1 SET LOCATION '" + tabLocation + "'");
+
+    assertSemanticException(statement, "ALTER TABLE tb1 ADD IF NOT EXISTS PARTITION (b = '3') LOCATION '"
+        + tabLocation + "/part'");
     statement.close();
     connection.close();
 
 
   }
 
-  /* All on Database and select on table
+  /* Create on Database and select on table
   1. Create view :  HiveOperation.CREATEVIEW
    */
   @Test
@@ -494,8 +759,8 @@ public class TestOperations extends AbstractTestWithStaticConfiguration {
     adminCreate(DB2, null);
     policyFile
         .addPermissionsToRole("select_db1_tb1", privileges.get("select_db1_tb1"))
-        .addPermissionsToRole("all_db2", privileges.get("all_db2"))
-        .addRolesToGroup(USERGROUP1, "select_db1_tb1", "all_db2");
+        .addPermissionsToRole("create_db2", privileges.get("create_db2"))
+        .addRolesToGroup(USERGROUP1, "select_db1_tb1", "create_db2");
     writePolicyFile(policyFile);
 
     Connection connection = context.createConnection(USER1_1);
@@ -508,7 +773,7 @@ public class TestOperations extends AbstractTestWithStaticConfiguration {
     //Negative case
     policyFile
         .addPermissionsToRole("insert_db1_tb1", privileges.get("insert_db1_tb1"))
-        .addRolesToGroup(USERGROUP3, "insert_db1_tb1", "all_db2");
+        .addRolesToGroup(USERGROUP3, "insert_db1_tb1", "create_db2");
     writePolicyFile(policyFile);
 
     connection = context.createConnection(USER3_1);
@@ -523,7 +788,7 @@ public class TestOperations extends AbstractTestWithStaticConfiguration {
   }
 
   /*
-   1. HiveOperation.IMPORT : All on db + all on URI
+   1. HiveOperation.IMPORT : Create on db + all on URI
    2. HiveOperation.EXPORT : SELECT on table + all on uri
    */
 
@@ -540,12 +805,12 @@ public class TestOperations extends AbstractTestWithStaticConfiguration {
     createTable(ADMIN1, DB1, dataFile, tableName);
     String location = dfs.getBaseDir() + "/" + Math.random();
     policyFile
-        .addPermissionsToRole("all_db1", privileges.get("all_db1"))
+        .addPermissionsToRole("create_db1", privileges.get("create_db1"))
         .addPermissionsToRole("all_uri", "server=server1->uri="+ location)
         .addPermissionsToRole("select_db1_tb1", privileges.get("select_db1_tb1"))
         .addPermissionsToRole("insert_db1", privileges.get("insert_db1"))
         .addRolesToGroup(USERGROUP1, "select_db1_tb1", "all_uri")
-        .addRolesToGroup(USERGROUP2, "all_db1", "all_uri")
+        .addRolesToGroup(USERGROUP2, "create_db1", "all_uri")
         .addRolesToGroup(USERGROUP3, "insert_db1", "all_uri");
     writePolicyFile(policyFile);
     Connection connection;
@@ -615,7 +880,7 @@ public class TestOperations extends AbstractTestWithStaticConfiguration {
   }
 
   /*
-  1. HiveOperation.CREATETABLE_AS_SELECT : All on db + select on table
+  1. HiveOperation.CREATETABLE_AS_SELECT : Create on db + select on table
    */
   @Test
   public void testCTAS() throws Exception {
@@ -632,9 +897,9 @@ public class TestOperations extends AbstractTestWithStaticConfiguration {
     policyFile
         .addPermissionsToRole("select_db1_tb1", privileges.get("select_db1_tb1"))
         .addPermissionsToRole("select_db1_view1", privileges.get("select_db1_view1"))
-        .addPermissionsToRole("all_db2", privileges.get("all_db2"))
-        .addRolesToGroup(USERGROUP1, "select_db1_tb1", "all_db2")
-        .addRolesToGroup(USERGROUP2, "select_db1_view1", "all_db2");
+        .addPermissionsToRole("create_db2", privileges.get("create_db2"))
+        .addRolesToGroup(USERGROUP1, "select_db1_tb1", "create_db2")
+        .addRolesToGroup(USERGROUP2, "select_db1_view1", "create_db2");
     writePolicyFile(policyFile);
 
     connection = context.createConnection(USER1_1);
@@ -713,4 +978,33 @@ public class TestOperations extends AbstractTestWithStaticConfiguration {
     statement.execute("drop table tb1");
   }
 
+  @Test
+  public void testExternalTables() throws Exception{
+    createDb(ADMIN1, DB1);
+    File externalTblDir = new File(dataDir, "exttab");
+    assertTrue("Unable to create directory for external table test" , externalTblDir.mkdir());
+
+    policyFile
+        .addPermissionsToRole("create_db1", privileges.get("create_db1"))
+        .addPermissionsToRole("all_uri", "server=server1->uri=file://" + dataDir.getPath())
+        .addRolesToGroup(USERGROUP1, "create_db1", "all_uri")
+        .addRolesToGroup(USERGROUP2, "create_db1");
+    writePolicyFile(policyFile);
+
+    Connection connection = context.createConnection(USER2_1);
+    Statement statement = context.createStatement(connection);
+    assertSemanticException(statement, "create external table " + DB1 + ".tb1(a int) stored as " +
+        "textfile location 'file:" + externalTblDir.getAbsolutePath() + "'");
+    statement.close();
+    connection.close();
+
+    connection = context.createConnection(USER1_1);
+    statement = context.createStatement(connection);
+    statement.execute("create external table " + DB1 + ".tb1(a int) stored as " +
+        "textfile location 'file:" + externalTblDir.getAbsolutePath() + "'");
+    statement.close();
+    connection.close();
+
+
+  }
 }

http://git-wip-us.apache.org/repos/asf/incubator-sentry/blob/05a239da/sentry-tests/sentry-tests-hive/src/test/java/org/apache/sentry/tests/e2e/metastore/SentryPolicyProviderForDb.java
----------------------------------------------------------------------
diff --git a/sentry-tests/sentry-tests-hive/src/test/java/org/apache/sentry/tests/e2e/metastore/SentryPolicyProviderForDb.java b/sentry-tests/sentry-tests-hive/src/test/java/org/apache/sentry/tests/e2e/metastore/SentryPolicyProviderForDb.java
index c60d0d5..f98394a 100644
--- a/sentry-tests/sentry-tests-hive/src/test/java/org/apache/sentry/tests/e2e/metastore/SentryPolicyProviderForDb.java
+++ b/sentry-tests/sentry-tests-hive/src/test/java/org/apache/sentry/tests/e2e/metastore/SentryPolicyProviderForDb.java
@@ -147,7 +147,7 @@ public class SentryPolicyProviderForDb extends PolicyFile {
       } else if (uriPath != null) {
         sentryClient.grantURIPrivilege(ADMIN1, roleName, serverName, uriPath);
       } else if (serverName != null) {
-        sentryClient.grantServerPrivilege(ADMIN1, roleName, serverName);
+        sentryClient.grantServerPrivilege(ADMIN1, roleName, serverName, action);
         ;
       }
     }

http://git-wip-us.apache.org/repos/asf/incubator-sentry/blob/05a239da/sentry-tests/sentry-tests-hive/src/test/java/org/apache/sentry/tests/e2e/metastore/TestMetastoreEndToEnd.java
----------------------------------------------------------------------
diff --git a/sentry-tests/sentry-tests-hive/src/test/java/org/apache/sentry/tests/e2e/metastore/TestMetastoreEndToEnd.java b/sentry-tests/sentry-tests-hive/src/test/java/org/apache/sentry/tests/e2e/metastore/TestMetastoreEndToEnd.java
index 55ae2f4..8ce78bc 100644
--- a/sentry-tests/sentry-tests-hive/src/test/java/org/apache/sentry/tests/e2e/metastore/TestMetastoreEndToEnd.java
+++ b/sentry-tests/sentry-tests-hive/src/test/java/org/apache/sentry/tests/e2e/metastore/TestMetastoreEndToEnd.java
@@ -70,7 +70,7 @@ public class TestMetastoreEndToEnd extends
         .addRolesToGroup(USERGROUP3, tab2_read_role)
         .addPermissionsToRole(db_all_role, "server=server1->db=" + dbName)
         .addPermissionsToRole("read_db_role",
-            "server=server1->db=" + dbName + "->table=*->action=SELECT")
+            "server=server1->db=" + dbName + "->action=SELECT")
         .addPermissionsToRole(tab1_all_role,
             "server=server1->db=" + dbName + "->table=" + tabName1)
         .addPermissionsToRole(tab2_all_role,