You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@geode.apache.org by kl...@apache.org on 2016/05/04 22:57:37 UTC

[37/63] [abbrv] incubator-geode git commit: GEODE-17: enhance the GeodeSecurityUtil and review changes

http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/7c38f0d8/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/GeodeSecurityUtilCustomRealmJUnitTest.java
----------------------------------------------------------------------
diff --git a/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/GeodeSecurityUtilCustomRealmJUnitTest.java b/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/GeodeSecurityUtilCustomRealmJUnitTest.java
new file mode 100644
index 0000000..cc6af0e
--- /dev/null
+++ b/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/GeodeSecurityUtilCustomRealmJUnitTest.java
@@ -0,0 +1,52 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.gemstone.gemfire.management.internal.security;
+
+import java.util.Properties;
+
+import com.gemstone.gemfire.distributed.internal.DistributionConfig;
+import com.gemstone.gemfire.security.CustomAuthRealm;
+import com.gemstone.gemfire.test.junit.categories.UnitTest;
+
+import org.apache.shiro.SecurityUtils;
+import org.apache.shiro.mgt.DefaultSecurityManager;
+import org.apache.shiro.mgt.SecurityManager;
+import org.apache.shiro.realm.Realm;
+import org.junit.BeforeClass;
+import org.junit.experimental.categories.Category;
+
+/**
+ * this test and ShiroUtilWithIniFileJunitTest uses the same test body, but initialize the SecurityUtils differently.
+ * If you change shiro-ini.json, remmber to change the shiro.ini to match the changes as well.
+ */
+
+@Category(UnitTest.class)
+public class GeodeSecurityUtilCustomRealmJUnitTest extends GeodeSecurityUtilWithIniFileJUnitTest {
+  @BeforeClass
+  public static void beforeClass() throws Exception{
+    Properties properties = new Properties();
+    properties.put(DistributionConfig.SECURITY_CLIENT_AUTHENTICATOR_NAME, JSONAuthorization.class.getName() + ".create");
+    properties.put(DistributionConfig.SECURITY_CLIENT_ACCESSOR_NAME, JSONAuthorization.class.getName() + ".create");
+    JSONAuthorization.setUpWithJsonFile("shiro-ini.json");
+
+    Realm realm = new CustomAuthRealm(properties);
+    SecurityManager securityManager = new DefaultSecurityManager(realm);
+    SecurityUtils.setSecurityManager(securityManager);
+  }
+
+}

http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/7c38f0d8/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/GeodeSecurityUtilWithIniFileJUnitTest.java
----------------------------------------------------------------------
diff --git a/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/GeodeSecurityUtilWithIniFileJUnitTest.java b/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/GeodeSecurityUtilWithIniFileJUnitTest.java
new file mode 100644
index 0000000..4ad390d
--- /dev/null
+++ b/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/GeodeSecurityUtilWithIniFileJUnitTest.java
@@ -0,0 +1,147 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.gemstone.gemfire.management.internal.security;
+
+import static org.assertj.core.api.Assertions.*;
+
+import com.gemstone.gemfire.cache.operations.OperationContext;
+import com.gemstone.gemfire.security.GemFireSecurityException;
+import com.gemstone.gemfire.security.GeodeSecurityUtil;
+import com.gemstone.gemfire.test.junit.categories.UnitTest;
+
+import org.apache.shiro.SecurityUtils;
+import org.apache.shiro.config.IniSecurityManagerFactory;
+import org.apache.shiro.mgt.SecurityManager;
+import org.apache.shiro.util.ThreadContext;
+import org.junit.AfterClass;
+import org.junit.BeforeClass;
+import org.junit.Test;
+import org.junit.experimental.categories.Category;
+
+/**
+ * this test and ShiroUtilCustomRealmJUunitTest uses the same test body, but initialize the SecurityUtils differently.
+ * If you change shiro.ini, remmber to change the shiro-ini.json to match the changes as well.
+ */
+@Category(UnitTest.class)
+public class GeodeSecurityUtilWithIniFileJUnitTest {
+  @BeforeClass
+  public static void beforeClass() throws Exception{
+    ThreadContext.remove();
+    IniSecurityManagerFactory factory = new IniSecurityManagerFactory("classpath:shiro.ini");
+    SecurityManager securityManager = factory.getInstance();
+    SecurityUtils.setSecurityManager(securityManager);
+  }
+
+  @AfterClass
+  public static void afterClass(){
+    ThreadContext.remove();
+  }
+
+  @Test
+  public void testRoot(){
+    GeodeSecurityUtil.login("root", "secret");
+    GeodeSecurityUtil.authorize(TestCommand.none);
+    GeodeSecurityUtil.authorize(TestCommand.everyOneAllowed);
+    GeodeSecurityUtil.authorize(TestCommand.dataRead);
+    GeodeSecurityUtil.authorize(TestCommand.dataWrite);
+    GeodeSecurityUtil.authorize(TestCommand.regionARead);
+    GeodeSecurityUtil.authorize(TestCommand.regionAWrite);
+    GeodeSecurityUtil.authorize(TestCommand.clusterWrite);
+    GeodeSecurityUtil.authorize(TestCommand.clusterRead);
+  }
+
+  @Test
+  public void testGuest(){
+    GeodeSecurityUtil.login("guest", "guest");
+    GeodeSecurityUtil.authorize(TestCommand.none);
+    GeodeSecurityUtil.authorize(TestCommand.everyOneAllowed);
+
+    assertNotAuthorized(TestCommand.dataRead);
+    assertNotAuthorized(TestCommand.dataWrite);
+    assertNotAuthorized(TestCommand.regionARead);
+    assertNotAuthorized(TestCommand.regionAWrite);
+    assertNotAuthorized(TestCommand.clusterRead);
+    assertNotAuthorized(TestCommand.clusterWrite);
+    GeodeSecurityUtil.logout();
+  }
+
+  @Test
+  public void testRegionAReader(){
+    GeodeSecurityUtil.login("regionAReader", "password");
+    GeodeSecurityUtil.authorize(TestCommand.none);
+    GeodeSecurityUtil.authorize(TestCommand.everyOneAllowed);
+    GeodeSecurityUtil.authorize(TestCommand.regionARead);
+
+    assertNotAuthorized(TestCommand.regionAWrite);
+    assertNotAuthorized(TestCommand.dataRead);
+    assertNotAuthorized(TestCommand.dataWrite);
+    assertNotAuthorized(TestCommand.clusterRead);
+    assertNotAuthorized(TestCommand.clusterWrite);
+    GeodeSecurityUtil.logout();
+  }
+
+  @Test
+  public void testRegionAUser(){
+    GeodeSecurityUtil.login("regionAUser", "password");
+    GeodeSecurityUtil.authorize(TestCommand.none);
+    GeodeSecurityUtil.authorize(TestCommand.everyOneAllowed);
+    GeodeSecurityUtil.authorize(TestCommand.regionAWrite);
+    GeodeSecurityUtil.authorize(TestCommand.regionARead);
+
+    assertNotAuthorized(TestCommand.dataRead);
+    assertNotAuthorized(TestCommand.dataWrite);
+    assertNotAuthorized(TestCommand.clusterRead);
+    assertNotAuthorized(TestCommand.clusterWrite);
+    GeodeSecurityUtil.logout();
+  }
+
+  @Test
+  public void testDataReader(){
+    GeodeSecurityUtil.login("dataReader", "12345");
+    GeodeSecurityUtil.authorize(TestCommand.none);
+    GeodeSecurityUtil.authorize(TestCommand.everyOneAllowed);
+    GeodeSecurityUtil.authorize(TestCommand.regionARead);
+    GeodeSecurityUtil.authorize(TestCommand.dataRead);
+
+    assertNotAuthorized(TestCommand.regionAWrite);
+    assertNotAuthorized(TestCommand.dataWrite);
+    assertNotAuthorized(TestCommand.clusterRead);
+    assertNotAuthorized(TestCommand.clusterWrite);
+    GeodeSecurityUtil.logout();
+  }
+
+  @Test
+  public void testReader(){
+    GeodeSecurityUtil.login("reader", "12345");
+    GeodeSecurityUtil.authorize(TestCommand.none);
+    GeodeSecurityUtil.authorize(TestCommand.everyOneAllowed);
+    GeodeSecurityUtil.authorize(TestCommand.regionARead);
+    GeodeSecurityUtil.authorize(TestCommand.dataRead);
+    GeodeSecurityUtil.authorize(TestCommand.clusterRead);
+
+    assertNotAuthorized(TestCommand.regionAWrite);
+    assertNotAuthorized(TestCommand.dataWrite);
+    assertNotAuthorized(TestCommand.clusterWrite);
+    GeodeSecurityUtil.logout();
+  }
+
+  private void assertNotAuthorized(OperationContext context){
+    assertThatThrownBy(()-> GeodeSecurityUtil.authorize(context)).isInstanceOf(GemFireSecurityException.class).hasMessageContaining(context.toString());
+  }
+
+}

