[
https://issues.apache.org/jira/browse/SHIRO-459?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=13771949#comment-13771949
]
Daniel Bimschas commented on SHIRO-459:
---------------------------------------
Here's a simple straight-forward implementation for the issue:
{code:title=HttpMethodRolesAuthorizationFilter.java|borderStyle=solid}
package org.apache.shiro.web.filter.authz;
import org.apache.shiro.subject.Subject;
import org.apache.shiro.web.filter.authz.RolesAuthorizationFilter;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import java.io.IOException;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Map;
import java.util.Set;
import static java.util.Collections.addAll;
public class HttpMethodRolesAuthorizationFilter extends
RolesAuthorizationFilter {
private static enum HttpMethod {
GET, DELETE, HEAD, MKCOL, OPTIONS, POST, PUT, TRACE;
@Override
public String toString() {
return super.toString().toLowerCase();
}
public static HttpMethod parse(String method) {
for (HttpMethod httpMethod : values()) {
if
(httpMethod.toString().equals(method.toLowerCase())) {
return httpMethod;
}
}
throw new IllegalArgumentException("Unknown HTTP
method: " + method);
}
}
@Override
public boolean isAccessAllowed(ServletRequest request, ServletResponse
response, Object mappedValue) throws
IOException {
Subject subject = getSubject(request, response);
String[] rolesArray = (String[]) mappedValue;
if (rolesArray == null || rolesArray.length == 0) {
//no roles specified, so nothing to check - allow
access.
return true;
}
final Map<HttpMethod, Set<String>> methodToRolesMapping = new
HashMap<HttpMethod, Set<String>>();
for (String rolesEntry : rolesArray) {
final String[] kv = rolesEntry.split("=");
final HttpMethod httpMethod = HttpMethod.parse(kv[0]);
final String[] roles = kv[1].split("&");
final HashSet<String> rolesSet = new
HashSet<String>(roles.length);
addAll(rolesSet, roles);
methodToRolesMapping.put(httpMethod, rolesSet);
}
final HttpMethod requestMethod =
HttpMethod.parse(((HttpServletRequest) request).getMethod());
final Set<String> roleIdentifiers =
methodToRolesMapping.get(requestMethod);
return roleIdentifiers == null ||
subject.hasAllRoles(roleIdentifiers);
}
}
{code}
> Support role-based authorization depending on HTTP request method
> -----------------------------------------------------------------
>
> Key: SHIRO-459
> URL: https://issues.apache.org/jira/browse/SHIRO-459
> Project: Shiro
> Issue Type: New Feature
> Components: Authorization (access control)
> Affects Versions: 1.2.2
> Reporter: Daniel Bimschas
> Priority: Minor
> Labels: features, newbie
>
> Below is a copy+paste from the Shiro users mailing list:
> =====================
> Dear Shiro gods!
> I'm struggling to figure out how I can do role-based authorization depending
> on what HTTP method a request is using. I've posted this question on
> StackOverflow as it seems nobody has been asking it before (at least I
> couldn't find it with my search terms). I would be incredibly happy if you
> could take a look!
> http://stackoverflow.com/questions/18824670/how-to-do-role-based-authorization-with-apache-shiro-depending-on-http-request-m
> Cheers
> Daniel Bimschas
> =============================
> Then, in a second mail I proposed a solution to the issue:
> =============================
> Digging into the Shiro source codes I found that this feature is in fact not
> available in Shiro. I've now implemented my own custom filter (extending
> RolesAuthorizationFilter) that allows you to do exactly what I wanted.
> Configuration for the filter follows the following example:
> [main]
> myFilter=my.package.HttpMethodRolesAuthorizationFilter
> [urls]
> /rest = authcBasic,
> myFilter[PUT=SERVICE_PROVIDER&EXPERIMENTER,POST=EXPERIMENTER,DELETE=ADMINISTRATOR]
> So, in this example
> - a user must be authenticated to execute any operation
> - a user with both roles SERVICE_PROVIDER and EXPERIMENTER can send a PUT
> request,
> - a user with role EXPERIMENTER can send POST requests, and
> - a user with role ADMINISTRATOR can DELETE things
> I would be more than happy to contribute this little bit of code to the
> project in case you're interested!
> =============================
--
This message is automatically generated by JIRA.
If you think it was sent incorrectly, please contact your JIRA administrators
For more information on JIRA, see: http://www.atlassian.com/software/jira