分配名称和定制的URL

在web.xml中完成的一个最常见的任务是对servlet或JSP页面给出名称和定制的URL。用servlet元素分配名称，使用servlet-mapping元素将定制的URL与刚分配的名称相关联。

## 1 分配名称

为了提供初始化参数，对servlet或JSP页面定义一个定制URL或分配一个安全角色，必须首先给servlet或JSP页面一个名称。可通过 servlet元素分配一个名称。最常见的格式包括servlet-name和servlet-class子元素（在web-app元素内），如下所示：

<servlet>

<servlet-name>Test</servlet-name>

<servlet-class>moreservlets.TestServlet</servlet-class>

</servlet>

这表示位于WEB-INF/classes/moreservlets/TestServlet的servlet已经得到了注册名Test。给 servlet一个名称具有两个主要的含义。

首先，初始化参数、定制的URL模式以及其他定制通过此注册名而不是类名引用此servlet。

其次,可在 URL而不是类名中使用此名称。因此，利用刚才给出的定义，URL http://host/webAppPrefix/servlet/Test 可用于

http://host/webAppPrefix/servlet/moreservlets.TestServlet 的场所。

请记住：

XML元素不仅是大小写敏感的，而且定义它们的次序也很重要。

例如，web-app元素内所有servlet元素必须位于所有servlet- mapping元素之前，而且还要位于与过滤器或文档相关的元素（如果有的话）之前。

servlet 的servlet-name子元素也必须出现在servlet-class之前。

例如，下面的程序中给出了一个名为TestServlet的简单servlet，它驻留在moreservlets程序包中。因为此servlet是扎根在一个名为deployDemo的目录中的Web应用的组成部分，所以TestServlet.class放在deployDemo/WEB- INF/classes/moreservlets中。

程序给出将放置在deployDemo/WEB-INF/内的web.xml文件的一部分。此web.xml文件使用servlet-name和servlet-class元素将名称Test与TestServlet.class相关联。图中分别显示利用缺省URL和注册名调用TestServlet时的结果。

TestServlet.java

1. package moreservlets;

2.

3. import java.io.*;

4. import javax.servlet.*;

5. import javax.servlet.http.*;

6.

7. public class TestServlet extends HttpServlet {

8. public void doGet(HttpServletRequest request,

9. HttpServletResponse response)

10. throws ServletException, IOException {

11. response.setContentType("text/html");

12. PrintWriter out = response.getWriter();

13. String uri = request.getRequestURI();

14. out.println(ServletUtilities.headWithTitle("Test Servlet") +

15. "<BODY BGCOLOR=\"#FDF5E6\">\n" +

16. "<H2>URI: " + uri + "</H2>\n" +

17. "</BODY></HTML>");

18. }

19. }

web.xml（说明servlet名称的摘录）

1. <?xml version="1.0" encoding="ISO-8859-1"?>

2. <!DOCTYPE web-app

3. PUBLIC "-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN"

4. "java.sun.com/dtd/web-app_2_3.dtd" target="_blank">http://java.sun.com/dtd/web-app_2_3.dtd">

5. <web-app>

6. <!-- … -->

7. <servlet>

8. <servlet-name>Test</servlet-name>

9. <servlet-class>moreservlets.TestServlet</servlet-class>

10. </servlet>

11. <!-- … -->

12. </web-app>

13.

## 2 定义定制的URL

大多数服务器具有一个缺省的serlvet URL：

http://host/webAppPrefix/servlet/packageName.ServletName。

虽然在开发中使用这个URL很方便，但是我们常常会希望另一个URL用于部署。

例如，可能会需要一个出现在Web应用顶层的URL（如，http: //host/webAppPrefix/Anyname），并且在此URL中没有servlet项。位于顶层的URL简化了相对URL的使用。此外，对许多开发人员来说，顶层URL看上去比更长更麻烦的缺省URL更简短。

事实上，有时需要使用定制的URL。

比如，你可能想关闭缺省URL映射，以便更好地强制实施安全限制或防止用户意外地访问无初始化参数的servlet。如果你禁止了缺省的URL，那么你怎样访问servlet呢？这时只有使用定制的URL了。

