请求转发
-
请求转发:客户端的一次请求到达后,发现需要借助其他Servlet来实现功能。
- 客户端浏览器发送一个请求到ServletA中,想借助ServletA去实现一些功能,但是ServletA完成不了这个功能,这时候它发现ServletB是可以实现这些功能的,所以ServletA就这次请求转发个ServletB
-
特点:
- 浏览器地址栏不变:(还是ServletA的地址)
- 域对象中的数据不丢失:(可以在ServletA中去设置一些共享数据,ServletB就能获取这些数据)
- 负责转发的Servlet转发前后的响应正文会丢失:(因为最终是由ServletB去响应给客户端的,所以ServletA的正文会丢失)
- 由转发的目的地来响应客户端
-
实现方法
-
代码实现
转发的Servlet
@WebServlet("/qqzf1") public class qqzfDemo1 extends HttpServlet { @Override protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { //设置共享数据 req.setAttribute("encoding","gbk"); //获取请求调度对象 RequestDispatcher rd = req.getRequestDispatcher("/qqzf2"); //实现转发功能 rd.forward(req,resp); } @Override protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { doGet(req,resp); } }
真正执行的Servlet
@WebServlet("/qqzf2") public class qqzfDemo2 extends HttpServlet { @Override protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { //获取共享数据 Object encoding = req.getAttribute("encoding"); System.out.println(encoding); System.out.println("qqzf2执行了"); } @Override protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { doGet(req,resp); } } /* gbk qqzf2执行了 */
请求包含
-
请求包含:可以合并其他Servlet中的功能一起响应给客户端。
- 客户端浏览器发送一个请求,找到了ServletA实现一些功能,但是ServletA只能完成一部分,另一部分实现不了,替换ServletA发现ServletB可以把另外一部分的功能实现,所以这个时候ServletA就把ServletB包含了一下。能够在ServletA中合并其他Servlet当中的功能,一起响应给客户端
-
特点:
- 浏览器地址栏不变(还是ServletA的地址)
- 域对象中的数据不丢失(可以在ServletA中去设置一些共享数据,ServletB就能获取这些数据)
- 被包含的Servlet响应头会丢失(ServletB的消失)
-
实现方法
-
代码测试
@WebServlet("/qqzf1") public class qqzfDemo1 extends HttpServlet { @Override protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { //设置共享数据 req.setAttribute("encoding","gbk"); //获取请求调度对象 RequestDispatcher rd = req.getRequestDispatcher("/qqzf2"); //实现转发功能 rd.include(req,resp); } @Override protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { doGet(req,resp); } }
@WebServlet("/qqzf2") public class qqzfDemo2 extends HttpServlet { @Override protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { //获取共享数据 Object encoding = req.getAttribute("encoding"); System.out.println(encoding); System.out.println("qqzf2执行了"); } @Override protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { doGet(req,resp); } } /* gbk qqzf2执行了 */
请求重定向
- 请求重定向:客户端的一次请求到达后,发现需要借助其他Servlet来实现功能。
- 特点
- 1.浏览器地址栏会发生改变,
- 2.两次请求请求域对象中不能共享数据
- 3.可以重定向到其他服务器。
- 重定向是两次请求
- 特点
@WebServlet("/xiangy1")
public class xiangyServlet extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
System.out.println("xiangy1执行了");
///设置重定向
//这个是浏览器的输入地址,就是我想访问reqduix,在浏览器地址栏做输入的内容
resp.sendRedirect(req.getContextPath()+"/reqduix");
resp.sendRedirect("https:.//www.baidu.com");//访问这个Servlet的话,重定向到百度的页面去
}
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
doGet(req,resp);
}
}
如何选择重定向还是请求转发
查看跳转资源的时候需不需要共享数据,如果需要的话使用的就是请求转发,不需要就可以使用重定向