• Servlet各种路径、URL配置分析


    大家都知道,Servlet有个配置:

    <servlet>
      <servlet-name>zolltyMVC</servlet-name>
      <servlet-class>org.zollty.framework.mvc.servlet.DispatcherServlet</servlet-class>
    </servlet>
    <servlet-mapping>
      <servlet-name>zolltyMVC</servlet-name>
      <url-pattern>/</url-pattern>
    </servlet-mapping>

    对于<url-pattern>/</url-pattern>这一项,有时候会 带有 “*” 这种写法,这和没有 "*" 号时有什么差别呢?

    首先来看一下,通过 HttpServletRequest request 我们能取到哪些重要参数:

    System.out.println("getServerName" + request.getServerName());
    System.out.println("getLocalName" + request.getLocalName());
    System.out.println("------------------------------------");
    System.out.println("getPathInfo" + request.getPathInfo());
    System.out.println("getPathTranslated" + request.getPathTranslated());
    System.out.println("------------------------------------");
    System.out.println("getRemoteHost" + request.getRemoteHost());
    System.out.println("getRemoteAddr" + request.getRemoteAddr());
    System.out.println("getLocalAddr" + request.getLocalAddr());
    System.out.println("------------------------------------");
    System.out.println("getRequestURI" + request.getRequestURI());
    System.out.println("getServletPath" + request.getServletPath());
    System.out.println("getContextPath" + request.getContextPath());
    System.out.println("------------------------------------");
    System.out.println("getScheme" + request.getScheme());
    System.out.println("getLocale" + request.getLocale().getLanguage());
    System.out.println("------------------------------------");
    System.out.println("getServerPort" + request.getServerPort());
    System.out.println("getLocalPort" + request.getLocalPort());
    System.out.println("getRemotePort" + request.getRemotePort());
    System.out.println("------------------------------------");
    System.out.println("getMethod" + request.getMethod());
    System.out.println("getProtocol" + request.getProtocol());
    System.out.println("getRemoteUser" + request.getRemoteUser());
    System.out.println("getRequestedSessionId" + request.getRequestedSessionId());
    System.out.println("getCharacterEncoding" + request.getCharacterEncoding());
    System.out.println("getContentType" + request.getContentType());

    当配置为 <url-pattern>/</url-pattern>时,打印的结果如下:

    getServerNamelocalhost
    getLocalName0.0.0.0
    ------------------------------------
    getPathInfonull
    getPathTranslatednull
    ------------------------------------
    getRemoteHost0:0:0:0:0:0:0:1
    getRemoteAddr0:0:0:0:0:0:0:1
    getLocalAddr0.0.0.0
    ------------------------------------
    getRequestURI/sss/sd/ds
    getServletPath/sd/ds
    getContextPath/sss
    ------------------------------------
    getSchemehttp
    getLocalezh
    ------------------------------------
    getServerPort8081
    getLocalPort8081
    getRemotePort65281
    ------------------------------------
    getMethodGET
    getProtocolHTTP/1.1
    getRemoteUsernull
    getRequestedSessionIdE6CED285C020625E0D6531BBBD25033A
    getCharacterEncodingnull
    getContentTypenull

    当配置为 <url-pattern>/*</url-pattern> 时,打印的结果如下:

    getServerNamelocalhost
    getLocalName0.0.0.0
    ------------------------------------
    getPathInfo/sd/ds
    getPathTranslatedD:CJavaapache-tomcat-7.0.23webappsssssdds
    ------------------------------------
    getRemoteHost0:0:0:0:0:0:0:1
    getRemoteAddr0:0:0:0:0:0:0:1
    getLocalAddr0.0.0.0
    ------------------------------------
    getRequestURI/sss/sd/ds
    getServletPath
    getContextPath/sss
    ------------------------------------
    getSchemehttp
    getLocalezh
    ------------------------------------
    getServerPort8081
    getLocalPort8081
    getRemotePort65388
    ------------------------------------
    getMethodGET
    getProtocolHTTP/1.1
    getRemoteUsernull
    getRequestedSessionIdE6CED285C020625E0D6531BBBD25033A
    getCharacterEncodingnull
    getContentTypenull

    区别在如下几个地方:

    // ------------------------------------
    // getPathInfo/
    // getPathTranslatedD:CJavaapache-tomcat-7.0.23webappssss
    // ------------------------------------
    // getRequestURI/sss/p/
    // getServletPath/p

    对于"/"形式,得到的getPathInfo和getPathTranslated都为null;

    对于"/*"形式,则能得到 "/" 和 项目的所在磁盘上的绝对路径

    而对于ServletPath 和 RequestURI ,分析如下:

    // ServletPath = 不含项目名称的访问地址 -- 如果是/p/*方式配置,则访问地址为/p,如果是/*则是""(空); 如果是/方式配置,则访问地址是全路径(包括斜杠)
    // RequestURI = 包含项目名称的访问地址 -- 不管是/或者/*或者/p/*方式配置,访问地址都为/{项目名}+全路径(包括斜杠)

    也就是说,带"*"时,ServletPath 获取的是"/*"前面的内容(没有斜杠),不带"*"时,获取的是全部内容(有没有斜杠取决于输入的URL)。

    RequestURI 则比较统一,都等于: /{项目名}+全路径(有没有斜杠取决于输入的URL),例如

    输入的是:

    http://localhost:8081/zollty/ds,则为/zollty/ds(不带斜杠)

    输入的是:

    http://localhost:8081/zollty/ds/,则为/zollty/ds/(带斜杠)

     

    另外,getContextPath等于 "/" + 项目名称 ,即: /{项目名},也比较常用,但是每次都去取,比较麻烦,还不如把项目名称作为一个静态常量。

     另外,servlet url的解析顺序如下:

    准则1、   在servlet-mapping配置中,带"*"的优先级,大于不带"*"的;

    准则2、   系统自带的servlet,比如default Servlet、jsp Servlet,优先级高于自定义的servelt的(将优先处理),但是这些servlet如果处理不了,会把请求转发到后续的servelt去处理。

    准则3、   同一文件中的配置,前面的servlet-mapping配置,优先级高于后面的servlet-mapping配置。

    另外,说明一点:  

       带"*"的配置方式,是强行拦截,只要匹配上,请求都会被拦截(比如,/*会拦截所有请求,*.jsp 会拦截所有 以.jsp结尾的请求。

       不带"*"的配置方式,理论上是“精确拦截”,只会拦截和设置的url精确匹配的那一个请求的url,比如/prog,则只有http://...{项目名}/prog请求才会被拦截,

    其他比如http://...{项目名}/prog/、http://...{项目名}/prog/abc等,都不会被拦截。但是设置成 "/" 时,是个例外,它会拦截所有请求(进一步说,"/"的拦截范围和"/*"的拦截范围其实是一样的,只不过"/*"不仅仅是拦截范围广,更重要的是它的优先级高,比没有设置"/*"的系统自带的servlet优先级还高)。

    以下是本人亲自测试多次的结果:

    优先级从高到低,依次为:

    <servlet-name>default</servlet-name>

    <url-pattern>/*</url-pattern>

    <servlet-name>jsp</servlet-name>

    <url-pattern>/*</url-pattern>

    <servlet-name>{自定义的servlet}</servlet-name>

    <url-pattern>/*</url-pattern>

    <servlet-name>jsp</servlet-name>

    <url-pattern>*.jsp</url-pattern>

    <servlet-name>default</servlet-name>

    <url-pattern>/</url-pattern>

    <servlet-name>{自定义的servlet}</servlet-name>

    <url-pattern>/</url-pattern>

  • 相关阅读:
    Oracle 删除某个用户下的所有对象,执行需谨慎
    ORACLE常用性能监控SQL
    mysql千万级大数据SQL查询优化
    qt小例子:实现阿里云物联网设备登录信息计算器
    mqtt协议
    亚马逊物联网平台c-sdk的使用
    esp32-cam开发环境搭建
    qt小例子:实现选值框和滑块同步变化
    在qt5中使用qtmqtt库
    将short类型转换为char类型
  • 原文地址:https://www.cnblogs.com/zollty/p/3319999.html
Copyright © 2020-2023  润新知