【问题标题】:web.xml and/or Filters to return welcome-fileweb.xml 和/或过滤器返回欢迎文件
【发布时间】:2014-01-15 11:56:02
【问题描述】:

我需要为特定功能配置我的 Tomcat WAR,但不确定是否可以全部通过 web.xml 完成,或者我是否需要实现 1+ 自定义 Filters,或者使用其他类型的黑客。

我的应用打包为myapp.war。因此,当它从本地 Tomcat 实例提供服务时,我可以通过转到 http://localhost:8080/myapp 来访问它。

很简单,如果 Tomcat 收到以下请求,我希望得到一个 welcome-file (myapp.html):

  • localhost:8080/myapp
  • localhost:8080/myapp/
  • localhost:8080/myapp/#
  • localhost:8080/myapp/#

...其中<blah> 是井号 (#) 之后的任何字符串/正则表达式。

因此,如果用户转到http://localhost:8080/myapp,则返回myapp.html。如果用户去http://localhost:8080/myapp/#fjrifjri,那你猜怎么着?回复myapp.html

但是,如果用户转到 http://localhost:8080/myapp/fizz,那么我希望正常的 web.xml servlet-mapping 逻辑启动,并且我希望 Tomcat 提供任何映射到 @987654335 的 servlet @等

目前我的web.xml 看起来像:

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:schemaLocation="http://java.sun.com/xml/ns/javaee 
        http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"
        version="2.5"
        xmlns="http://java.sun.com/xml/ns/javaee">
    <welcome-file-list>
        <welcome-file>myapp.html</welcome-file>
    </welcome-file-list>
</web-app>

我怎样才能做到这一点?

【问题讨论】:

  • JAX-RS 资源可以工作。可能还有很多其他方式。
  • 根据您当前的配置,哪些情况有效,哪些无效?
  • 谢谢@MarcelStör (+1) - 你是说我已经有这个工作了吗?如果是这样,这怎么可能?!?
  • 关于配置 URL 映射的附加信息请阅读this answer
  • 磅符号指定给定页面(在本例中为欢迎页面)中的目标位置,如果目标不存在,则页面显示相同。

标签: java tomcat servlets web.xml servlet-filters


【解决方案1】:

无需创建过滤器。简单的解决方案是:

  1. 编辑 web.xml

    <welcome-file-list>
        <welcome-file>index.html</welcome-file>
    </welcome-file-list>
    
  2. 将 myapp.html 重命名为 index.html

  3. 编辑 index.html 并在其中某处放置一个带有id="blah" 属性的标签。这是为了 让localhost:8080/myapp/#&lt;blah&gt; 工作。

【讨论】:

    【解决方案2】:

    实现此目的的一种方法是使用过滤器,如下所示:

    • 创建一个过滤器,它映射到web.xml中的根/,如下所示

      <filter>
        <filter-name>myWelcomeFilter</filter-name>
        <filter-class>com.test.MyWelcomeFilter</filter-class>
      </filter> 
      
    • 和过滤器映射如下

    <filter-mapping>
      <filter-name>myWelcomeFilter</filter-name>
      <url-pattern>/*</url-pattern>
    </filter-mapping>
    
    • doFilter() 方法中使用以下代码。
     String pathInfo = request.getPathInfo();
     if(null == pathInfo || pathInfo.startsWith("#") ){
     response.sendRedirect("/myapp/myapp.html")
     }else{
      chain.doFilter(request, response);
     }
    

    【讨论】:

      【解决方案3】:

      使用过滤器 -

      <filter>
            <filter-name>MyFilter</filter-name>
            <filter-class>package.MyFilter</filter-class>          
      </filter>
      <filter-mapping>
            <filter-name>MyFilter</filter-name>
             <url-pattern>/*</url-pattern> 
      </filter-mapping>
      
      public class MyFilter implements javax.servlet.Filter {
      
      
       @Override
       public void doFilter(ServletRequest req, ServletResponse res, FilterChain fc) throws   IOException, ServletException {
      //this method calling before controller(servlet), every request
      
      HttpServletRequest request = (HttpServletRequest) req;
      String url = request.getRequestURL().toString();
      if(url.lastIndexOf("/fizz") > -1) //fix this as it could be /fizz33 too
      {
      
      
          RequestDispatcher dispatcher = request.getRequestDispatcher("fizz.jsp"); //or whatever page..
          dispatcher.forward(req, res);
      } else {
          fc.doFilter(req, res);
      }
      }
      

      【讨论】:

        【解决方案4】:

        web.xml 和 servlet 无法识别 URL 中的“#”,这纯粹是一个前端构造,它告诉浏览器您要转到页面中的哪个链接。您需要做的是为主页设置一个映射,如下所示:

        <servlet>
            <servlet-name>WelcomePage</servlet-name>
            <jsp-file>/myapp.jsp</jsp-file>
        </servlet>
        
        <servlet-mapping>
            <servlet-name>WelcomePage</servlet-name>
            <url-pattern>/</url-pattern>   
        </servlet-mapping>
        

        然后像往常一样进行其余的 servlet 映射。

        【讨论】:

          【解决方案5】:

          正如其他人提到的,您只需要整理/myapp 的servlet 映射; # 之后的映射实际上是多余的。 # 之后的内容,以及哈希本身are never sent to the server anyway

          【讨论】:

            【解决方案6】:

            我最近遇到了和你一样的问题,至少在你的前两个要求方面。这就是我解决问题的方法:

            我的 web.xml 有这个:

            <?xml version="1.0" encoding="UTF-8"?>
            <web-app version="2.5" xmlns="http://java.sun.com/xml/ns/javaee"
                 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                 xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd">
            
            <listener>
                <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
            </listener>
            <context-param>
                <param-name>contextConfigLocation</param-name>
                <param-value>classpath:../myapp-context.xml</param-value>
            </context-param>
            
            <servlet>
                <servlet-name>appServlet</servlet-name>
                <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
                <init-param>
                    <param-name>contextConfigLocation</param-name>
                    <param-value></param-value>
                </init-param>
                <load-on-startup>1</load-on-startup>
            </servlet>
            
            <servlet-mapping>
                <servlet-name>appServlet</servlet-name>
                <url-pattern>/</url-pattern>
            </servlet-mapping>
            </web-app>
            

            我的应用程序上下文(myapp-context.xml)有这个:

            <?xml version="1.0" encoding="UTF-8"?>
            <beans xmlns="http://www.springframework.org/schema/beans"
               xmlns:mvc="http://www.springframework.org/schema/mvc"
               xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
               xmlns:context="http://www.springframework.org/schema/context"
               xsi:schemaLocation="http://www.springframework.org/schema/beans
                                   http://www.springframework.org/schema/beans/spring-beans.xsd
                                   http://www.springframework.org/schema/mvc
                                   http://www.springframework.org/schema/mvc/spring-mvc.xsd
                                   http://www.springframework.org/schema/context
                                   http://www.springframework.org/schema/context/spring-context.xsd">
            
            <context:component-scan base-package="com.toolkt.spring.mvc.app"/>
            
            <mvc:annotation-driven />
            
            <mvc:view-controller path="/" view-name="index" />
            
            <bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
                <property name="prefix" value="/WEB-INF/jsp/" />
                <property name="suffix" value=".jsp" />
            </bean>
            

            我将我的索引文件 (index.jsp) 放在 TOMCAT_HOME/webapps/appctx/WEB-INF/jsp 中。如上所示,我没有将欢迎文件列表放在 web.xml 中。

            当我将浏览器指向 http://localhost:8080/appctxhttp://localhost:8080/appctx/ 我登陆索引文件。

            我使用 spring-framework-3.1.2 并在 windows 7 上的 tomcat-7.0.27 中运行该应用程序。(我的 tomcat 开发服务器中只有两个应用程序 - ROOT 和 appctx

            我希望这会有所帮助。祝你好运。

            【讨论】:

              【解决方案7】:

              您始终可以编写 javascript 或 jsp 或 servlet 代码,您可以在其中判断 url 并根据需要转发请求。

              【讨论】:

                【解决方案8】:

                我认为您正在尝试做的是默认行为。我不知道您为什么要为此使用过滤器。网址:http://localhost:8080/myapp/#fjrifjri 如果您在 web.xml 中使用 myapp.html 作为欢迎文件,或者类似的内容会出现在 myapp.html 中。要打开特定的 servlet,您可以使用 Andrew 提到的 servlet 标记。

                【讨论】:

                  【解决方案9】:

                  如果你需要处理 URL,你需要使用 servletservlet-mapping 标签:

                  <?xml version="1.0" encoding="UTF-8"?>
                  <web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                      xsi:schemaLocation="http://java.sun.com/xml/ns/javaee 
                      http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"
                      version="2.5"
                      xmlns="http://java.sun.com/xml/ns/javaee">
                    <welcome-file-list>
                      <welcome-file>myapp.html</welcome-file>
                    </welcome-file-list>
                  
                    <servlet>
                      <servlet-name>fizz</servlet-name>
                      <servlet-class>demo.fizz</servlet-class>
                    </servlet>
                    <servlet-mapping>
                      <servlet-name>fizz</servlet-name>
                      <url-pattern>/fizz</url-pattern>
                    </servlet-mapping>
                  </web-app>
                  

                  demo 是你的包,fizz 你的 fizz.java
                  要修改附加到当前 url 的 url 和文件,您需要使用 servlet-mapping 标签,其中名为 fizz 的 servlet 映射到 /fizz

                  这将允许您更改您正在寻找的设置。

                  希望对你有帮助...

                  【讨论】:

                  • 正确。作为附加信息:在 web.xml 中配置 servlet 映射的替代方法是使用自 Servlet 版本 3.0 起可用的 @WebServlet 注释(因为 OP 使用 Apache Tomcat它必须是minimum Tomcat 7)。此外,Java by convention 中的类名应以 大写 大小写字母开头(即 Fizz.java
                  • 谢谢@Andrew_Dublin (+1) - 你能给我具体的 servlet 映射来实现我想要的吗?再次感谢!
                  猜你喜欢
                  • 2012-04-26
                  • 1970-01-01
                  • 2015-04-06
                  • 2015-03-21
                  • 2013-04-17
                  • 1970-01-01
                  • 1970-01-01
                  • 1970-01-01
                  • 2014-02-07
                  相关资源
                  最近更新 更多