最近项目上客户提了一个小需求,要求添加一个mac白名单管理机制。在白名单里面的机顶盒访问portal接口时允许访问,不在白名单内的进行拦截。在所有接口上添加判断太过麻烦,所以考虑使用Java接口过滤器来实现这一功能。
Filter过滤器
Java开发人员通过Filter技术,对web服务器管理的所有web资源:例如Jsp, action, 静态图片文件或静态 html 文件等进行拦截,从而实现一些特殊的功能。
Servlet API中提供了一个Filter接口,开发web应用时,如果编写的Java类实现了这个接口,则把这个java类称之为过滤器Filter。通过Filter技术,开发人员
可以实现用户在访问某个目标资源之前,对访问的请求和响应进行拦截。
创建Filter
package com.inspur.portal.core.filter;import java.io.IOException;
import java.io.PrintWriter;
import java.util.HashMap;
import java.util.Map;
import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import org.apache.commons.lang3.StringUtils;
import org.apache.log4j.Logger;
import com.alibaba.fastjson.JSON;
import com.inspur.portal.core.common.SystemConstant;
public class AuthorityFilter implements Filter {
private static Logger log = Logger.getLogger(AuthorityFilter.class);
/**
* 需要排除的页面 接口
*/
private String excludedPages;
private String[] excludedPageArray;
@Override
public void init(FilterConfig filterConfig) throws ServletException {
log.info("filter初始化");
excludedPages = filterConfig.getInitParameter("excludedPages");
if (StringUtils.isNotEmpty(excludedPages)) {
excludedPageArray = excludedPages.split(",");
}
return;
}
@Override
public void doFilter(ServletRequest request, ServletResponse response,
FilterChain chain) throws IOException, ServletException {
boolean isExcludedPage = false;
for (String page : excludedPageArray) {// 判断是否在过滤url之外
if (((HttpServletRequest) request).getServletPath().equals(page)) {
isExcludedPage = true;
break;
}
}
Map<String, Object> map = new HashMap<String, Object>();
response.setCharacterEncoding("utf-8");
response.setContentType("application/json;charset=utf-8");
// 在过滤url之外
if (isExcludedPage) {
chain.doFilter(request, response); // 让目标资源执行,放行
} else {
String mac = request.getParameter("mac");
if (SystemConstant.MAC_WHITE_LIST.contains(mac)) {
chain.doFilter(request, response); // 让目标资源执行,放行
} else {
PrintWriter out = response.getWriter();
map.put("flag", false);
map.put("msg", "没有该权限");
out.write(JSON.toJSONString(map));
out.flush();
out.close();
}
}
}
@Override
public void destroy() {
log.info("filter过滤器销毁");
}
}
针对上面代码进行下简单讲解:
首先创建AuthorityFilter类实现Filter接口,并实现它的3个方法,init、doFiter和destroy。init方法是在过滤器初始化时调用的方法,上面init方法中的
代码作用是通过filterConfig.getInitParameter方法获取到不在拦截范围内的url资源,然后将这些资源放到excludedPageArray中。如果你需要全部拦截,那在
init方法里面你不需要做任何处理,单纯的加个打印即可。
在doFilter方法中代码用于判断url资源是否拦截或放行。如果url资源在excludedPageArray内,直接放行,因为这些资源不需要拦截。因为我们的目的是
为了判断访问mac是否在我们的白名单内,所以通过传过来的mac来判断,如果mac在白名单内,放行;如果不在白名单内,进行拦截,并返回flag为false,提示
没有权限访问。
web.xml中的处理
web.xml中添加如下配置:
<!--配置过滤器-->
<filter>
<filter-name>MacWhiteFilter</filter-name>
<filter-class>com.inspur.portal.core.filter.AuthorityFilter</filter-class>
<init-param>
<param-name>excludedPages</param-name>
<param-value>/addOrUpdateStbinfo</param-value>
</init-param>
</filter>
<!--映射过滤器-->
<filter-mapping>
<filter-name>MacWhiteFilter</filter-name>
<!--“/*”表示拦截所有的请求 -->
<url-pattern>/*</url-pattern>
</filter-mapping>
filter-name、filter-class不必多说,用于定义Filter名字和对应的类,init-param用于定义不在拦截范围内的资源,param-name对应上面
AuthorityFilter类中的excludedPages变量,/addOrUpdateStbinfo代表不在拦截范围内的url。param-name和param-value针对自己情况进行设定,只要和
AuthorityFilter类中的变量、web应用url对应即可。当然你也可以将init-param定义为需要拦截的资源,只要在AuthorityFilter类中if (isExcludedPage)
做好对应的判断就好。视自己情况而定。如果你需要对全部的接口url进行拦截,那就不需要设定init-param。定义完filter之后别忘了定义对应的filter-mapping。
好了,Java中的Filter到此为止基本的功能已经实现了,下图为实现效果。我设定的mac白名单为[345678],mac=2并不在我的白名单内,我返回没权限。
当我调用addOrUpdateStbinfo时,因为该url不在拦截范围内,所以不管mac在不在白名单,直接放行。
有问题或见解欢迎在评论区交流指正~~~
最后,打波广告。微信搜索公众号"省钱潮",公众号微信号:IT20151230 淘宝购物领券,专为你省钱。