Tomcat:一个webapp的两个上下文路径

Tomcat:一个webapp的两个上下文路径,tomcat,Tomcat,问题是: 我有一个web应用程序,此web应用程序部署到$TOMCAT_HOME/webapps/XXX目录。 我可以在http://localhost:8080/XXX地址 但是,我想访问http://localhost:8080/YYY地址也是。 我在server.xml中添加了以下内容: <Server> <Service> <Engine> <Host> ...

问题是: 我有一个web应用程序,此web应用程序部署到
$TOMCAT_HOME/webapps/XXX
目录。 我可以在
http://localhost:8080/XXX
地址 但是,我想访问
http://localhost:8080/YYY
地址也是。 我在server.xml中添加了以下内容:

<Server>
    <Service>
        <Engine>
            <Host>
                .......
                <Context path="/YYY" docBase="XXX"></Context>
            </Host>
        </Engine>
    </Service>
</Server>

.......
这有所帮助,但Tomcat启动了两个web上下文,并导致了其他一些问题。
是否可以为一个web应用创建“多个”地址?

尝试使用crossContext属性:

<Context path="/YYY" docBase="XXX" crossContext="true"></Context>

web应用程序的url如下所示:

协议://DOMAIN:PORT/CONTEXT/pagename

在两个不同地址上使用相同应用程序的解决方案如下:

  • 如果您只想在协议(比如http和https)上有所不同,那么在server.xml中只需要两个连接器

  • <Context docBase="myapp" path="/address1" reloadable="true" />
    <Context docBase="myapp" path="/address2" reloadable="true" />
    
  • 如果你想在域名上有所不同,那么这是在DNS级别上解决的

  • 如果您想在上下文名称(web应用程序名称)上有所不同,应该将apache放在前面(mod_proxy或mod_ajp),然后创建一个重写规则(mod_rewrite)。让我们假设将所有从
    /a/*
    /b/*
    重写为
    /c/*

  • 如果您想在页面名称上有所不同,那么应该使用servlet映射

  • 通过mod_代理将apache放在tomcat前面非常容易,因为web上有多种资源。复制应用程序(将所有内容加载两次)是非常糟糕的

    至于你的问题,我建议不要在server.xml中重复

    <Context docBase="myapp" path="/address1" reloadable="true" />
    <Context docBase="myapp" path="/address2" reloadable="true" />
    
    
    

    这是内存的杀手,也是会话机制、并发性等的杀手。

    尝试使用Tomcat的重写阀(docs)

    {TOMCAT_HOME}/conf/server.xml

    <Host name="localhost" ... >
        <Valve className="org.apache.catalina.valves.rewrite.RewriteValve" />
    </Host>
    
    注意Tomcat 9文档()中的这个安全警告

    安全警告:由于Java的正则表达式匹配的方式,格式不良的正则表达式模式容易受到“灾难性回溯”(也称为“正则表达式拒绝服务”或重做)的攻击。因此,重写规则模式时应格外小心。一般来说,很难自动检测出这种易受攻击的正则表达式,因此一个很好的防御方法是阅读一些关于灾难性回溯的内容。一个很好的参考是OWASP重做指南


    明确地说,它仅在您希望使用
    ServletContext\35; getContext()
    访问另一个上下文时才允许返回该上下文。不过,我不确定这是否符合问题中发布的信息。是的,你是对的。我很久以前就调查过这件事,还记得我对它有些困惑。很抱歉。在发布建议之前,你应该仔细研究一下。@david rabinowitz:这个问题有没有你感兴趣的特定部分,以及因此而得到的赏金?既然Tomcat将使应用程序在/XXX和/YYY上都可用,如果你这样做映射的话。你不能只做一个JSP重定向吗?因此,在tomcat/webapps/YYY/目录中放置一个index.jsp,它执行重定向或转发。请问您为什么要这样做?Http服务器代理重定向是使其工作的最简单方法。这并不能解决问题。您只需部署两个不同的Web应用程序,而不是同一个。您必须使用URL重写。项目符号1、2、3中列出了2个地址的1个web应用的解决方案。这些提议都不意味着两个不同的webapps。你的评论是针对哪个解决方案(段落)的?我面临着同样的问题,第三个选项是最好的。然而,这给我带来了另一个问题。在我的例子中,我的webapp使用摘要身份验证进行保护,而在摘要中,浏览器发送的密码是某种或多或少复杂的哈希值,其中包含URI。浏览器的URI不是webapp的URI(我用mod_rewrite修改了它),因此身份验证失败。如何解决这个问题?基本身份验证是附加到HTTP请求的一个简单HTTP头。它不应该包括uri(例如:“授权:Basic ZGV2OnNwaWwxMQ==”)。所以,若两个站点的身份验证提供程序相同,那个么就不会有问题。否则,您可以在Apache上重写时始终附加头。