- 浏览: 868457 次
- 性别:
- 来自: 北京
文章分类
- 全部博客 (687)
- java (127)
- servlet (38)
- struts (16)
- spring (22)
- hibernate (40)
- javascript (58)
- jquery (18)
- tomcat (51)
- 设计模式 (6)
- EJB (13)
- jsp (3)
- oracle (29)
- RUP (2)
- ajax (3)
- java内存管理 (4)
- java线程 (12)
- socket (13)
- path (5)
- XML (10)
- swing (2)
- UML (1)
- JBPM (2)
- 开发笔记 (45)
- Note参考 (15)
- JAXB (4)
- Quartz (2)
- 乱码 (2)
- CSS (2)
- Exception (4)
- Tools (7)
- sqlserver (3)
- DWR (7)
- Struts2 (47)
- WebService (2)
- 问题解决收藏 (7)
- JBOSS (7)
- cache (10)
- easyUI (19)
- jQuery Plugin (11)
- FreeMarker (6)
- Eclipse (2)
- Compass (2)
- JPA (1)
- WebLogic (1)
- powerdesigner (1)
- mybatis (1)
最新评论
-
bugyun:
受教了,谢谢
java 正则表达式 过滤html标签 -
xiongxingxing_123:
学习了,感谢了
java 正则表达式 过滤html标签 -
wanmeinange:
那如果无状态的。对同一个任务并发控制怎么做?比如继承Quart ...
quartz中参数misfireThreshold的详解 -
fanjieshanghai:
...
XPath 元素及属性查找 -
tianhandigeng:
还是没明白
quartz中参数misfireThreshold的详解
最近需要在项目中做一个缓存框架,通过插件方式加入,要求可以通过配置文件,指定需要缓存页面的URL。
于是就想到做一个拦截器Filter。
该Filter可以首先拦截所有的请求,然后取得请求的URL,与配置中的需要缓存的URL对比,如果需要缓存,则进入缓存处理,如果不需要缓存,则直接到下一个Fitler。
具体的缓存处理,采用开源框架OScache。
方案还是比较简单的。 测试中发现,一般的Fitler只能拦截到从浏览器地址栏中过来的请求。 而页面的采用<jsp:include>方式载入的请求页面,则不能拦截到。
查看相关资料http://www.ibm.com/developerworks/java/library/j-tomcat2/ 后,得出结论:
在Servlet2.3中,Fitler是不能拦截include, forward, error 方式发来的请求的。
在Serlvet2.4中,则增强了Filter的功能,使之可以拦截到上面说的三个请求。 不过需要在配置文件中增加一个配置。
<filter>
该方式,不能拦截到 include 请求。
- <filter-name>Cache</filter-name>
- <filter-class>prx.cache.filter.CacheFilter</filter-class>
- <init-param>
- <!-- 过期时间设置,默认为60秒 -->
- <param-name>refreshPeriod</param-name>
- <param-value>120</param-value>
- </init-param>
- </filter>
- <filter-mapping>
- <filter-name>Cache</filter-name>
- <url-pattern>/*</url-pattern>
- </filter-mapping>
修改如下:
在配置文件,增加 <dispatcher></dispatcher>配置:
- <filter>
- <filter-name>Cache</filter-name>
- <filter-class>prx.cache.filter.CacheFilter</filter-class>
- <init-param>
- <!-- 过期时间设置,默认为60秒 -->
- <param-name>refreshPeriod</param-name>
- <param-value>120</param-value>
- </init-param>
- </filter>
- <filter-mapping>
- <filter-name>Cache</filter-name>
- <url-pattern>/index.jsp</url-pattern>
- <dispatcher>request</dispatcher>
- <!-- 使得页面中通过 include 方式嵌入的匹配页面也可以通过该Filter -->
- <dispatcher>include</dispatcher>
- </filter-mapping>
<dispatcher>request </dispatcher> Filter 只能拦截 匹配的 request 方式的请求,为默认值 。
<dispatcher>include </dispatcher> Filter 只能拦截 匹配的 incldue 方式的请求
<dispatcher>forward </dispatcher> Filter 只能拦截 匹配的 forward 方式的请求
<dispatcher>error </dispatcher> Filter 只能拦截 匹配的 error 方式的请求
dispatcher可以配置多个,用来组合各种需求。
例如:上面的配置,Fitler可以拦截 request和include 方式的请求。
通过以上的配置,就可以是Filter拦截到 include 的请求了。(当然,tomcat需要支持 servlet2.4)
到此解决了问题一。
在后来的测试又发现,虽然Filter是拦截了 incldue 的请求,但是在 Fitler 中,却无法取得该 incldue 的URL
由于项目的缓存方案是需要,取得URL请求,然后再判断是否需要缓存。 所以必须取得该 include 请求的URL。
- public void doFilter(ServletRequest request, ServletResponse response,
- FilterChain chain) throws IOException, ServletException {
- HttpServletRequest httpRequest = (HttpServletRequest)request;
- //取的url相对地址,例如:/PrxWebCache/index.jsp
- String url = httpRequest.getRequestURI();
- System.out.println(url);
- int cacheGrade = CacheUtils.isNeedCacheUrl(url);
- if(cacheGrade != 0) { //是否是需要缓存的url
- String key = CacheUtils.createKeyByUrl(httpRequest);
- boolean isInCache = CacheUtils.isInCache(httpRequest, key, cacheGrade);
- if(isInCache) {
- try {
- String content = (String)CacheUtils.getFromCache(httpRequest, key, cacheGrade, refreshPeriod);
- System.out.println("缓存");
- response.getWriter().print(content);
- } catch (NeedsRefreshException e) { //过期,需要刷新
- System.out.println("刷新");
- cacheAndResponseContent(httpRequest, response, chain, key, cacheGrade);
- }
- } else {
- //拦截响应数据,先加入缓存,再响应给客户端
- cacheAndResponseContent(httpRequest, response, chain, key, cacheGrade);
- }
- } else {
- chain.doFilter(request, response);
- }
- }
在Filter中,通过 httpRequest.getRequestURI(); 取出的 URL:
1. 当是 request 请求时,取得的 URL 是正确的。
2. 当是 include 请求时, 取得的 URL 是 包含该 include 元素的原页面的 URL
比如: 在 main.jsp 页面中 有个 <jsp:include page="index.jsp?type=test"/>
当Fitler拦截到 该 include请求时, httpRequest.getRequestURI(); 得出的是 main.jsp 而不是我需要的 index.jsp
但是 通过 httpRequest.getParameter("type"); 却可以得到 传入的参数 "test"。
到网上搜个半天,都没有相关答案。最后在 OScache 源码中发现了一个方法。
httpRequest.getAttribute("javax.servlet.include.request_uri")
通过该方法,可以直接取出 include 请求的 URL 值。
至于,这个 "javax.servlet.include.request_uri" 参数怎么设置进来的,还没仔细研究。 时间紧张,先用着,以后再研究吧。
又发现一个问题:
在Filter中拦截到incldue方式的请求后,在取得传入的所有参数的时候,会把request 的请求参数也读出来。
比如:请求页面 /index.jsp?type1=request¶m1=test1 然后再 index.jsp页面中有一个 <jsp:include page="/main.jsp?type2=include¶m2=test2"/>
当访问 /index.jsp?type1=request¶m1=test1 时,使用上面的方法拦截到 include请求 /main.jsp?type2=include¶m2=test2
Filter中的 在取得该请求的所有参数的时候,会将 /index.jsp的参数(type1=request¶m1=test1)也读出来
该方法返回的结果为: /main.jsp?type2=include¶m2=test2&type1=request¶m1=test1
- /**
- * 返回请求的URL的参数部分,例如:url=/index.jsp?type=1&searchWord=java,则返回type=1&searchWord=java
- * @param request
- */
- private static String getSortedQueryString(HttpServletRequest request) {
- Map paramMap = request.getParameterMap();
- if (paramMap.isEmpty()) {
- return null;
- }
- Set paramSet = new TreeMap(paramMap).entrySet();
- StringBuffer buf = new StringBuffer();
- boolean first = true;
- for (Iterator it = paramSet.iterator(); it.hasNext();) {
- Map.Entry entry = (Map.Entry) it.next();
- String[] values = (String[]) entry.getValue();
- for (int i = 0; i < values.length; i++) {
- String key = (String) entry.getKey();
- if ((key.length() != 10) || !"jsessionid".equals(key)) {
- if (first) {
- first = false;
- } else {
- buf.append('&');
- }
- buf.append(key).append('=').append(values[i]);
- }
- }
- }
- // We get a 0 length buffer if the only parameter was a jsessionid
- if (buf.length() == 0) {
- return null;
- } else {
- return buf.toString();
- }
- }
这样就取得了包含,index.jsp的参数。
我现在想要只想要取得 include请求的参数,即 /main.jsp?type2=include¶m2=test2 的参数部分type2=include¶m2=test2
但是通过 request.getParameter()方法,是无法判断出哪个参数才是 include 请求的参数。
经过上面的启发,于是又想到了,是不是有别的AttributeName 可以仅取到 include 请求的参数呢?
通过测试,果然发现的确有该AttributeName:"javax.servlet.include.query_string"
只要通过一句话便可以得到该 参数字符串:
该结果即为:type2=include¶m2=test2 正是需要的仅为 include 请求的参数。
- (String)request.getAttribute("javax.servlet.include.query_string");
发表评论
-
java解决网站静态页面生成方案(源码)
2012-07-01 01:51 0提升网站性能的方式有很多,例如有效的使用缓存,生成静态页 ... -
Servlet映射的匹配原则,优先级
2012-06-08 22:45 1425一个元素用于映射一个已经注册的Servlet的一个对外访问 ... -
TOMCAT SESSION的持久化方法
2012-06-12 09:56 1243Tomcat5.5.12 实现Session持久化的配置: ... -
Servlet和filter的JAVAEE的配置
2012-06-05 22:52 855一、servlet容器对url的匹配过程: 当一个请求发送 ... -
tomcat 静态资源处理类DefaultServlet&Apache静态资源服务
2012-06-05 21:13 2290DefaultServlet是tomcat中用来处理静态资源和 ... -
如何获取搜索引擎的来源和其中的关键字
2011-08-30 21:39 1788在做商务E流量分析的时候,需要实现一个功能:如果访客是通过搜索 ... -
RequestDispatcher接口中的include()方法和forward()方法的区别
2011-04-19 15:34 1126请求转发中 RequestDispatcher 接口中的 in ... -
文件上传下载(oreilly之MultipartReques)
2011-04-10 22:36 1208上传篇代码片段: import com.oreill ... -
使用jstl还要在web.xml里面配一下
2011-01-30 11:26 1897悲剧,有人说是不用apac ... -
JAVA WEB学习笔记(五)-自定义JSP标签
2011-01-27 13:28 790一、基本概念:********** ... -
<转>web.xml 中的listener、 filter、servlet 加载顺序及其详解
2010-12-10 22:45 890转载自 ailongni 最终编 ... -
web.xml里listener、filter和servlet加载顺序和详解(二)
2010-12-10 22:44 1213相应元素配置 1、Web应用图标:指出IDE和GUI工具用来 ... -
转】servlet中web.xml配置详解(转)
2010-12-10 22:42 854转载自 limpid1215 最终编辑 limpid121 ... -
Tomcat6中启用invoker心得
2010-10-26 08:31 1547今天下了看了一下示例,TOMCAT6中启用invoker 访问 ... -
el表达式不起作用的解决方案
2010-10-12 14:18 850关键字: el表达式不起作用 今天晚上学习SSH,发现一个el ... -
getOutputStream() has already been called for this response
2010-10-11 16:15 1244java.lang.IllegalStateException ... -
关于serveletContext.getRealPath()方法
2010-10-11 10:23 20211.关于request.getRealPath 问 ... -
采用application/vnd.ms-excel导出excel时修改文件名
2010-09-26 10:17 3473设置response属性,如下 response.se ... -
HttpServletResponse addHeader 与 setHeader 区别
2010-09-09 19:09 3852setHeader(name,value) :如果Header ... -
web.xml配置详解
2010-09-09 09:47 721转自:http://blog.csdn.net/j ...
相关推荐
对request请求进行拦截,对请求参数修改。常用于前台提交表单参数关键字的过滤。此工具可以对参数拦截并转义后提交到对应的处理类。 除了添加两个JsFilter.java和GetHttpServletRequestWrapper.java之外,需要在web....
利用java filter 实现业务异常拦截 跳转到错误信息提示页面 我们在做项目中肯定都会遇到自定义业务异常 ,然后将业务异常信息跳转的统一的信息提示页面的情况,比如我们在struts的时候我们会用到struts的异常处理...
演示了过滤器捕获客户端发送的request请求,并对request请求进行分析处理,从而让后台得到处理后的请求
struts2在struts2.xml里配置拦截器可以过滤到指定的url的请求,但是对于ajax的请求确是过滤不了,比如说sesion超时或某些页面有权限控制的,通过ajax的请求时系统会报错最近在解决此类问题时碰上了找了不少资料,...
java filter打印请求返回参数
拦截器 FILTER 代码样例
使用 Filter 实现对 servlet 权限拦截,例子简单易懂
主要介绍了详解AOP与Filter拦截请求打印日志实用例子,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
编写 Servlet 并添加两个 Filter,并确保在 Servlet 执行之前和之后...在此方法中,您可以编写逻辑,例如打印 "Filter01 before",并在处理完请求后打印 "Filter01 after"。 创建第二个 Filter,将其命名为 Filter02
在通过Google Chrome进行URI请求时Filter的doFilter中的输出(sout)语句会被打印两次,原因是Chrome在进行请求URI的时同时请求了http://localhost:8080/favicon.ico可以使用Charles (Web Debugging Proxy)工具进行...
filter是javaWeb中一个十分重要的知识点,可以拦截webApp的所有请求。 使用场景: 1、可以利用filter做到网站自登录。 2、可以利用filter全局修改参数编码,从而解决中文乱码问题(十分重要)。
NULL 博文链接:https://yanfei133.iteye.com/blog/1882020
Filter 或者目标 Servlet 程序去处理,也可以直接向客户端返回响应信息,或者利用 RequestDispatcher 的 forward() 和 include() 方法,以及 HttpServletResponse 的 sendRedirect() 方法将请求转向到其他资源。...
本案例中 使用maven 搭建spring boot 基本案例 其中实现了 用户登录功能,实现Filter 和 拦截器两种方式 来过滤session登录,后续会使用token方式,请大家关注
本篇文章主要介绍了防止SpringMVC拦截器拦截js等静态资源文件的解决方法,具有一定的参考价值,有兴趣的同学可以了解一下
Filter是Servlet规范里面的,属于容器范围,Springboot中没有web.xml,那Springboot中,不用管Filter是如何交给Ser...SpringBoot整合XssFilter,Jsoup等实现请求参数的过滤,处理Xss攻击及sql注入.zip
15.1 拦截器概述 Spring MVC中的拦截器(Interceptor)类似于Servlet中的过滤器(Filter),它主要用于拦截用户请求并作相应的处理。例如通过拦截器可以进行权限验证、记录请求信息的日志、判断用户是否登录等。 ...
网络数据拦截(TDI Filter Hook)
项目集成了sso资源拦截的控制,自己写了一个springBoot自定义的filter。可以减少一些不必要的资源拦截。自己做的一个小demo,共享于大家。
用户在没有登录的情况下,无法浏览除登录页面之外的其他页面,并且如果用户名为空,也不能进如其他页面。