http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/7c38f0d8/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/GfshCommandsSecurityTest.java
----------------------------------------------------------------------
diff --git a/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/GfshCommandsSecurityTest.java b/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/GfshCommandsSecurityTest.java
index 56d7030..b5ef0a6 100644
--- a/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/GfshCommandsSecurityTest.java
+++ b/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/GfshCommandsSecurityTest.java
@@ -31,6 +31,8 @@ import com.gemstone.gemfire.management.internal.cli.result.CommandResult;
 import com.gemstone.gemfire.management.internal.cli.result.ErrorResultData;
 import com.gemstone.gemfire.management.internal.cli.result.ResultBuilder;
 import com.gemstone.gemfire.test.junit.categories.IntegrationTest;
+
+import org.apache.shiro.authz.permission.WildcardPermission;
 import org.junit.Before;
 import org.junit.ClassRule;
 import org.junit.Rule;
@@ -122,7 +124,7 @@ public class GfshCommandsSecurityTest {
 
 
   private void runCommandsWithAndWithout(String permission) throws Exception{
-    List<TestCommand> permitted = TestCommand.getCommandsOfPermission(permission);
+    List<TestCommand> permitted = TestCommand.getPermittedCommands(new WildcardPermission(permission));
     for(TestCommand clusterRead:permitted) {
       LogService.getLogger().info("Processing authorized command: "+clusterRead.getCommand());gfsh.executeCommand(clusterRead.getCommand());
       CommandResult result = (CommandResult) gfsh.getResult();
@@ -155,7 +157,7 @@ public class GfshCommandsSecurityTest {
       }
 
       assertEquals(ResultBuilder.ERRORCODE_UNAUTHORIZED, ((ErrorResultData) result.getResultData()).getErrorCode());
-      assertTrue(result.getContent().toString().contains(other.getPermission()));
+      assertTrue(result.getContent().toString().contains(other.getPermission().toString()));
     }
   }
 

http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/7c38f0d8/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/JSONAuthorization.java
----------------------------------------------------------------------
diff --git a/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/JSONAuthorization.java b/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/JSONAuthorization.java
index 48e0a39..83f4876 100644
--- a/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/JSONAuthorization.java
+++ b/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/JSONAuthorization.java
@@ -32,8 +32,6 @@ import javax.management.remote.JMXPrincipal;
 import com.gemstone.gemfire.LogWriter;
 import com.gemstone.gemfire.cache.Cache;
 import com.gemstone.gemfire.cache.operations.OperationContext;
-import com.gemstone.gemfire.cache.operations.OperationContext.OperationCode;
-import com.gemstone.gemfire.cache.operations.OperationContext.Resource;
 import com.gemstone.gemfire.distributed.DistributedMember;
 import com.gemstone.gemfire.internal.logging.LogService;
 import com.gemstone.gemfire.security.AccessControl;
@@ -41,41 +39,16 @@ import com.gemstone.gemfire.security.AuthenticationFailedException;
 import com.gemstone.gemfire.security.Authenticator;
 import com.gemstone.gemfire.security.NotAuthorizedException;
 import com.gemstone.gemfire.util.test.TestUtil;
+
 import org.json.JSONArray;
 import org.json.JSONException;
 import org.json.JSONObject;
 
 public class JSONAuthorization implements AccessControl, Authenticator {
 
-  static class Permission {
-
-    private final Resource resource;
-    private final OperationCode operationCode;
-
-    Permission(Resource resource, OperationCode operationCode) {
-      this.resource = resource;
-      this.operationCode = operationCode;
-    }
-
-    public Resource getResource() {
-      return resource;
-    }
-
-    public OperationCode getOperationCode() {
-      return operationCode;
-    }
-
-    @Override
-    public String toString() {
-      String result = resource.toString() + ":" + operationCode.toString();
-      return result;
-    }
-  }
-
   public static class Role {
-    List<Permission> permissions = new ArrayList<>();
+    List<OperationContext> permissions = new ArrayList<>();
     String name;
-    List<String> regionNames = null; // when checking, if regionNames is null, that means all regions are allowed.
     String serverGroup;
   }
 
@@ -139,29 +112,18 @@ public class JSONAuthorization implements AccessControl, Authenticator {
       JSONObject obj = array.getJSONObject(i);
       Role role = new Role();
       role.name = obj.getString("name");
+      String regionNames = null;
+      if(obj.has("regions")) {
+        regionNames = obj.getString("regions");
+      }
       JSONArray ops = obj.getJSONArray("operationsAllowed");
       for (int j = 0; j < ops.length(); j++) {
         String[] parts = ops.getString(j).split(":");
-        Resource r = Resource.valueOf(parts[0]);
-        OperationCode op = parts.length > 1 ? OperationCode.valueOf(parts[1]) : OperationCode.READ;
-        role.permissions.add(new Permission(r, op));
-      }
-
-      if(obj.has("region")) {
-        if (role.regionNames == null) {
-          role.regionNames = new ArrayList<>();
-        }
-        role.regionNames.add(obj.getString("region"));
-      }
-
-      if(obj.has("regions")) {
-        JSONArray regions = obj.getJSONArray("regions");
-        if (role.regionNames == null) {
-          role.regionNames = new ArrayList<>();
-        }
-        for (int j = 0; j < regions.length(); j++) {
-          role.regionNames.add(regions.getString(j));
+        if(regionNames!=null) {
+          role.permissions.add(new ResourceOperationContext(parts[0], parts[1], regionNames));
         }
+        else
+          role.permissions.add(new ResourceOperationContext(parts[0], parts[1], "*"));
       }
 
       roleMap.put(role.name, role);
@@ -194,28 +156,15 @@ public class JSONAuthorization implements AccessControl, Authenticator {
     if(user == null)
       return false; // this user is not authorized to do anything
 
-    LogService.getLogger().info("Checking for permission " + context.getResource() + ":" + context.getOperationCode());
-
     // check if the user has this permission defined in the context
     for(Role role:acl.get(user.name).roles) {
-      for (Permission perm : role.permissions) {
-        if (context.getResource() == perm.getResource() && context.getOperationCode() == perm.getOperationCode()) {
-          LogService.getLogger().info("Found permission " + perm);
-
-          //no need to further check the rgionName
-          if(context.getRegionName()==null){
-            return true;
-          }
-
-          if(role.regionNames == null || role.regionNames.contains(context.getRegionName())){
-            // if regionName is null, i.e. all regions are allowed
-            return true;
-          }
+      for (OperationContext permitted : role.permissions) {
+        if (permitted.implies(context)) {
+          return true;
         }
       }
     }
 
-    LogService.getLogger().info("Did not find code " + context);
     return false;
   }
 

http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/7c38f0d8/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/LockServiceMBeanAuthorizationJUnitTest.java
----------------------------------------------------------------------
diff --git a/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/LockServiceMBeanAuthorizationJUnitTest.java b/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/LockServiceMBeanAuthorizationJUnitTest.java
index b4b3f72..f07358b 100644
--- a/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/LockServiceMBeanAuthorizationJUnitTest.java
+++ b/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/LockServiceMBeanAuthorizationJUnitTest.java
@@ -81,10 +81,10 @@ public class LockServiceMBeanAuthorizationJUnitTest {
   @Test
   @JMXConnectionConfiguration(user = "data-user", password = "1234567")
   public void testNoAccess() throws Exception {
-    assertThatThrownBy(() -> lockServiceMBean.becomeLockGrantor()).hasMessageContaining("DATA:MANAGE");
-    assertThatThrownBy(() -> lockServiceMBean.fetchGrantorMember()).hasMessageContaining("CLUSTER:READ");
-    assertThatThrownBy(() -> lockServiceMBean.getMemberCount()).hasMessageContaining("CLUSTER:READ");
-    assertThatThrownBy(() -> lockServiceMBean.isDistributed()).hasMessageContaining("CLUSTER:READ");
-    assertThatThrownBy(() -> lockServiceMBean.listThreadsHoldingLock()).hasMessageContaining("CLUSTER:READ");
+    assertThatThrownBy(() -> lockServiceMBean.becomeLockGrantor()).hasMessageContaining(TestCommand.dataManage.toString());
+    assertThatThrownBy(() -> lockServiceMBean.fetchGrantorMember()).hasMessageContaining(TestCommand.clusterRead.toString());
+    assertThatThrownBy(() -> lockServiceMBean.getMemberCount()).hasMessageContaining(TestCommand.clusterRead.toString());
+    assertThatThrownBy(() -> lockServiceMBean.isDistributed()).hasMessageContaining(TestCommand.clusterRead.toString());
+    assertThatThrownBy(() -> lockServiceMBean.listThreadsHoldingLock()).hasMessageContaining(TestCommand.clusterRead.toString());
   }
 }

http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/7c38f0d8/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/ManagerMBeanAuthorizationJUnitTest.java
----------------------------------------------------------------------
diff --git a/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/ManagerMBeanAuthorizationJUnitTest.java b/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/ManagerMBeanAuthorizationJUnitTest.java
index 2548d21..425c467 100644
--- a/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/ManagerMBeanAuthorizationJUnitTest.java
+++ b/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/ManagerMBeanAuthorizationJUnitTest.java
@@ -71,8 +71,8 @@ public class ManagerMBeanAuthorizationJUnitTest {
   @Test
   @JMXConnectionConfiguration(user = "data-admin", password = "1234567")
   public void testSomeAccess() throws Exception {
-    assertThatThrownBy(() -> managerMXBean.start()).hasMessageContaining("CLUSTER:MANAGE");
-    assertThatThrownBy(() -> managerMXBean.getPulseURL()).hasMessageContaining("CLUSTER:WRITE");
+    assertThatThrownBy(() -> managerMXBean.start()).hasMessageContaining(TestCommand.clusterManage.toString());
+    assertThatThrownBy(() -> managerMXBean.getPulseURL()).hasMessageContaining(TestCommand.clusterWrite.toString());
     managerMXBean.isRunning();
   }
 }

http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/7c38f0d8/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/MemberMBeanSecurityJUnitTest.java
----------------------------------------------------------------------
diff --git a/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/MemberMBeanSecurityJUnitTest.java b/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/MemberMBeanSecurityJUnitTest.java
index c5ff369..8261d09 100644
--- a/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/MemberMBeanSecurityJUnitTest.java
+++ b/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/MemberMBeanSecurityJUnitTest.java
@@ -66,7 +66,7 @@ public class MemberMBeanSecurityJUnitTest {
   @Test
   @JMXConnectionConfiguration(user = "cluster-admin", password = "1234567")
   public void testClusterAdmin() throws Exception {
-    assertThatThrownBy(() -> bean.compactAllDiskStores()).hasMessageContaining("DATA:MANAGE");
+    assertThatThrownBy(() -> bean.compactAllDiskStores()).hasMessageContaining(TestCommand.dataManage.toString());
     bean.shutDownMember();
     bean.createManager();
     bean.fetchJvmThreads();
@@ -84,8 +84,8 @@ public class MemberMBeanSecurityJUnitTest {
   @JMXConnectionConfiguration(user = "data-admin", password = "1234567")
   public void testDataAdmin() throws Exception {
     bean.compactAllDiskStores();
-    assertThatThrownBy(() -> bean.shutDownMember()).hasMessageContaining("CLUSTER:MANAGE");
-    assertThatThrownBy(() -> bean.createManager()).hasMessageContaining("CLUSTER:MANAGE");
+    assertThatThrownBy(() -> bean.shutDownMember()).hasMessageContaining(TestCommand.clusterManage.toString());
+    assertThatThrownBy(() -> bean.createManager()).hasMessageContaining(TestCommand.clusterManage.toString());
     bean.showJVMMetrics();
     bean.status();
   }
@@ -93,18 +93,18 @@ public class MemberMBeanSecurityJUnitTest {
   @Test
   @JMXConnectionConfiguration(user = "data-user", password = "1234567")
   public void testDataUser() throws Exception {
-    assertThatThrownBy(() -> bean.shutDownMember()).hasMessageContaining("CLUSTER:MANAGE");
-    assertThatThrownBy(() -> bean.createManager()).hasMessageContaining("CLUSTER:MANAGE");
-    assertThatThrownBy(() -> bean.compactAllDiskStores()).hasMessageContaining("DATA:MANAGE");
-    assertThatThrownBy(() -> bean.fetchJvmThreads()).hasMessageContaining("CLUSTER:READ");
-    assertThatThrownBy(() -> bean.getName()).hasMessageContaining("CLUSTER:READ");
-    assertThatThrownBy(() -> bean.getDiskStores()).hasMessageContaining("CLUSTER:READ");
-    assertThatThrownBy(() -> bean.hasGatewayReceiver()).hasMessageContaining("CLUSTER:READ");
-    assertThatThrownBy(() -> bean.isCacheServer()).hasMessageContaining("CLUSTER:READ");
-    assertThatThrownBy(() -> bean.isServer()).hasMessageContaining("CLUSTER:READ");
-    assertThatThrownBy(() -> bean.listConnectedGatewayReceivers()).hasMessageContaining("CLUSTER:READ");
+    assertThatThrownBy(() -> bean.shutDownMember()).hasMessageContaining(TestCommand.clusterManage.toString());
+    assertThatThrownBy(() -> bean.createManager()).hasMessageContaining(TestCommand.clusterManage.toString());
+    assertThatThrownBy(() -> bean.compactAllDiskStores()).hasMessageContaining(TestCommand.dataManage.toString());
+    assertThatThrownBy(() -> bean.fetchJvmThreads()).hasMessageContaining(TestCommand.clusterRead.toString());
+    assertThatThrownBy(() -> bean.getName()).hasMessageContaining(TestCommand.clusterRead.toString());
+    assertThatThrownBy(() -> bean.getDiskStores()).hasMessageContaining(TestCommand.clusterRead.toString());
+    assertThatThrownBy(() -> bean.hasGatewayReceiver()).hasMessageContaining(TestCommand.clusterRead.toString());
+    assertThatThrownBy(() -> bean.isCacheServer()).hasMessageContaining(TestCommand.clusterRead.toString());
+    assertThatThrownBy(() -> bean.isServer()).hasMessageContaining(TestCommand.clusterRead.toString());
+    assertThatThrownBy(() -> bean.listConnectedGatewayReceivers()).hasMessageContaining(TestCommand.clusterRead.toString());
     //assertThatThrownBy(() -> bean.processCommand("create region --name=Region_A")).hasMessageContaining("DATA:MANAGE");
-    assertThatThrownBy(() -> bean.showJVMMetrics()).hasMessageContaining("CLUSTER:READ");
-    assertThatThrownBy(() -> bean.status()).hasMessageContaining("CLUSTER:READ");
+    assertThatThrownBy(() -> bean.showJVMMetrics()).hasMessageContaining(TestCommand.clusterRead.toString());
+    assertThatThrownBy(() -> bean.status()).hasMessageContaining(TestCommand.clusterRead.toString());
   }
 }

http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/7c38f0d8/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/ResourceOperationContextJUnitTest.java
----------------------------------------------------------------------
diff --git a/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/ResourceOperationContextJUnitTest.java b/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/ResourceOperationContextJUnitTest.java
new file mode 100644
index 0000000..318d327
--- /dev/null
+++ b/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/ResourceOperationContextJUnitTest.java
@@ -0,0 +1,88 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.gemstone.gemfire.management.internal.security;
+
+import static org.junit.Assert.*;
+
+import com.gemstone.gemfire.cache.operations.OperationContext.OperationCode;
+import com.gemstone.gemfire.cache.operations.OperationContext.Resource;
+import com.gemstone.gemfire.test.junit.categories.UnitTest;
+
+import org.apache.shiro.authz.permission.WildcardPermission;
+import org.junit.Test;
+import org.junit.experimental.categories.Category;
+
+@Category(UnitTest.class)
+public class ResourceOperationContextJUnitTest {
+
+  private ResourceOperationContext context;
+
+  @Test
+  public void testEmptyConstructor(){
+    context = new ResourceOperationContext();
+    assertEquals(Resource.NULL, context.getResource());
+    assertEquals(OperationCode.NULL, context.getOperationCode());
+    assertEquals("NULL", context.getRegionName());
+  }
+
+  @Test
+  public void testIsPermission(){
+    context = new ResourceOperationContext();
+    assertTrue(context instanceof WildcardPermission);
+  }
+
+  @Test
+  public void testConstructor(){
+    context = new ResourceOperationContext(null, null, null);
+    assertEquals(Resource.NULL, context.getResource());
+    assertEquals(OperationCode.NULL, context.getOperationCode());
+    assertEquals("NULL", context.getRegionName());
+
+    context = new ResourceOperationContext(null, null);
+    assertEquals(Resource.NULL, context.getResource());
+    assertEquals(OperationCode.NULL, context.getOperationCode());
+    assertEquals("NULL", context.getRegionName());
+
+    context = new ResourceOperationContext("DATA", null, null);
+    assertEquals(Resource.DATA, context.getResource());
+    assertEquals(OperationCode.NULL, context.getOperationCode());
+    assertEquals("NULL", context.getRegionName());
+
+    context = new ResourceOperationContext(null, "MANAGE", "REGIONA");
+    assertEquals(Resource.NULL, context.getResource());
+    assertEquals(OperationCode.MANAGE, context.getOperationCode());
+    assertEquals("REGIONA", context.getRegionName());
+
+    context = new ResourceOperationContext("DATA", "MANAGE", "REGIONA");
+    assertEquals(Resource.DATA, context.getResource());
+    assertEquals(OperationCode.MANAGE, context.getOperationCode());
+    assertEquals("REGIONA", context.getRegionName());
+  }
+
+  @Test
+  public void testToString(){
+    context = new ResourceOperationContext();
+    assertEquals("[null]:[null]:[null]", context.toString());
+
+    context = new ResourceOperationContext("DATA", "MANAGE");
+    assertEquals("[data]:[manage]:[null]", context.toString());
+
+    context = new ResourceOperationContext("DATA", "MANAGE", "REGIONA");
+    assertEquals("[data]:[manage]:[regiona]", context.toString());
+  }
+}

http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/7c38f0d8/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/TestCommand.java
----------------------------------------------------------------------
diff --git a/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/TestCommand.java b/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/TestCommand.java
index c25044d..56eeeec 100644
--- a/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/TestCommand.java
+++ b/geode-core/src/test/java/com/gemstone/gemfire/management/internal/security/TestCommand.java
@@ -20,8 +20,24 @@ package com.gemstone.gemfire.management.internal.security;
 import java.util.ArrayList;
 import java.util.List;
 
+import com.gemstone.gemfire.cache.operations.OperationContext;
+
+import org.apache.shiro.authz.Permission;
+
 public class TestCommand {
-  
+  public static OperationContext none = null;
+  public static OperationContext everyOneAllowed = new ResourceOperationContext();
+  public static OperationContext dataRead = new ResourceOperationContext("DATA", "READ");
+  public static OperationContext dataWrite = new ResourceOperationContext("DATA", "WRITE");
+  public static OperationContext dataManage = new ResourceOperationContext("DATA", "MANAGE");
+
+  public static OperationContext regionARead = new ResourceOperationContext("DATA", "READ", "RegionA");
+  public static OperationContext regionAWrite = new ResourceOperationContext("DATA", "WRITE", "RegionA");
+
+  public static OperationContext clusterRead = new ResourceOperationContext("CLUSTER", "READ");
+  public static OperationContext clusterWrite = new ResourceOperationContext("CLUSTER", "WRITE");
+  public static OperationContext clusterManage = new ResourceOperationContext("CLUSTER", "MANAGE");
+
   private static List<TestCommand> testCommands = new ArrayList<>();
 
   static{
@@ -29,14 +45,14 @@ public class TestCommand {
   }
   
   private final String command;
-  private final String permission;
+  private final OperationContext permission;
   
-  public TestCommand(String command, String permission) {
+  public TestCommand(String command, OperationContext permission) {
     this.command = command;
     this.permission = permission;
   }
   
-  private static void createTestCommand(String command, String permission) {
+  private static void createTestCommand(String command, OperationContext permission) {
     TestCommand instance = new TestCommand(command, permission);
     testCommands.add(instance);
   }
@@ -45,7 +61,7 @@ public class TestCommand {
     return this.command;
   }
 
-  public String getPermission() {
+  public OperationContext getPermission() {
     return this.permission;
   }
 
@@ -53,11 +69,11 @@ public class TestCommand {
     return testCommands;
   }
 
-  public static List<TestCommand> getCommandsOfPermission(String permission){
+  public static List<TestCommand> getPermittedCommands(Permission permission){
     List<TestCommand> result = new ArrayList<>();
     for(TestCommand testCommand:testCommands){
-      String cPerm = testCommand.getPermission();
-      if(cPerm!=null && cPerm.startsWith(permission)){
+      OperationContext cPerm = testCommand.getPermission();
+      if(cPerm!=null && permission.implies(cPerm)){
         result.add(testCommand);
       }
     }
@@ -66,75 +82,75 @@ public class TestCommand {
 
   private static void init() {
     // ClientCommands
-    createTestCommand("list clients", "CLUSTER:READ");
-    createTestCommand("describe client --clientID=172.16.196.144", "CLUSTER:READ");
+    createTestCommand("list clients", clusterRead);
+    createTestCommand("describe client --clientID=172.16.196.144", clusterRead);
 
     // ConfigCommands
-    createTestCommand("alter runtime", "CLUSTER:MANAGE");
-    createTestCommand("describe config --member=Member1", "CLUSTER:READ");
-    createTestCommand("export config --member=member1", "CLUSTER:READ");
+    createTestCommand("alter runtime", clusterManage);
+    createTestCommand("describe config --member=Member1", clusterRead);
+    createTestCommand("export config --member=member1", clusterRead);
 
     //CreateAlterDestroyRegionCommands
-    createTestCommand("alter region --name=region1 --eviction-max=5000", "DATA:MANAGE");
-    createTestCommand("create region --name=region12 --type=REPLICATE", "DATA:MANAGE");
-    createTestCommand("destroy region --name=value", "DATA:MANAGE");
+    createTestCommand("alter region --name=region1 --eviction-max=5000", dataManage);
+    createTestCommand("create region --name=region12 --type=REPLICATE", dataManage);
+    createTestCommand("destroy region --name=value", dataManage);
 
     //Data Commands
-    createTestCommand("rebalance --include-region=region1", "DATA:MANAGE");
-    createTestCommand("export data --region=region1 --file=export.txt --member=exportMember", "DATA:READ");
-    createTestCommand("import data --region=region1 --file=import.txt --member=importMember", "DATA:WRITE");
-    createTestCommand("put --key=key1 --value=value1 --region=region1", "DATA:WRITE");
-    createTestCommand("get --key=key1 --region=region1", "DATA:READ");
-    createTestCommand("remove --region=region1", "DATA:MANAGE");
-    createTestCommand("query --query='SELECT * FROM /region1'", "DATA:READ");
-    createTestCommand("locate entry --key=k1 --region=secureRegion", "DATA:READ");
+    createTestCommand("rebalance --include-region=regionA", dataManage);
+    createTestCommand("export data --region=regionA --file=export.txt --member=exportMember", regionARead);
+    createTestCommand("import data --region=regionA --file=import.txt --member=importMember", regionAWrite);
+    createTestCommand("put --key=key1 --value=value1 --region=regionA", regionAWrite);
+    createTestCommand("get --key=key1 --region=regionA", regionARead);
+    createTestCommand("remove --region=regionA", dataManage);
+    createTestCommand("query --query='SELECT * FROM /region1'", dataRead);
+    createTestCommand("locate entry --key=k1 --region=regionA", regionARead);
 
     // Deploy commands
-    //createTestCommand("deploy --jar=group1_functions.jar --group=Group1", "DATA:MANAGE"); // TODO: this command will fail in GfshCommandsSecurityTest at interceptor for jar file checking
-    createTestCommand("undeploy --group=Group1", "DATA:MANAGE");
+    //createTestCommand("deploy --jar=group1_functions.jar --group=Group1", dataManage); // TODO: this command will fail in GfshCommandsSecurityTest at interceptor for jar file checking
+    createTestCommand("undeploy --group=Group1", dataManage);
 
     // Diskstore Commands
-    createTestCommand("backup disk-store --dir=foo", "DATA:READ");
-    createTestCommand("list disk-stores", "CLUSTER:READ");
-    createTestCommand("create disk-store --name=foo --dir=bar", "DATA:MANAGE");
-    createTestCommand("compact disk-store --name=foo", "DATA:MANAGE");
+    createTestCommand("backup disk-store --dir=foo", dataRead);
+    createTestCommand("list disk-stores", clusterRead);
+    createTestCommand("create disk-store --name=foo --dir=bar", dataManage);
+    createTestCommand("compact disk-store --name=foo", dataManage);
     createTestCommand("compact offline-disk-store --name=foo --disk-dirs=bar", null);
     createTestCommand("upgrade offline-disk-store --name=foo --disk-dirs=bar", null);
-    createTestCommand("describe disk-store --name=foo --member=baz", "CLUSTER:READ");
-    createTestCommand("revoke missing-disk-store --id=foo", "DATA:MANAGE");
-    createTestCommand("show missing-disk-stores", "CLUSTER:READ");
+    createTestCommand("describe disk-store --name=foo --member=baz", clusterRead);
+    createTestCommand("revoke missing-disk-store --id=foo", dataManage);
+    createTestCommand("show missing-disk-stores", clusterRead);
     createTestCommand("describe offline-disk-store --name=foo --disk-dirs=bar", null);
     createTestCommand("export offline-disk-store --name=foo --disk-dirs=bar --dir=baz", null);
     createTestCommand("validate offline-disk-store --name=foo --disk-dirs=bar", null);
     createTestCommand("alter disk-store --name=foo --region=xyz --disk-dirs=bar", null);
-    createTestCommand("destroy disk-store --name=foo", "DATA:MANAGE");
+    createTestCommand("destroy disk-store --name=foo", dataManage);
 
     // DurableClientCommands
-    createTestCommand("close durable-client --durable-client-id=client1", "DATA:MANAGE");
-    createTestCommand("close durable-cq --durable-client-id=client1 --durable-cq-name=cq1", "DATA:MANAGE");
-    createTestCommand("show subscription-queue-size --durable-client-id=client1", "CLUSTER:READ");
-    createTestCommand("list durable-cqs --durable-client-id=client1", "CLUSTER:READ");
+    createTestCommand("close durable-client --durable-client-id=client1", dataManage);
+    createTestCommand("close durable-cq --durable-client-id=client1 --durable-cq-name=cq1", dataManage);
+    createTestCommand("show subscription-queue-size --durable-client-id=client1", clusterRead);
+    createTestCommand("list durable-cqs --durable-client-id=client1", clusterRead);
 
     //ExportIMportSharedConfigurationCommands
-    createTestCommand("export cluster-configuration --zip-file-name=mySharedConfig.zip", "CLUSTER:READ");
-    createTestCommand("import cluster-configuration --zip-file-name=value.zip", "CLUSTER:MANAGE");
+    createTestCommand("export cluster-configuration --zip-file-name=mySharedConfig.zip", clusterRead);
+    createTestCommand("import cluster-configuration --zip-file-name=value.zip", clusterManage);
 
     //FunctionCommands
-    //createTestCommand("destroy function --id=InterestCalculations", "DATA:MANAGE");
-    createTestCommand("execute function --id=InterestCalculations --group=Group1", "DATA:WRITE");
-    createTestCommand("list functions", "CLUSTER:READ");
+    //createTestCommand("destroy function --id=InterestCalculations", dataManage);
+    createTestCommand("execute function --id=InterestCalculations --group=Group1", dataWrite);
+    createTestCommand("list functions", clusterRead);
 
     //GfshHelpCommands
     createTestCommand("hint", null);
     createTestCommand("help", null);
 
     //IndexCommands
-    createTestCommand("clear defined indexes", "DATA:MANAGE");
-    createTestCommand("create defined indexes", "DATA:MANAGE");
-    createTestCommand("create index --name=myKeyIndex --expression=region1.Id --region=region1 --type=key", "DATA:MANAGE");
-    createTestCommand("define index --name=myIndex1 --expression=exp1 --region=/exampleRegion", "DATA:MANAGE");
-    createTestCommand("destroy index --member=server2", "DATA:MANAGE");
-    createTestCommand("list indexes", "CLUSTER:READ");
+    createTestCommand("clear defined indexes", dataManage);
+    createTestCommand("create defined indexes", dataManage);
+    createTestCommand("create index --name=myKeyIndex --expression=region1.Id --region=region1 --type=key", dataManage);
+    createTestCommand("define index --name=myIndex1 --expression=exp1 --region=/exampleRegion", dataManage);
+    createTestCommand("destroy index --member=server2", dataManage);
+    createTestCommand("list indexes", clusterRead);
 
     //LauncherLifecycleCommands
     createTestCommand("start jconsole", null);
@@ -145,38 +161,38 @@ public class TestCommand {
     createTestCommand("start vsd", null);
     createTestCommand("status locator", null);
     createTestCommand("status server", null);
-    //createTestCommand("stop locator --name=locator1", "CLUSTER:MANAGE");
-    //createTestCommand("stop server --name=server1", "CLUSTER:MANAGE");
+    //createTestCommand("stop locator --name=locator1", clusterManage);
+    //createTestCommand("stop server --name=server1", clusterManage);
 
     //MemberCommands
-    createTestCommand("describe member --name=server1", "CLUSTER:READ");
-    createTestCommand("list members", "CLUSTER:READ");
+    createTestCommand("describe member --name=server1", clusterRead);
+    createTestCommand("list members", clusterRead);
 
     // Misc Commands
-    createTestCommand("change loglevel --loglevel=severe --member=server1", "CLUSTER:WRITE");
-    createTestCommand("export logs --dir=data/logs", "CLUSTER:READ");
-    createTestCommand("export stack-traces --file=stack.txt", "CLUSTER:READ");
-    createTestCommand("gc", "CLUSTER:MANAGE");
-    createTestCommand("netstat --member=server1", "CLUSTER:READ");
-    createTestCommand("show dead-locks --file=deadlocks.txt", "CLUSTER:READ");
-    createTestCommand("show log --member=locator1 --lines=5", "CLUSTER:READ");
-    createTestCommand("show metrics", "CLUSTER:READ");
+    createTestCommand("change loglevel --loglevel=severe --member=server1", clusterWrite);
+    createTestCommand("export logs --dir=data/logs", clusterRead);
+    createTestCommand("export stack-traces --file=stack.txt", clusterRead);
+    createTestCommand("gc", clusterManage);
+    createTestCommand("netstat --member=server1", clusterRead);
+    createTestCommand("show dead-locks --file=deadlocks.txt", clusterRead);
+    createTestCommand("show log --member=locator1 --lines=5", clusterRead);
+    createTestCommand("show metrics", clusterRead);
 
 
     // PDX Commands
-    createTestCommand("configure pdx --read-serialized=true", "DATA:MANAGE");
-    //createTestCommand("pdx rename --old=com.gemstone --new=com.pivotal --disk-store=ds1 --disk-dirs=/diskDir1", "DATA:MANAGE");
+    createTestCommand("configure pdx --read-serialized=true", dataManage);
+    //createTestCommand("pdx rename --old=com.gemstone --new=com.pivotal --disk-store=ds1 --disk-dirs=/diskDir1", dataManage);
 
     // Queue Commands
-    createTestCommand("create async-event-queue --id=myAEQ --listener=myApp.myListener", "DATA:MANAGE");
-    createTestCommand("list async-event-queues", "CLUSTER:READ");
+    createTestCommand("create async-event-queue --id=myAEQ --listener=myApp.myListener", dataManage);
+    createTestCommand("list async-event-queues", clusterRead);
 
     //RegionCommands
-    createTestCommand("describe region --name=value", "CLUSTER:READ");
-    createTestCommand("list regions", "CLUSTER:READ");
+    createTestCommand("describe region --name=value", clusterRead);
+    createTestCommand("list regions", clusterRead);
 
     // StatusCommands
-    createTestCommand("status cluster-config-service", "CLUSTER:READ");
+    createTestCommand("status cluster-config-service", clusterRead);
 
     // Shell Commands
     createTestCommand("connect", null);
@@ -190,22 +206,22 @@ public class TestCommand {
 
 
     // WAN Commands
-    createTestCommand("create gateway-sender --id=sender1 --remote-distributed-system-id=2", "DATA:MANAGE");
-    createTestCommand("start gateway-sender --id=sender1", "DATA:MANAGE");
-    createTestCommand("pause gateway-sender --id=sender1", "DATA:MANAGE");
-    createTestCommand("resume gateway-sender --id=sender1", "DATA:MANAGE");
-    createTestCommand("stop gateway-sender --id=sender1", "DATA:MANAGE");
-    createTestCommand("load-balance gateway-sender --id=sender1", "DATA:MANAGE");
-    createTestCommand("list gateways", "CLUSTER:READ");
-    createTestCommand("create gateway-receiver", "DATA:MANAGE");
-    createTestCommand("start gateway-receiver", "DATA:MANAGE");
-    createTestCommand("stop gateway-receiver", "DATA:MANAGE");
-    createTestCommand("status gateway-receiver", "CLUSTER:READ");
-    createTestCommand("status gateway-sender --id=sender1", "CLUSTER:READ");
+    createTestCommand("create gateway-sender --id=sender1 --remote-distributed-system-id=2", dataManage);
+    createTestCommand("start gateway-sender --id=sender1", dataManage);
+    createTestCommand("pause gateway-sender --id=sender1", dataManage);
+    createTestCommand("resume gateway-sender --id=sender1", dataManage);
+    createTestCommand("stop gateway-sender --id=sender1", dataManage);
+    createTestCommand("load-balance gateway-sender --id=sender1", dataManage);
+    createTestCommand("list gateways", clusterRead);
+    createTestCommand("create gateway-receiver", dataManage);
+    createTestCommand("start gateway-receiver", dataManage);
+    createTestCommand("stop gateway-receiver", dataManage);
+    createTestCommand("status gateway-receiver", clusterRead);
+    createTestCommand("status gateway-sender --id=sender1", clusterRead);
 
     //ShellCommand
     createTestCommand("disconnect", null);
     //Misc commands
-    //createTestCommand("shutdown", "CLUSTER:MANAGE");
+    //createTestCommand("shutdown", clusterManage);
   };
 }

http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/7c38f0d8/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/auth3.json
----------------------------------------------------------------------
diff --git a/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/auth3.json b/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/auth3.json
index cfd43f5..635cff5 100644
--- a/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/auth3.json
+++ b/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/auth3.json
@@ -11,7 +11,7 @@
       "operationsAllowed": [
         "REGION:GET"
       ],
-      "region": "secureRegion"
+      "regions": "secureRegion"
     }
   ],
   "users": [

http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/7c38f0d8/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/cacheServer.json
----------------------------------------------------------------------
diff --git a/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/cacheServer.json b/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/cacheServer.json
index 01c9fd6..638ae07 100644
--- a/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/cacheServer.json
+++ b/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/cacheServer.json
@@ -76,16 +76,18 @@
     {
       "name": "region1-use",
       "operationsAllowed": [
-        "DATA"
+        "DATA:READ",
+        "DATA:WRITE"
       ],
-      "region": "region1"
+      "regions": "null,region1"
     },
     {
       "name": "secure-use",
       "operationsAllowed": [
-        "DATA"
+        "DATA:READ",
+        "DATA:WRITE"
       ],
-      "regions": ["region1", "secureRegion"]
+      "regions": "null,region1,secureRegion"
     }
   ],
   "users": [

http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/7c38f0d8/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/shiro-ini.json
----------------------------------------------------------------------
diff --git a/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/shiro-ini.json b/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/shiro-ini.json
new file mode 100644
index 0000000..d586fa1
--- /dev/null
+++ b/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/shiro-ini.json
@@ -0,0 +1,87 @@
+{
+  "roles": [
+    {
+      "name": "admin",
+      "operationsAllowed": [
+        "CLUSTER:MANAGE",
+        "CLUSTER:WRITE",
+        "CLUSTER:READ",
+        "DATA:MANAGE",
+        "DATA:WRITE",
+        "DATA:READ"
+      ]
+    },
+    {
+      "name": "readRegionA",
+      "operationsAllowed": [
+        "DATA:READ"
+      ],
+      "regions": "RegionA"
+    },
+    {
+      "name": "useRegionA",
+      "operationsAllowed": [
+        "DATA:MANAGE",
+        "DATA:WRITE",
+        "DATA:READ"
+      ],
+      "regions": "RegionA"
+    },
+    {
+      "name": "readData",
+      "operationsAllowed": [
+        "DATA:READ"
+      ]
+    },
+    {
+      "name": "readAll",
+      "operationsAllowed": [
+        "CLUSTER:READ",
+        "DATA:READ"
+      ]
+    }
+  ],
+  "users": [
+    {
+      "name": "root",
+      "password": "secret",
+      "roles": [
+        "admin"
+      ]
+    },
+    {
+      "name": "guest",
+      "password": "guest",
+      "roles": [
+      ]
+    },
+    {
+      "name": "regionAReader",
+      "password": "password",
+      "roles": [
+        "readRegionA"
+      ]
+    },
+    {
+      "name": "regionAUser",
+      "password": "password",
+      "roles": [
+        "useRegionA"
+      ]
+    },
+    {
+      "name": "dataReader",
+      "password": "12345",
+      "roles": [
+        "readData"
+      ]
+    },
+    {
+      "name": "reader",
+      "password": "12345",
+      "roles": [
+        "readAll"
+      ]
+    }
+  ]
+}

http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/7c38f0d8/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/testInheritRole.json
----------------------------------------------------------------------
diff --git a/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/testInheritRole.json b/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/testInheritRole.json
deleted file mode 100644
index 3053a92..0000000
--- a/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/testInheritRole.json
+++ /dev/null
@@ -1,40 +0,0 @@
-{
-"roles" : [	
-			{
-				"name" : "jmxReader",
-				"operationsAllowed" : ["QUERY"]				
-			},
-			{
-				"name" : "jmxWriter",
-				"operationsAllowed" : ["CHANGE_LOG_LEVEL"]				
-			},
-			{
-				"name" : "admin",
-				"operationsAllowed" : ["CMD_SHUTDOWN"]	
-			},
-			{
-				"name" : "adminSG1",
-				"inherit" : [ "admin" ],
-				"serverGroup" : "SG1"
-			},
-			{
-				"name" : "adminSG2",
-				"inherit" : [ "admin" , "jmxWriter"],
-				"serverGroup" : "SG2"
-			}
-		],
-users : [
-	 		{
-	 			"name" : "tushark",
-	 			"roles" : ["jmxReader"]
-	 		},
-	 		{
-	 			"name" : "admin1",
-	 			"roles" : ["adminSG1"]
-	 		},
-	 		{
-	 			"name" : "admin2",
-	 			"roles" : ["adminSG2"]
-	 		}
-		]
-}

http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/7c38f0d8/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/testSimpleUserAndRole.json
----------------------------------------------------------------------
diff --git a/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/testSimpleUserAndRole.json b/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/testSimpleUserAndRole.json
deleted file mode 100644
index 0542cf4..0000000
--- a/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/testSimpleUserAndRole.json
+++ /dev/null
@@ -1,18 +0,0 @@
-{
-  "roles": [
-    {
-      "name": "jmxReader",
-      "operationsAllowed": [
-        "QUERY:EXECUTE"
-      ]
-    }
-  ],
-  "users": [
-    {
-      "name": "tushark",
-      "roles": [
-        "jmxReader"
-      ]
-    }
-  ]
-}

http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/7c38f0d8/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/testUserAndRoleRegionServerGroup.json
----------------------------------------------------------------------
diff --git a/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/testUserAndRoleRegionServerGroup.json b/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/testUserAndRoleRegionServerGroup.json
deleted file mode 100644
index 6bb28bf..0000000
--- a/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/testUserAndRoleRegionServerGroup.json
+++ /dev/null
@@ -1,20 +0,0 @@
-{
-  "roles": [
-    {
-      "name": "jmxReader",
-      "operationsAllowed": [
-        "QUERY:EXECUTE"
-      ],
-      "serverGroup": "SG2",
-      "region": "secureRegion"
-    }
-  ],
-  "users": [
-    {
-      "name": "tushark",
-      "roles": [
-        "jmxReader"
-      ]
-    }
-  ]
-}

http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/7c38f0d8/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/testUserMultipleRole.json
----------------------------------------------------------------------
diff --git a/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/testUserMultipleRole.json b/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/testUserMultipleRole.json
deleted file mode 100644
index 7a07a21..0000000
--- a/geode-core/src/test/resources/com/gemstone/gemfire/management/internal/security/testUserMultipleRole.json
+++ /dev/null
@@ -1,26 +0,0 @@
-{
-  "roles": [
-    {
-      "name": "jmxReader",
-      "operationsAllowed": [
-        "QUERY:EXECUTE"
-      ]
-    },
-    {
-      "name": "sysMonitors",
-      "operationsAllowed": [
-        "MEMBER:EXPORT_LOGS",
-        "MEMBER:GC"
-      ]
-    }
-  ],
-  "users": [
-    {
-      "name": "tushark",
-      "roles": [
-        "jmxReader",
-        "sysMonitors"
-      ]
-    }
-  ]
-}

http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/7c38f0d8/geode-core/src/test/resources/shiro.ini
----------------------------------------------------------------------
diff --git a/geode-core/src/test/resources/shiro.ini b/geode-core/src/test/resources/shiro.ini
index 37b81b2..a9746a5 100644
--- a/geode-core/src/test/resources/shiro.ini
+++ b/geode-core/src/test/resources/shiro.ini
@@ -13,6 +13,8 @@
 # See the License for the specific language governing permissions and
 # limitations under the License.
 
+# the users and roles in this file needs to be kept in sync with shiro.ini
+# since they are used by the same test to test ShiroUtil
 # -----------------------------------------------------------------------------
 # Users and their (optional) assigned roles
 # username = password, role1, role2, ..., roleN
@@ -20,7 +22,10 @@
 [users]
 root = secret, admin
 guest = guest, guest
-stranger = 12345, none
+regionAReader = password, readRegionA
+regionAUser = password, useRegionA
+dataReader = 12345, readData
+reader = 12345, readAll
 
 # -----------------------------------------------------------------------------
 # Roles with assigned permissions
@@ -28,4 +33,8 @@ stranger = 12345, none
 # -----------------------------------------------------------------------------
 [roles]
 admin = *
-guest = none
\ No newline at end of file
+guest = none
+readRegionA = DATA:READ:RegionA
+useRegionA = *:*:RegionA
+readData = DATA:READ
+readAll = *:READ
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/7c38f0d8/geode-junit/src/main/java/com/gemstone/gemfire/test/junit/rules/DescribedExternalResource.java
----------------------------------------------------------------------
diff --git a/geode-junit/src/main/java/com/gemstone/gemfire/test/junit/rules/DescribedExternalResource.java b/geode-junit/src/main/java/com/gemstone/gemfire/test/junit/rules/DescribedExternalResource.java
index 543b7fc..b12bab1 100644
--- a/geode-junit/src/main/java/com/gemstone/gemfire/test/junit/rules/DescribedExternalResource.java
+++ b/geode-junit/src/main/java/com/gemstone/gemfire/test/junit/rules/DescribedExternalResource.java
@@ -14,18 +14,17 @@
  * See the License for the specific language governing permissions and
  * limitations under the License.
  */
-
-/**
- * this class extends the capability of JUnit's ExternalResource in that
- * it provides a Description object in the before and after methods, so that
- * the implementation would have access to the annotation of the test methods
- */
 package com.gemstone.gemfire.test.junit.rules;
 
 import org.junit.rules.TestRule;
 import org.junit.runner.Description;
 import org.junit.runners.model.Statement;
 
+/**
+ * this class extends the capability of JUnit's ExternalResource in that
+ * it provides a Description object in the before and after methods, so that
+ * the implementation would have access to the annotation of the test methods
+ */
 public class DescribedExternalResource implements TestRule {
   public Statement apply(Statement base, Description description) {
     return statement(base, description);

http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/7c38f0d8/geode-pulse/src/main/java/com/vmware/gemfire/tools/pulse/internal/security/GemFireAuthentication.java
----------------------------------------------------------------------
diff --git a/geode-pulse/src/main/java/com/vmware/gemfire/tools/pulse/internal/security/GemFireAuthentication.java b/geode-pulse/src/main/java/com/vmware/gemfire/tools/pulse/internal/security/GemFireAuthentication.java
index 5253f2f..a7a611d 100644
--- a/geode-pulse/src/main/java/com/vmware/gemfire/tools/pulse/internal/security/GemFireAuthentication.java
+++ b/geode-pulse/src/main/java/com/vmware/gemfire/tools/pulse/internal/security/GemFireAuthentication.java
@@ -14,9 +14,9 @@
  * See the License for the specific language governing permissions and
  * limitations under the License.
  */
+
 package com.vmware.gemfire.tools.pulse.internal.security;
 
-import java.io.IOException;
 import java.util.ArrayList;
 import java.util.Collection;
 import javax.management.MBeanServerConnection;
@@ -33,87 +33,59 @@ import org.springframework.security.core.authority.SimpleGrantedAuthority;
 
 /**
  * Spring security authentication object for GemFire
- * 
+ * <p>
  * To use GemFire Integrated Security Model set Spring Application Profile to pulse.authentication.gemfire
- * 
- * 1. Authentication : 
- *    1.a GemFire profile creates JMX connection with given credentials at the login time. 
- *    1.b Successful connect is considered as Successful Authentication for Pulse WebApp
- *    
- *    
+ * <p>
+ * 1. Authentication :
+ * 1.a GemFire profile creates JMX connection with given credentials at the login time.
+ * 1.b Successful connect is considered as Successful Authentication for Pulse WebApp
+ * <p>
+ * <p>
  * 2. Authorization :
- *    2.a Using newly created authenticated connection AccessControlMXBean is called to get authentication
- *      levels. See @See {@link #populateAuthorities(JMXConnector)}. This sets Spring Security Authorities
- *    2.b DataBrowser end-points are required to be authorized against Spring Granted Authority
- *      @See spring-security.xml
- *    2.c When executing Data-Browser query, user-level jmx connection is used so at to put access-control
- *      over the resources query is accessing. 
- *      @See #com.vmware.gemfire.tools.pulse.internal.data.JMXDataUpdater#executeQuery
- *         
- * 3. Connection Management - Spring Security LogoutHandler closes session level connection
- *
- * TODO : Better model would be to maintain background connection map for Databrowser instead
- * of each web session creating rmi connection and map user to correct entry in the connection map
- *
+ * 2.a Using newly created authenticated connection AccessControlMXBean is called to get authentication
+ * levels. See @See {@link #populateAuthorities(JMXConnector)}. This sets Spring Security Authorities
+ * 2.b DataBrowser end-points are required to be authorized against Spring Granted Authority
  * @since version 9.0
  */
-public class GemFireAuthentication extends UsernamePasswordAuthenticationToken {	
+public class GemFireAuthentication extends UsernamePasswordAuthenticationToken {
 
   private final static PulseLogWriter logger = PulseLogWriter.getLogger();
-  
-	private JMXConnector jmxc=null;	
-	
-	public GemFireAuthentication(Object principal, Object credentials, Collection<GrantedAuthority> list, JMXConnector jmxc) {
-		super(principal, credentials, list);
-		this.jmxc = jmxc;
-	}
 
-	private static final long serialVersionUID = SpringSecurityCoreVersion.SERIAL_VERSION_UID;
-		
-	
-	public void closeJMXConnection(){
-		try {
-			jmxc.close();
-		} catch (IOException e) {
-			throw new RuntimeException(e);
-		}
-	}
-	
-	public MBeanServerConnection getRemoteMBeanServer() {
-		try {
-			return jmxc.getMBeanServerConnection();
-		} catch (IOException e) {
-			throw new RuntimeException(e);
-		}
-	}
+  private JMXConnector jmxc = null;
+
+  public GemFireAuthentication(Object principal, Object credentials, Collection<GrantedAuthority> list, JMXConnector jmxc) {
+    super(principal, credentials, list);
+    this.jmxc = jmxc;
+  }
+
+  private static final long serialVersionUID = SpringSecurityCoreVersion.SERIAL_VERSION_UID;
 
-	public static ArrayList<GrantedAuthority> populateAuthorities(JMXConnector jmxc) {
-		ObjectName name;
-		ArrayList<GrantedAuthority> authorities = new ArrayList<>();
-		try {
-			name = new ObjectName(PulseConstants.OBJECT_NAME_ACCESSCONTROL_MBEAN);
-			MBeanServerConnection mbeanServer = jmxc.getMBeanServerConnection();
+  public static ArrayList<GrantedAuthority> populateAuthorities(JMXConnector jmxc) {
+    ObjectName name;
+    ArrayList<GrantedAuthority> authorities = new ArrayList<>();
+    try {
+      name = new ObjectName(PulseConstants.OBJECT_NAME_ACCESSCONTROL_MBEAN);
+      MBeanServerConnection mbeanServer = jmxc.getMBeanServerConnection();
 
-			for(String role : PulseConstants.PULSE_ROLES){
-				Object[] params = role.split(":");
-				String[] signature = new String[] {String.class.getCanonicalName(), String.class.getCanonicalName()};
-				boolean result = (Boolean)mbeanServer.invoke(name, "authorize", params, signature);
-				if(result){
-					authorities.add(new SimpleGrantedAuthority(role));
-				}
-			}
-		}catch (Exception e){
-			throw new RuntimeException(e.getMessage(), e);
-		}
+      for (String role : PulseConstants.PULSE_ROLES) {
+        Object[] params = role.split(":");
+        String[] signature = new String[] { String.class.getCanonicalName(), String.class.getCanonicalName() };
+        boolean result = (Boolean) mbeanServer.invoke(name, "authorize", params, signature);
+        if (result) {
+          authorities.add(new SimpleGrantedAuthority(role));
+        }
+      }
+    }
+    catch (Exception e) {
+      throw new RuntimeException(e.getMessage(), e);
+    }
 
-		return authorities;
+    return authorities;
 
-	}
+  }
 
-	public JMXConnector getJmxc() {
-		return jmxc;
-	}
-	
-	
+  public JMXConnector getJmxc() {
+    return jmxc;
+  }
 
 }

http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/7c38f0d8/geode-pulse/src/main/java/com/vmware/gemfire/tools/pulse/internal/security/GemFireAuthenticationProvider.java
----------------------------------------------------------------------
diff --git a/geode-pulse/src/main/java/com/vmware/gemfire/tools/pulse/internal/security/GemFireAuthenticationProvider.java b/geode-pulse/src/main/java/com/vmware/gemfire/tools/pulse/internal/security/GemFireAuthenticationProvider.java
index 548c3a5..ee263b1 100644
--- a/geode-pulse/src/main/java/com/vmware/gemfire/tools/pulse/internal/security/GemFireAuthenticationProvider.java
+++ b/geode-pulse/src/main/java/com/vmware/gemfire/tools/pulse/internal/security/GemFireAuthenticationProvider.java
@@ -16,8 +16,12 @@
  */
 package com.vmware.gemfire.tools.pulse.internal.security;
 
+import java.util.Collection;
+import javax.management.remote.JMXConnector;
+
 import com.vmware.gemfire.tools.pulse.internal.data.Repository;
 import com.vmware.gemfire.tools.pulse.internal.log.PulseLogWriter;
+
 import org.springframework.security.authentication.AuthenticationProvider;
 import org.springframework.security.authentication.AuthenticationServiceException;
 import org.springframework.security.authentication.BadCredentialsException;
@@ -26,14 +30,9 @@ import org.springframework.security.core.Authentication;
 import org.springframework.security.core.AuthenticationException;
 import org.springframework.security.core.GrantedAuthority;
 
-import javax.management.remote.JMXConnector;
-import java.util.Collection;
-
 /**
  * Spring security AuthenticationProvider for GemFire. It connects to gemfire manager using given credentials.
  * Successful connect is treated as successful authentication and web user is authenticated
- *
- * @author Tushar Khairnar
  * @since version 9.0
  */
 public class GemFireAuthenticationProvider implements AuthenticationProvider {

http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/7c38f0d8/geode-pulse/src/main/java/com/vmware/gemfire/tools/pulse/internal/security/LogoutHandler.java
----------------------------------------------------------------------
diff --git a/geode-pulse/src/main/java/com/vmware/gemfire/tools/pulse/internal/security/LogoutHandler.java b/geode-pulse/src/main/java/com/vmware/gemfire/tools/pulse/internal/security/LogoutHandler.java
index a70925d..7309f90 100644
--- a/geode-pulse/src/main/java/com/vmware/gemfire/tools/pulse/internal/security/LogoutHandler.java
+++ b/geode-pulse/src/main/java/com/vmware/gemfire/tools/pulse/internal/security/LogoutHandler.java
@@ -16,20 +16,20 @@
  */
 package com.vmware.gemfire.tools.pulse.internal.security;
 
+import java.io.IOException;
+import javax.servlet.ServletException;
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+
 import com.vmware.gemfire.tools.pulse.internal.data.Repository;
 import com.vmware.gemfire.tools.pulse.internal.log.PulseLogWriter;
+
 import org.springframework.security.core.Authentication;
 import org.springframework.security.web.authentication.logout.LogoutSuccessHandler;
 import org.springframework.security.web.authentication.logout.SimpleUrlLogoutSuccessHandler;
 
-import javax.servlet.ServletException;
-import javax.servlet.http.HttpServletRequest;
-import javax.servlet.http.HttpServletResponse;
-import java.io.IOException;
-
 /**
  * Handler is used to close jmx connection maintained at user-level
- * @author tushark
  *
  */
 public class LogoutHandler extends SimpleUrlLogoutSuccessHandler implements LogoutSuccessHandler {