getRequestDispatcher(“path”)在哪里看?

时间:2014-04-10 19:20:13

标签: java tomcat servlets

使用嵌入式tomcat,此代码:

System.out.println("getServletPath: " + request.getServletPath());
System.out.println("getServletContext: " + request.getServletContext().getContextPath());
System.out.println("getServerName: " + request.getServerName());
System.out.println("getServerPort: " + request.getServerPort());

打印出来:

getServletPath: /example
getServletContext: 
getServerName: localhost
getServerPort: 9090

这是否意味着:

request.getRequestDispatcher("/example/read.jsp").forward(request, response);

将查看此URL的forward(request, response)到JSP:

http://localhost:9090/example/read.jsp

有没有办法打印出绝对网址getRequestDispatcher("relativePath")正在寻址的内容?

1 个答案:

答案 0 :(得分:8)

Servlet Specification解释了这个

  

getRequestDispatcher方法采用描述a的String参数   ServletContext范围内的路径。 此路径必须   相对于ServletContext的根,以'/'开头,或者   是空的。该方法使用路径查找servlet,使用   第12章“映射请求到”中的servlet路径匹配规则   Servlets“,用RequestDispatcher对象包装它,然后返回   结果对象。如果没有servlet可以根据给定的解析   path,提供一个RequestDispatcher,用于返回内容   那道路。

这些规则如下

  
      
  1. 容器将尝试查找请求路径与servlet路径的完全匹配。成功的比赛选择   的servlet。
  2.   
  3. 容器将递归尝试匹配最长的路径前缀。这是通过逐步降低路径树的目录来完成的   一次,使用'/'字符作为路径分隔符。最长的   match确定所选的servlet。
  4.   
  5. 如果URL路径中的最后一个段包含扩展名(例如.jsp),则servlet容器将尝试匹配处理的servlet   请求延期。扩展名被定义为   最后一个'。'字符后的最后一段。
  6.   
  7. 如果前三个规则都没有导致servlet匹配,则容器将尝试提供适合的内容   资源要求。如果"默认" servlet是为   应用程序,它将被使用。许多容器提供隐含的   用于提供内容的默认servlet。
  8.   

你问

  

这是否意味着:

     

的request.getRequestDispatcher(" /example/display.jsp")。正向(请求,   响应);将查看此URL以转发(请求,响应)   JSP:

     

http://localhost:9090/example/display.jsp

不,它没有发送HTTP请求,因此该路径与URI无关。它更像是一个内部路径,Servlet容器将尝试与Servlet的各种url-mappings匹配。

你也问

  

有没有办法打印出绝对URL getRequestDispatcher(" relativePath")正在寻址?

没有。它并不是一个绝对的URL。它是Web应用程序上下文中某些资源可以处理的路径。


修改后,您addWebapp转到Tomcat个实例。

tomcat.addWebapp(null, "/view2/example2", new File("src/com/example/view/example").getAbsolutePath());

然后您向

发送请求
 /view2/example2/read.jsp

我将假设read.jsp

src/com/example/view/example/

我相信它位于Web应用程序的可公开访问的部分,因此Servlet容器可以呈现它并使用它进行响应。

您还添加了一个addContext的网络应用,似乎与addWebapp类似

context = tomcat.addContext("", base.getAbsolutePath());

并将映射添加到上下文。

Tomcat.addServlet(context, "example", new ExampleController());
context.addServletMapping("/example/*", "example");

我错误地认为/example/*无法处理/example

当您向

发送请求时
/example

由于上下文路径为"",将使用上面的Context,映射将与上面注册的ExampleController匹配。您的Servlet代码将执行并到达

request.getRequestDispatcher("/view2/example2/read.jsp").forward(request, response);

请注意ServletRequest#getRequestDispatcher(String)

的javadoc
  

指定的路径名​​可能是相对的,但不能扩展   在当前servlet上下文之外。

换句话说,ServletExampleController已在映射到上下文路径ServletContext的{​​{1}}中注册,即。根。路径""指的是另一个上下文。由于此上下文没有映射,因此它以404响应。

您可以在不同的上下文中获取对其他Web应用程序的引用。您必须使用ServletContext#getContext(String)。例如

/view2/example2/read.jsp

现在您已拥有 ServletContext otherContext = request.getServletContext().getContext("/view2/example2"); ,您可以在 上下文中获取ServletContext资源。

RequestDispatcher

因为ServletContext#getRequestDispatcher(String)

  

路径名必须以/开头,并且被解释为相对于当前上下文根。


最终答案:

otherContext.getRequestDispatcher("/read.jsp").forward(request, response); 将在引用JSP文件时查看getRequestDispatcher("path")方法中设置的目录。如果显示空白页面或addWebapp,请确保您已完成以下操作:

  1. 删除所有NullPointerException定义。
  2. 运行addWebapp然后addContext,这样他们都指向addWebApp
  3. ROOT

    1. 在servlet中使用File base = new File("src/com/example/view"); context = tomcat.addContext("", base.getAbsolutePath()); tomcat.addWebapp(null, "/", base.getAbsolutePath());指向jsp,前提是request.getRequestDispatcher("/example/read.jsp").forward(request, response);中存在目录/示例。
相关问题