springboot集成shiro 前后端分离

前后端分离情况下 首先考虑是否跨域,如果没有跨域是可以使用shiro原生的session+cookie,无需特别处理。

如果涉及到跨域则需要考虑cookie问题(本质上也是重写shiro获取JESSIONID的地方即可)

登陆的时候将生成的的sessionId返回给前端,前端保存之后放在header里面即可,以后请求的时候加一个token,这个字段就是保存的sessionId

@PostMapping("/login")
    public ResultVO login(User user){
        Map<String,String> map = Maps.newHashMap();
        Subject subject = SecurityUtils.getSubject();
        UsernamePasswordToken usernamePasswordToken = new UsernamePasswordToken(user.getUserName(),user.getPassword());
        try{
            subject.login(usernamePasswordToken);
            String sessionId = (String) subject.getSession().getId();
            map.put("sessionId",sessionId);
        }catch (Exception e){
            log.error(e.getMessage());
        }

        return ResultVOUtil.success(map);
    }

 

重写DefaultWebSessionManager获取sessionId的方法

        public class MySessionManager extends DefaultWebSessionManager {
        @Override
        protected Serializable getSessionId(ServletRequest request, ServletResponse response) {
            HttpServletRequest httpServletRequest = WebUtils.toHttp(request);
            String token = httpServletRequest.getHeader("token");
            System.out.println("token:"+token);
            if(!StringUtils.isEmpty(token)){
                request.setAttribute(ShiroHttpServletRequest.REFERENCED_SESSION_ID_SOURCE, "token");
                request.setAttribute(ShiroHttpServletRequest.REFERENCED_SESSION_ID, token);
                request.setAttribute(ShiroHttpServletRequest.REFERENCED_SESSION_ID_IS_VALID, Boolean.TRUE);
                return token;

            }else{
                return super.getSessionId(request, response);
            }
        }
    }

  完整代码见下

package com.palmdrive.lemon.config;

import com.palmdrive.lemon.filter.ShiroFormAuthenticationFilter;
import com.palmdrive.lemon.shiro.MyShiroRealm;
import com.palmdrive.lemon.util.CookieUtil;
import org.apache.shiro.mgt.SecurityManager;
import org.apache.shiro.session.mgt.SessionManager;
import org.apache.shiro.spring.web.ShiroFilterFactoryBean;
import org.apache.shiro.web.mgt.DefaultWebSecurityManager;
import org.apache.shiro.web.servlet.ShiroHttpServletRequest;
import org.apache.shiro.web.session.mgt.DefaultWebSessionManager;
import org.apache.shiro.web.util.WebUtils;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.util.StringUtils;
import org.springframework.web.servlet.HandlerExceptionResolver;
import org.springframework.web.servlet.ModelAndView;

import javax.servlet.Filter;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.Serializable;
import java.util.HashMap;
import java.util.LinkedHashMap;
import java.util.Map;

@Configuration
public class ShiroConfig {

    @Bean
    public ShiroFilterFactoryBean shirFilter(){
        System.out.println("shiro-------");
        ShiroFilterFactoryBean shiroFilterFactoryBean = new ShiroFilterFactoryBean();
        shiroFilterFactoryBean.setSecurityManager(securityManager());

        Map<String, Filter> filtersMap = new LinkedHashMap<>();
        filtersMap.put("shiroAuthc", new ShiroFormAuthenticationFilter());
        shiroFilterFactoryBean.setFilters(filtersMap);

        Map<String,String> map = new HashMap<String, String>();
        //对所有用户认证
        map.put("/admin/login", "anon");
        map.put("/seller/product/list", "shiroAuthc,perms[product:table:student:view]");
        map.put("/**","shiroAuthc");
        shiroFilterFactoryBean.setUnauthorizedUrl("/admin/unauth");

        shiroFilterFactoryBean.setFilterChainDefinitionMap(map);


        return shiroFilterFactoryBean;
    }

    @Bean
    public SecurityManager securityManager() {
        DefaultWebSecurityManager securityManager = new DefaultWebSecurityManager();
        securityManager.setRealm(myShiroRealm());
        // 自定义session管理 使用redis
        securityManager.setSessionManager(sessionManager());
        // 自定义缓存实现 使用redis
//        securityManager.setCacheManager(cacheManager());
        return securityManager;
    }


    @Bean
    public SessionManager sessionManager() {
        MySessionManager mySessionManager = new MySessionManager();
        return mySessionManager;
    }

    @Bean
    public MyShiroRealm myShiroRealm() {
        MyShiroRealm myShiroRealm = new MyShiroRealm();
        return myShiroRealm;
    }



        public class MySessionManager extends DefaultWebSessionManager {
        @Override
        protected Serializable getSessionId(ServletRequest request, ServletResponse response) {
            HttpServletRequest httpServletRequest = WebUtils.toHttp(request);
            String token = httpServletRequest.getHeader("token");
            System.out.println("token:"+token);
            if(!StringUtils.isEmpty(token)){
                request.setAttribute(ShiroHttpServletRequest.REFERENCED_SESSION_ID_SOURCE, "token");
                request.setAttribute(ShiroHttpServletRequest.REFERENCED_SESSION_ID, token);
                request.setAttribute(ShiroHttpServletRequest.REFERENCED_SESSION_ID_IS_VALID, Boolean.TRUE);
                return token;

            }else{
                return super.getSessionId(request, response);
            }
//            if(CookieUtil.get(httpServletRequest,"JSESSIONID") != null){
//                System.out.println(CookieUtil.get(httpServletRequest,"JSESSIONID").getValue());
//            }
        }
    }

}

  

  

 

posted @ 2018-07-05 17:09  cshhs  阅读(10438)  评论(0编辑  收藏  举报