在springmvc.xml文件中配置拦截器
AuthorizationInterceptor">
2. 定义@Authorization注解
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface Authorization {
}
3.
AuthorizationInterceptor实现类
public class AuthorizationInterceptor implements HandlerInterceptor {
@Autowired
private TokenManager tokenManager;
@Autowired
private RoleService roleService;
@Override
public boolean preHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object handler) throws Exception {
//如果不是映射到方法直接通过
if (!(handler instanceof HandlerMethod)) {
return true;
}
HandlerMethod handlerMethod = (HandlerMethod) handler;
Method method = handlerMethod.getMethod();
//从header中得到token
String authorization = httpServletRequest.getHeader(Constants.AUTHORIZATION);
//System.out.println("authorization = " + authorization);
//验证token
TokenModel model = tokenManager.getToken(authorization);
if (tokenManager.checkToken(model)) {
//如果token验证成功,将token对应的用户id存在request中,便于之后注入
httpServletRequest.setAttribute(Constants.CURRENT_USER_ID, model.getUserId());
/*权限校验开始
//请求路径
String servletPath = httpServletRequest.getServletPath();
//查询是否有该权限
Function function = roleService.selectFunc(model.getUserId(),servletPath);
if(null == function){
httpServletResponse.setCharacterEncoding("UTF-8");
httpServletResponse.setContentType("text/x-json;charset=UTF-8");
解决跨域问题
httpServletResponse.setHeader("Access-Control-Allow-Origin", httpServletRequest.getHeader("origin"));
JSONObject jsObject =JSONObject.fromObject(new JsonResult(false, "权限不足", ""));
httpServletResponse.getWriter().write(jsObject.toString());
//httpServletResponse.getOutputStream().write(jsObject.toString().getBytes("UTF8"));
//httpServletResponse.getOutputStream().close();
return false;
}
权限校验结束*/
return true;
}
//如果验证token失败,并且方法注明了Authorization,返回401错误
if (method.getAnnotation(Authorization.class) != null) {
httpServletResponse.setStatus(HttpServletResponse.SC_UNAUTHORIZED);
return false;
}
return true;
}
@Override
public void postHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, ModelAndView modelAndView) throws Exception {
}
@Override
public void afterCompletion(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, Exception e) throws Exception {
}
}
4.在controller类中使用注解
@Controller
@CrossOrigin
@RequestMapping("Evaluate")
public class EvaluateController {
@Resource
private EvaluateService evaluateService;
// 添加评估记录
@Authorization
@ResponseBody
@RequestMapping(value = "/EvaluateAdd", method = RequestMethod.POST)
public JsonResult evaluateAdd(@CurrentUser User loginUser,
@Validated(value = { EvaluateValid.class }) Evaluate evaluate,BindingResult br) {
String[] validateParam = { "oldmanId", "evaluateType", "evaluateDate",
"evaluator", "result", "picture" };
Map errorMap = ValidateUtil.getErrorMap(br,
validateParam);
if (errorMap != null && errorMap.size() != 0) {
/* 返回参数校验错误详情 */
return new JsonResult(false, "添加评估记录参数错误", errorMap);
}
Evaluate evaluate1 = evaluateService.selectByOldManId(evaluate);
if(!(null == evaluate1)){
return new JsonResult(false, "该老人该类型的评估记录数据已存在", 0);
}
evaluate.setModifier(loginUser.getUserid());
evaluate.setHomeId(loginUser.getHomeid());
int n = evaluateService.insert(evaluate);
if (n <= 0) {
return new JsonResult(false, "添加失败", n);
}
return new JsonResult(true, "添加成功", n);
}
在做权限拦截时遇到了一个问题:关于报错:java.lang.IllegalStateException: getWriter() has already been called for this
原因:在同一次请求中,getWriter 和getOutputStream不能同时使用;该场景在权限认证使用了getWriter方法 ,但是在 controller中的注解@ResponseBody默认使用的是Response.getOutputStream方法
解决方法:在权限认证时
httpServletResponse.getOutputStream().write(jsObject.toString().getBytes("UTF8"));
httpServletResponse.getOutputStream().close();
或者使用return false结束,不执行使用ResponseBody注解的方法中