Servlet请求转发之RequestDispatcher

本文探讨了Servlet中的请求转发原理,通过示例代码解释了转发过程中Response的状态和编码设置。强调了被转发Servlet无法修改HttpServletResponse对象信息,并讨论了转发静态HTML文件时可能出现的Content-Type问题以及解决方案。同时,指出了ServletContext与Request中获取RequestDispatcher方法的差异。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

转发的原理:

Servlet请求转发原理图

 

 

图片来自:http://blog.sina.com.cn/s/blog_4a157f470100a86y.html?retcode=0

 

浏览器将请求发送至servlet容器后,相应的组件获取到这个请求,然后在其内部将这个请求转发(request, response)给另外一个组件2,然后有组件2来响应浏览器的请求,但是此时浏览器上看到的仍然是组件1的地址。

在转发中,实际上转发的只有request,返回个浏览器的response的内容仍然是组件1中的设置。看下面代码:

 

IncludingServlet.java

 

IncludedServlet.java

 

*代码源自《Java Web开发内幕——核心基础》

 

在web.xml文件中注册上面两个servlet,运行tomcat,在浏览器中输入对IncludingSerlvet的请求,得到结果:

这里面正确地显示出了“中国”两个UTF-8编码的字符,但看上面的代码可以发现,两段代码都对response进行了设置文字编码操作,那究竟是哪一个设置起的作用?

尝试将IncludingServlet.java中的response的操作注释掉,再看结果,如下:

此时中国两个字显示成了乱码,这就说明了被转发的Servlet不能改变响应消息的状态码和响应头,同样,无法修改HttpServletRespnse对象中的信息。同样也看到了虽然IncludingServlet转发给了IncludedServlet,但是浏览器地址栏显示的还是调用者IncludingServlet的URI。

 

再来讨论另外一种情况,在servlet文件目录下新建一个chinese.html文件,内容为:

修改IncludingServlet.java文件的代码如下:

 

运行结果如下:

如果直接访问这个页面,得到如下结果:

为什么经过转发以后就不能解析html内容了呢?即,为什么直接访问html页面所得到的相映消息中包好Content-Type字段而通过IncludingServlet转发的则不包含呢?

解释是,凡是在web.xml中找不到匹配<servlet-mapping>元素的URL请求,也就是其他Serlvet都不处理的请求,都将交给tomcat的一个缺省servlet来处理,客户端对静态html的访问时间上就是在调用这个缺省servlet来完成响应的。所以,调用一个html和调用一个servlet本质上是一样的。

故在上面例子中,在IncludingServlet.java中加上

这样就能得到正确的输出了。

 

在一个问题,ServletContext中的getRequestDispatcher方法和Request中的getRequestDispatcher方法的不同之处:ServletContext中的getRequestDispatcher方法在指定URI时不能使用相对地址,而Request中的getRequestDispatcher方法可以。

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值