/** * Copyright 2016 benjobs * <p> * 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 * <p> * http://www.apache.org/licenses/LICENSE-2.0 * <p> * 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.opencron.server.handler; import org.opencron.common.utils.CommonUtils; import org.opencron.common.utils.StringUtils; import org.opencron.common.utils.WebUtils; import org.opencron.server.domain.User; import org.opencron.server.job.OpencronTools; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.stereotype.Component; import org.springframework.web.method.HandlerMethod; import org.springframework.web.servlet.handler.HandlerInterceptorAdapter; import javax.servlet.http.*; import java.util.ArrayList; import java.util.Enumeration; import java.util.List; import java.util.Map; /** * 登陆权限拦截器 */ @Component public class SecurityHandlerInterceptor extends HandlerInterceptorAdapter { private static final Logger logger = LoggerFactory.getLogger(SecurityHandlerInterceptor.class); public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception { request = new XssHttpServletRequest(request); HttpSession session = request.getSession(); String requestURI = request.getContextPath() + request.getServletPath(); // // 考虑到以后升级可能会改css或者js,用户重新升级部署后肯能有缓存,导致项目失败, // 特此加上防止用户端有缓存的Id来防止资源缓存,每次项目启动会生成一个随机码添加到所有的资源引用后 // session.setAttribute("resourceId", OpencronTools.getResourceId()); //静态资源,页面 if (requestURI.contains("/css/") || requestURI.contains("/fonts/") || requestURI.contains("/img/") || requestURI.contains("/js/") || requestURI.contains("/WEB-INF")) { return super.preHandle(request, response, handler); } //登陆 if (requestURI.contains("/login") || requestURI.contains("/upload") || requestURI.contains("/agent/autoreg")) { return super.preHandle(request, response, handler); } String referer = request.getHeader("referer"); if (referer != null && !referer.startsWith(WebUtils.getWebUrlPath(request))) { response.sendRedirect("/"); logger.info("[opencron]Bad request,redirect to login page"); OpencronTools.invalidSession(session); return false; } try { User user = OpencronTools.getUser(session); if (user == null) { //跳到登陆页面 response.sendRedirect("/"); logger.info("[opencron]User not login,redirect to login page"); return false; } } catch (IllegalStateException e) { logger.info("[opencron]Session already invalidated,redirect to login page"); response.sendRedirect("/"); return false; } //普通管理员不可访问的资源 if (!OpencronTools.isPermission(session) && (requestURI.contains("/config/") || requestURI.contains("/user/view") || requestURI.contains("/user/add") || requestURI.contains("/agent/add") || requestURI.contains("/agent/edit"))) { logger.info("[opencron]illegal or limited access"); return false; } if (handler instanceof HandlerMethod) { if (!verifyCSRF(request)) { response.sendRedirect("/"); logger.info("[opencron]Bad request,redirect to login page"); OpencronTools.invalidSession(session); return false; } } return super.preHandle(request, response, handler); } private boolean verifyCSRF(HttpServletRequest request) { String requstCSRF = OpencronTools.getCSRF(request); if (CommonUtils.isEmpty(requstCSRF)) { return false; } String sessionCSRF = OpencronTools.getCSRF(request.getSession()); if (CommonUtils.isEmpty(sessionCSRF)) { return false; } return requstCSRF.equals(sessionCSRF); } class XssHttpServletRequest extends HttpServletRequestWrapper { public XssHttpServletRequest(HttpServletRequest servletRequest) { super(servletRequest); } public String[] getParameterValues(String parameter) { String[] values = super.getParameterValues(parameter); if (values == null) { return null; } int count = values.length; String[] encodedValues = new String[count]; for (int i = 0; i < count; i++) { encodedValues[i] = cleanXSS(values[i]); } return encodedValues; } public Map getParameterMap() { Map<String, String[]> map = super.getParameterMap(); for (Map.Entry<String, String[]> entry : map.entrySet()) { String[] values = entry.getValue(); for (int i = 0; i < values.length; i++) { values[i] = cleanXSS(values[i]); } map.put(entry.getKey(), values); } return map; } public Enumeration getParameterNames() { class MyEnumeration implements Enumeration { private int count; private int length; private Object[] data; MyEnumeration(Object[] data) { this.count = 0; this.length = data.length; this.data = data; } @Override public boolean hasMoreElements() { return (count < length); } @Override public Object nextElement() { return data[count++]; } } Enumeration enumeration = super.getParameterNames(); List<Object> list = new ArrayList<Object>(); while (enumeration.hasMoreElements()) { Object value = enumeration.nextElement(); value = cleanXSS((String) value); list.add(value); } return new MyEnumeration(list.toArray()); } public String getParameter(String parameter) { String value = super.getParameter(parameter); if (value == null) { return null; } return cleanXSS(value); } private String cleanXSS(String value) { if (value == null) return null; return StringUtils.htmlEncode(value); } } }