详解JavaWeb中的过滤器Filter
过滤器的概念
过滤器Filter是Java Web中的一个组件,用于拦截HTTP请求和响应,并对请求和响应进行处理和转换。它可以在Servlet处理请求之前或之后介入,处理请求信息、过滤响应结果,完成一些类似于AOP的功能。
过滤器的作用
过滤器可以在请求和响应处理的过程中拦截并修改信息,常见的使用场景如下:
- 过滤敏感字符,如
<
、>
等,防止XSS攻击 - 过滤非法用户,检查是否登录或是否有权限访问
- 过滤危险操作,如删除数据、修改配置等,防止CSRF攻击
- 过滤请求参数,如URL传递的参数,进行安全校验和转换
过滤器的实现
通过实现javax.servlet.Filter接口可以创建一个过滤器,Filter接口有三个方法:
- init:初始化,容器启动时被调用
- doFilter:执行过滤,FilterChain对象的doFilter方法调用时被调用
- destroy:销毁,容器关闭时被调用
在init方法中可以进行过滤器的初始化工作,在doFilter方法中可以获取请求、响应信息进行处理,最后再调用FilterChain对象的doFilter方法,如果还有后续的过滤器,则会继续传递;如果没有,就交给应用处理。在整个过程中都可以修改请求参数和响应结果。在destroy方法中进行过滤器的销毁操作。
过滤器的配置
过滤器需要在web.xml中进行配置,示例如下:
<filter>
<filter-name>MyFilter</filter-name>
<filter-class>com.example.MyFilter</filter-class>
<init-param>
<param-name>param1</param-name>
<param-value>value1</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>MyFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
其中,filter-name为过滤器的名称,filter-class为过滤器类的全路径名,init-param用于初始化过滤器类中的参数,filter-mapping中的url-pattern表示需要拦截的URL。需要注意的是,不同过滤器之间的顺序也会影响最终执行结果。
示例1
假设我们的应用需要先进行用户登录操作,再进行其他操作,我们可以使用过滤器来检查是否已经登录,如果没有登录就重定向到登录页面,代码如下:
public class LoginFilter implements Filter {
private FilterConfig config;
public void init(FilterConfig config) throws ServletException {
this.config = config;
}
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws ServletException, IOException {
HttpServletRequest req = (HttpServletRequest)request;
HttpServletResponse res = (HttpServletResponse)response;
HttpSession session = req.getSession();
String url = req.getRequestURI();
if (url.endsWith(".jsp") && !url.endsWith("login.jsp")) {
if (session.getAttribute("username") == null) {
res.sendRedirect("login.jsp");
return;
}
}
chain.doFilter(request, response);
}
public void destroy() {
}
}
在上述代码中,我们使用了HttpServletRequest对象获取了请求的URI,判断是否为登录操作以及是否已经登录,如果是登录操作则继续往下执行,如果未登录则重定向到登录页面。需要注意的是,过滤器需要在web.xml中进行配置并指定拦截的URL。
示例2
假设我们要过滤请求参数中的敏感字符,比如<
、>
等,防止XSS攻击,我们可以使用过滤器来对请求参数进行处理,代码如下:
public class XSSFilter implements Filter {
private FilterConfig config;
public void init(FilterConfig config) throws ServletException {
this.config = config;
}
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws ServletException, IOException {
ParameterRequestWrapper requestWrapper = new ParameterRequestWrapper((HttpServletRequest) request);
String[] params = requestWrapper.getParameterValues("param");
if (params != null) {
for (int i = 0; i < params.length; i++) {
params[i] = protectXSS(params[i]);
}
}
chain.doFilter(requestWrapper, response);
}
public void destroy() {
}
private String protectXSS(String value) {
if (value != null) {
value = value.replaceAll("<", "<").replaceAll(">", ">");
}
return value;
}
}
class ParameterRequestWrapper extends HttpServletRequestWrapper {
private Map<String, String[]> params = new HashMap<>();
public ParameterRequestWrapper(HttpServletRequest request) {
super(request);
this.params.putAll(request.getParameterMap());
}
@Override
public String getParameter(String name) {
String[] values = params.get(name);
if (values == null || values.length == 0) {
return null;
}
return protectXSS(values[0]);
}
@Override
public String[] getParameterValues(String name) {
String[] values = params.get(name);
if (values == null || values.length == 0) {
return null;
}
String[] result = new String[values.length];
for (int i = 0; i < values.length; i++) {
result[i] = protectXSS(values[i]);
}
return result;
}
private String protectXSS(String value) {
if (value != null) {
value = value.replaceAll("<", "<").replaceAll(">", ">");
}
return value;
}
}
在上述代码中,我们通过override HttpServletRequest对象的getParameter、getParameterValues方法对请求参数进行处理,替换敏感字符为安全字符,并使用ParameterRequestWrapper对象封装HttpServletRequest对象,继而在过滤器中调用。需要注意的是,过滤器需要在web.xml中进行配置并指定拦截的URL。
本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:详解JavaWeb中的过滤器Filter - Python技术站