Repository: zeppelin
Updated Branches:
  refs/heads/master 767a50b41 -> d45d878a1


[ZEPPELIN-2913] Support for both user and role for AuthorizationFilter

Currently, Zeppelin only supports roles for AuthorizationFilter, but there can 
be a condition as described in 
https://issues.apache.org/jira/browse/ZEPPELIN-2913 where Zeppelin's user does 
not belong to a group/role, and the administrator wants to have control using 
user only.

[Feature]

* [x] - Add documentation

* https://issues.apache.org/jira/browse/ZEPPELIN-2913

add the following in shiro.ini:
```
[main]
...
anyofroles = org.apache.zeppelin.utils.AnyOfRolesUserAuthorizationFilter

[urls]
...
/api/interpreter/** = authc, anyofroles[admin, user1]
/api/configurations/** = authc, roles[admin]
/api/credential/** = authc, roles[admin]
```
With the above config both user (user1) and users the belong to role admin will 
have access to interpreter setting page.

Author: Prabhjyot Singh <prabhjyotsi...@gmail.com>

Closes #3004 from prabhjyotsingh/ZEPPELIN-2913 and squashes the following 
commits:

e05d72a9f [Prabhjyot Singh] rename AnyOfRolesAuthorizationFilter to 
AnyOfRolesUserAuthorizationFilter
724192ff4 [Prabhjyot Singh] add doc
53c0c034a [Prabhjyot Singh] [ZEPPELIN-2913] support for both user and role

Change-Id: I63cdebf66d76a67cfca0054283c7d1c65a9b5805


Project: http://git-wip-us.apache.org/repos/asf/zeppelin/repo
Commit: http://git-wip-us.apache.org/repos/asf/zeppelin/commit/d45d878a
Tree: http://git-wip-us.apache.org/repos/asf/zeppelin/tree/d45d878a
Diff: http://git-wip-us.apache.org/repos/asf/zeppelin/diff/d45d878a

Branch: refs/heads/master
Commit: d45d878a162d1012900f2de90314603a33323c5d
Parents: 767a50b
Author: Prabhjyot Singh <prabhjyotsi...@gmail.com>
Authored: Wed Jun 6 09:11:52 2018 +0530
Committer: Prabhjyot Singh <prabhjyotsi...@gmail.com>
Committed: Thu Jun 7 15:10:10 2018 +0530

----------------------------------------------------------------------
 docs/setup/security/shiro_authentication.md     |  8 +--
 .../zeppelin/integration/AuthenticationIT.java  |  8 +--
 .../utils/AnyOfRolesAuthorizationFilter.java    | 52 --------------------
 .../AnyOfRolesUserAuthorizationFilter.java      | 50 +++++++++++++++++++
 4 files changed, 59 insertions(+), 59 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/zeppelin/blob/d45d878a/docs/setup/security/shiro_authentication.md