为了分配一个定制的URL，可使用servlet-mapping元素及其servlet-name和url-pattern子元素。Servlet- name元素提供了一个任意名称，可利用此名称引用相应的servlet；url-pattern描述了相对于Web应用的根目录的URL。url- pattern元素的值必须以斜杠（/）起始。

下面给出一个简单的web.xml摘录，它允许使用URL http://host/webAppPrefix/UrlTest而不是http://host/webAppPrefix/servlet/Test或http: //host/webAppPrefix/servlet/moreservlets.TestServlet。

请注意，仍然需要XML头、 DOCTYPE声明以及web-app封闭元素。此外，可回忆一下，XML元素出现地次序不是随意的。特别是，需要把所有servlet元素放在所有 servlet-mapping元素之前。

1. <servlet>

2. <servlet-name>Test</servlet-name>

3. <servlet-class>moreservlets.TestServlet</servlet-class>

4. </servlet>

5. <!-- ... -->

6. <servlet-mapping>

7. <servlet-name>Test</servlet-name>

8. <url-pattern>/UrlTest</url-pattern>

9. </servlet-mapping>

URL模式还可以包含通配符。例如，下面的小程序指示服务器发送所有以Web应用的URL前缀开始，以..asp结束的请求到名为BashMS的servlet。

1. <servlet>

2. <servlet-name>BashMS</servlet-name>

3. <servlet-class>msUtils.ASPTranslator</servlet-class>

4. </servlet>

5. <!-- ... -->

6. <servlet-mapping>

7. <servlet-name>BashMS</servlet-name>

8. <url-pattern>/*.asp</url-pattern>

9. </servlet-mapping>

## 3 命名JSP页面

因为JSP页面要转换成sevlet，自然希望就像命名servlet一样命名JSP页面。毕竟，JSP页面可能会从初始化参数、安全设置或定制的URL中受益，正如普通的serlvet那样。虽然JSP页面的后台实际上是servlet这句话是正确的，但存在一个关键的猜疑：即，你不知道JSP页面的实际类名（因为系统自己挑选这个名字）。因此，为了命名JSP页面，可将jsp-file元素替换为servlet-calss元素，如下所示：

1. <servlet>

2. <servlet-name>Test</servlet-name>

3. <jsp-file>/TestPage.jsp</jsp-file>

4. </servlet>

命名JSP页面的原因与命名servlet的原因完全相同：

即为了提供一个与定制设置（如，初始化参数和安全设置）一起使用的名称，并且，以便能更改激活 JSP页面的URL（比方说，以便多个URL通过相同页面得以处理，或者从URL中去掉.jsp扩展名）。

但是，在设置初始化参数时，应该注意，JSP页面是利用jspInit方法，而不是init方法读取初始化参数的。

例如，下面的程序中给出一个名为TestPage.jsp的简单JSP页面，它的工作只是打印出用来激活它的URL的本地部分。TestPage.jsp放置在deployDemo应用的顶层。程序清单5-4给出了用来分配一个注册名PageName，然后将此注册名与http://host/webAppPrefix/UrlTest2/anything 形式的URL相关联的web.xml文件（即，deployDemo/WEB-INF/web.xml）的一部分。

程序：TestPage.jsp

1. <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">

2. <HTML>

3. <HEAD>

4. <TITLE>

5. JSP Test Page

6. </TITLE>

7. </HEAD>

8. <BODY BGCOLOR="#FDF5E6">

9. <H2>URI: <%= request.getRequestURI() %></H2>

10. </BODY>

11. </HTML>

12.

web.xml（说明JSP页命名的摘录）

1. <?xml version="1.0" encoding="ISO-8859-1"?>

2. <!DOCTYPE web-app

3. PUBLIC "-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN"

4. "java.sun.com/dtd/web-app_2_3.dtd" target="_blank">http://java.sun.com/dtd/web-app_2_3.dtd">

5.

6. <web-app>

7. <!-- ... -->

8. <servlet>

9. <servlet-name>PageName</servlet-name>

10. <jsp-file>/TestPage.jsp</jsp-file>

11. </servlet>

12. <!-- ... -->

13. <servlet-mapping>

14. <servlet-name> PageName </servlet-name>

15. <url-pattern>/UrlTest2/*</url-pattern>

16. </servlet-mapping>

17. <!-- ... -->

18. </web-app>