springmvc整合shiro权限控制

一、什么是Shiro  
Apache Shiro是一个强大易用的Java安全框架,提供了认证、授权、加密和会话管理等功能: 
  • 认证 - 用户身份识别,常被称为用户“登录”;
  • 授权 - 访问控制;
  • 密码加密 - 保护或隐藏数据防止被偷窥;
  • 会话管理 - 每用户相关的时间敏感的状态。

对于任何一个应用程序,Shiro都可以提供全面的安全管理服务。并且相对于其他安全框架,Shiro要简单的多。


二:springmvc整合shiro

    1,在web.xml中加入如下配置

   

  
  
  
  
    

    


    
        shiroFilter
        org.springframework.web.filter.DelegatingFilterProxy
        true
        
            targetFilterLifecycle
            true
        
    

    
        shiroFilter
        /*
        REQUEST
	
	

2,配置applicationContext.xml

 

  
  



    
        
    

    
    
        
        
        
        
    

    
    
        
        
        
        
        
        
    

    
    

    
    
        
        
        
    

    
        
        
        
    

    
    
        
        
        
    

    
    
        
        
    

    
    
        
        
    

    
    
        
        
        
        
        
        
        
    

    
    
        
        
        
        
    

    
    
        
        
    

    
    

	 
         
     
    

    
    
        
        
        
        
            
                
                
                
            
        
        
                        	
               	/**/*.js=anon
                /**/*.img=anon
                /**/*.css=anon
                /**/*.png=anon
                /**/*.gif=anon
                /**/*.jpg=anon
                /static/**=anon
                /admin/logout.do = logout
                /admin/login.do = authc
                /authenticated = authc
                /** = authc,user,sysUser         
            
        
    

    
    

       

securityManager:这个属性是必须的。

loginUrl:没有登录的用户请求需要登录的页面时自动跳转到登录页面,不是必须的属性,不输入地址的话会自动寻找项目web项目的根目录下的”/login.jsp页面。

successUrl:登录成功默认跳转页面,不配置则跳转至”/”。如果登陆前点击的一个需要登录的页面,则在登录自动跳转到那个需要登录的页面。不跳转到此。

unauthorizedUrl:没有权限默认跳转的页面。

3, 自定义的Realm类

    

     

import java.util.HashSet;
import java.util.Set;

import javax.annotation.Resource;

import org.apache.shiro.authc.AuthenticationException;
import org.apache.shiro.authc.AuthenticationInfo;
import org.apache.shiro.authc.AuthenticationToken;
import org.apache.shiro.authc.LockedAccountException;
import org.apache.shiro.authc.SimpleAuthenticationInfo;
import org.apache.shiro.authc.UnknownAccountException;
import org.apache.shiro.authz.AuthorizationInfo;
import org.apache.shiro.authz.SimpleAuthorizationInfo;
import org.apache.shiro.realm.AuthorizingRealm;
import org.apache.shiro.subject.PrincipalCollection;
import org.apache.shiro.util.ByteSource;


public class UserRealm extends AuthorizingRealm {

    @Resource
    private UserService userService;
		
		//这是授权方法  
    @Override
    protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principals) {
        String username = (String)principals.getPrimaryPrincipal();
        SimpleAuthorizationInfo authorizationInfo = new SimpleAuthorizationInfo();
        Set permissionsSet = null;
        Set permissionsSetStr = new HashSet();
        try {
        	
			authorizationInfo.setRoles(userService.findRoles(username));
			permissionsSet = userService.findPermissions(username);
        	for(String perStr:permissionsSet) {
        		if(perStr.indexOf("*")<0) {
        			permissionsSetStr.add(perStr);
        		}
        	}
			authorizationInfo.setStringPermissions(permissionsSetStr);
		} catch (Exception e) {
			e.printStackTrace();
		}
        return authorizationInfo;
    }

    //这是认证方法 
    @Override
    protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken token) throws AuthenticationException {

        String username = (String)token.getPrincipal();
        UserVo userVo = null;
        SimpleAuthenticationInfo authenticationInfo = null;
		try {
			userVo = userService.findByUsername(username);
			if(userVo == null) {
	            throw new UnknownAccountException();//没找到帐号
	        }
	        if(userVo.getLocked()==0) {
	            throw new LockedAccountException(); //帐号锁定
	        }
	        //交给AuthenticatingRealm使用CredentialsMatcher进行密码匹配
	        authenticationInfo = new SimpleAuthenticationInfo(
	        		userVo.getUsername(), //用户名
	        		userVo.getPassword(), //密码
	                ByteSource.Util.bytes(userVo.getCredentialsSalt()),//salt=username+salt
	                getName()  //realm name
	        );
		} catch (Exception e) {
			e.printStackTrace();
		}
     
        return authenticationInfo;
    }

    @Override
    public void clearCachedAuthorizationInfo(PrincipalCollection principals) {
        super.clearCachedAuthorizationInfo(principals);
    }

    @Override
    public void clearCachedAuthenticationInfo(PrincipalCollection principals) {
        super.clearCachedAuthenticationInfo(principals);
    }

    @Override
    public void clearCache(PrincipalCollection principals) {
        super.clearCache(principals);
    }

    public void clearAllCachedAuthorizationInfo() {
        getAuthorizationCache().clear();
    }

    public void clearAllCachedAuthenticationInfo() {
        getAuthenticationCache().clear();
    }

    public void clearAllCache() {
        clearAllCachedAuthenticationInfo();
        clearAllCachedAuthorizationInfo();
    }

}

4,controller层实例   

@RequiresPermissions

例如: @RequiresPermissions({"file:read", "write:aFile.txt"} )
  
void someMethod();

要求subject中必须同时含有file:readwrite:aFile.txt的权限才能执行方法someMethod()。否则抛出异常AuthorizationException

  

    @RequiresPermissions("sys:user:add")//此处就是控制权限的注解
    @RequestMapping(value = "/add", method = RequestMethod.POST)
    public ModelAndView addUser(){
    	ModelAndView mav = new ModelAndView("user/add");
    	List roleList = userService.add();
    	mav.addObject("roleList", roleList);
        return mav;
    }

5,jsp处控制

  <%@ taglib prefix="shiro" uri="http://shiro.apache.org/tags" %>//引入标签




6.

默认,添加或删除用户的角色 或资源 ,系统不需要重启,但是需要用户重新登录。

即用户的授权是首次登录后第一次访问需要权限页面时进行加载。

但是需要进行控制的权限资源,是在启动时就进行加载,如果要新增一个权限资源需要重启系统。

7.

Springsecurity apache shiro差别:

a) shiro 配置更加容易理解,容易上手; security 配置相对比较难懂。
b) spring 的环境下, security 整合性更好。 Shiro 对很多其他的框架兼容性更好,号称是无缝集成。
c) shiro 不仅仅可以使用在 web 中,它可以工作在任何应用环境中。
d) 在集群会话时 Shiro 最重要的一个好处或许就是它的会话是独立于容器的。
e) Shiro 提供的密码加密使用起来非常方便。

8.

控制精度:

注解方式控制权限只能是在方法上控制,无法控制类级别访问。

过滤器方式控制是根据访问的URL进行控制。允许使用*匹配URL,所以可以进行粗粒度,也可以进行细粒度控制。



你可能感兴趣的:(java)