----------------------------------------------------------------------
diff --git a/docs/setup/security/shiro_authentication.md 
b/docs/setup/security/shiro_authentication.md
index a51f77e..49b06c1 100644
--- a/docs/setup/security/shiro_authentication.md
+++ b/docs/setup/security/shiro_authentication.md
@@ -273,14 +273,16 @@ By default, Shiro will allow access to a URL if only user 
is part of "**all the
 /api/interpreter/** = authc, roles[admin, role1]
 ```
 
-If there is a need that user with "**any of the defined roles**" should be 
allowed, then following Shiro configuration can be used:
+### Apply multiple roles or user in Shiro configuration
+If there is a need that user with "**any of the defined roles or user 
itself**" should be allowed, then following Shiro configuration can be used:
+
 ```
 [main]
-anyofroles = org.apache.zeppelin.utils.AnyOfRolesAuthorizationFilter
+anyofrolesuser = org.apache.zeppelin.utils.AnyOfRolesUserAuthorizationFilter
 
 [urls]
 
-/api/interpreter/** = authc, anyofroles[admin, role1]
+/api/interpreter/** = authc, anyofrolesuser[admin, user1]
 /api/configurations/** = authc, roles[admin]
 /api/credential/** = authc, roles[admin]
 ```

http://git-wip-us.apache.org/repos/asf/zeppelin/blob/d45d878a/zeppelin-integration/src/test/java/org/apache/zeppelin/integration/AuthenticationIT.java
----------------------------------------------------------------------
diff --git 
a/zeppelin-integration/src/test/java/org/apache/zeppelin/integration/AuthenticationIT.java
 
b/zeppelin-integration/src/test/java/org/apache/zeppelin/integration/AuthenticationIT.java
index 4c194f3..ea6ad69 100644
--- 
a/zeppelin-integration/src/test/java/org/apache/zeppelin/integration/AuthenticationIT.java
+++ 
b/zeppelin-integration/src/test/java/org/apache/zeppelin/integration/AuthenticationIT.java
@@ -63,14 +63,14 @@ public class AuthenticationIT extends AbstractZeppelinIT {
       "securityManager.sessionManager = $sessionManager\n" +
       "securityManager.sessionManager.globalSessionTimeout = 86400000\n" +
       "shiro.loginUrl = /api/login\n" +
-      "anyofroles = org.apache.zeppelin.utils.AnyOfRolesAuthorizationFilter\n" 
+
+      "anyofrolesuser = 
org.apache.zeppelin.utils.AnyOfRolesUserAuthorizationFilter\n" +
       "[roles]\n" +
       "admin = *\n" +
       "hr = *\n" +
       "finance = *\n" +
       "[urls]\n" +
       "/api/version = anon\n" +
-      "/api/interpreter/** = authc, anyofroles[admin, finance]\n" +
+      "/api/interpreter/** = authc, anyofrolesuser[admin, finance]\n" +
       "/** = authc";
 
   static String originalShiro = "";
@@ -172,7 +172,7 @@ public class AuthenticationIT extends AbstractZeppelinIT {
   }
 
   @Test
-  public void testAnyOfRoles() throws Exception {
+  public void testAnyOfRolesUser() throws Exception {
     try {
       AuthenticationIT authenticationIT = new AuthenticationIT();
       authenticationIT.authenticationUser("admin", "password1");
@@ -220,7 +220,7 @@ public class AuthenticationIT extends AbstractZeppelinIT {
       authenticationIT.logoutUser("hr1");
 
     } catch (Exception e) {
-      handleException("Exception in AuthenticationIT while testAnyOfRoles ", 
e);
+      handleException("Exception in AuthenticationIT while testAnyOfRolesUser 
", e);
     }
   }
 

http://git-wip-us.apache.org/repos/asf/zeppelin/blob/d45d878a/zeppelin-server/src/main/java/org/apache/zeppelin/utils/AnyOfRolesAuthorizationFilter.java
----------------------------------------------------------------------
diff --git 
a/zeppelin-server/src/main/java/org/apache/zeppelin/utils/AnyOfRolesAuthorizationFilter.java
 
b/zeppelin-server/src/main/java/org/apache/zeppelin/utils/AnyOfRolesAuthorizationFilter.java
deleted file mode 100644
index 61fa0b5..0000000
--- 
a/zeppelin-server/src/main/java/org/apache/zeppelin/utils/AnyOfRolesAuthorizationFilter.java
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- * 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 org.apache.zeppelin.utils;
-
-import org.apache.shiro.subject.Subject;
-import org.apache.shiro.web.filter.authz.RolesAuthorizationFilter;
-
-import java.io.IOException;
-
-import javax.servlet.ServletRequest;
-import javax.servlet.ServletResponse;
-
-/**
- * Allows access if current user has at least one role of the specified list.
- * <p>
- * Basically, it's the same as {@link RolesAuthorizationFilter} but using 
{@literal OR} instead
- * of {@literal AND} on the specified roles.
- */
-public class AnyOfRolesAuthorizationFilter extends RolesAuthorizationFilter {
-  @Override
-  public boolean isAccessAllowed(ServletRequest request, ServletResponse 
response,
-          Object mappedValue) throws IOException {
-    final Subject subject = getSubject(request, response);
-    final String[] rolesArray = (String[]) mappedValue;
-
-    if (rolesArray == null || rolesArray.length == 0) {
-      //no roles specified, so nothing to check - allow access.
-      return true;
-    }
-
-    for (String roleName : rolesArray) {
-      if (subject.hasRole(roleName)) {
-        return true;
-      }
-    }
-    return false;
-  }
-}

http://git-wip-us.apache.org/repos/asf/zeppelin/blob/d45d878a/zeppelin-server/src/main/java/org/apache/zeppelin/utils/AnyOfRolesUserAuthorizationFilter.java
----------------------------------------------------------------------
diff --git 
a/zeppelin-server/src/main/java/org/apache/zeppelin/utils/AnyOfRolesUserAuthorizationFilter.java
 
b/zeppelin-server/src/main/java/org/apache/zeppelin/utils/AnyOfRolesUserAuthorizationFilter.java
new file mode 100644
index 0000000..e345dd6
--- /dev/null
+++ 
b/zeppelin-server/src/main/java/org/apache/zeppelin/utils/AnyOfRolesUserAuthorizationFilter.java
@@ -0,0 +1,50 @@
+/*
+ * 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 org.apache.zeppelin.utils;
+
+import java.io.IOException;
+import javax.servlet.ServletRequest;
+import javax.servlet.ServletResponse;
+import org.apache.shiro.subject.Subject;
+import org.apache.shiro.web.filter.authz.RolesAuthorizationFilter;
+
+/**
+ * Allows access if current user has at least one role of the specified list.
+ * <p>
+ * Basically, it's the same as {@link RolesAuthorizationFilter} but using 
{@literal OR} instead
+ * of {@literal AND} on the specified roles or user.
+ */
+public class AnyOfRolesUserAuthorizationFilter extends 
RolesAuthorizationFilter {
+  @Override
+  public boolean isAccessAllowed(ServletRequest request, ServletResponse 
response,
+          Object mappedValue) throws IOException {
+    final Subject subject = getSubject(request, response);
+    final String[] rolesArray = (String[]) mappedValue;
+
+    if (rolesArray == null || rolesArray.length == 0) {
+      //no roles specified, so nothing to check - allow access.
+      return true;
+    }
+
+    for (String roleName : rolesArray) {
+      if (subject.hasRole(roleName) || 
subject.getPrincipal().equals(roleName)) {
+        return true;
+      }
+    }
+    return false;
+  }
+}

Reply via email to