17

The problem is: I have a web app and this web app is deployed to the $TOMCAT_HOME/webapps/XXX directory. I can reach that on the http://localhost:8080/XXX address BUT, I would like to reach the web app on the http://localhost:8080/YYY address too. I added the following to the server.xml:

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

It helped but the Tomcat started two web contexts and it caused some other problem. Is it possible to create a "multiple" address for one web app?

Cœur
  • 37,241
  • 25
  • 195
  • 267
AlBundy
  • 179
  • 1
  • 1
  • 3
  • @david rabinowitz: is there a specific part of this problem you are interested in, and hence a bounty? Since Tomcat will make the app available on both /XXX and /YYY if you do the mapping this way. – JoseK Aug 26 '11 at 11:02
  • Can't you just do a JSP redirect? so in the directory of tomcat/webapps/YYY/ place an index.jsp which does a redirect or forward. – Tahir Malik Aug 30 '11 at 10:47
  • 1
    May I ask why you want to do this? Http server proxy redirect would be the easiest way to get it working. – Esko Piirainen Jun 10 '14 at 12:03

3 Answers3

6

The url of web application is assebled as follows:

PROTOCOL://DOMAIN:PORT/CONTEXT/pagename

The solutions for having same app on two distinct address are as follows:

  1. If you want to differ only in protocol (let's say between http, and https) then just have 2 connectors in server.xml.

  2. if you want to differ in DOMAIN name, then this is solved on DNS level.

  3. If you want to differ in context name (web application name), you should put apache in front (mod_proxy or mod_ajp) and then create a rewrite rule (mod_rewrite). let's say rewrite all from /a/* and /b/* to /c/*

  4. If you want to differ in page name, you should use servlet mappings.

Putting apache in front of tomcat via mod_proxy is very easy, there are multiple resources on the web. Very bad would be to duplicate applications (have everything loaded twice).

As for your question, i would advise agains duplication in server.xml.

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

This is killer for memory, as well as for session mechanisms, concurency, etc.

Michael Piefel
  • 18,660
  • 9
  • 81
  • 112
Mitja Gustin
  • 1,723
  • 13
  • 17
  • 1
    This does not solve the problem. You simply deploy two **distinct** webapps and **not** the same one. You must use URL rewriting. – Michael-O Jun 20 '13 at 11:11
  • Solutions for 1 web app at 2 adresses are in bullets 1 , 2, 3. None of this proposals means 2 distinct webapps. To which solution (paragraph) is your comment reffering to? – Mitja Gustin Jul 04 '13 at 11:13
  • basic authentication is a simple HTTP header appended to HTTP request. It should not include uri (example: "Authorization:Basic ZGV2OnNwaWwxMQ=="). So if authentication provider is same for both sites, it should not be problematic. Otherwise you can always append header at rewriting on Apache. – Mitja Gustin Dec 10 '14 at 16:10
1

Try using Tomcat's Rewrite Valve (docs here)

{TOMCAT_HOME}/conf/server.xml

<Host name="localhost" ... >
    <Valve className="org.apache.catalina.valves.rewrite.RewriteValve" />
</Host>

{TOMCAT_HOME}/conf/Catalina/localhost/rewrite.config

RewriteCond %{REQUEST_URI} ^/XXX/.*$
RewriteRule ^/XXX/(.*)$ /YYY/$1 [L]

Note this security warning in the Tomcat 9 docs (here),

Security warning: Due to the way Java's regex matching is done, poorly formed regex patterns are vulnerable to "catastrophic backtracking", also known as "regular expression denial of service" or ReDoS. Therefore, extra caution should be used for RewriteRule patterns. In general it is difficult to automatically detect such vulnerable regex, and so a good defense is to read a bit on the subject of catastrophic backtracking. A good reference is the OWASP ReDoS guide.

-3

Try using the crossContext attribute:

<Context path="/YYY" docBase="XXX" crossContext="true"></Context>
Eric
  • 757
  • 5
  • 11
  • To be clear, it only enables returning the other context when you want to access it using `ServletContext#getContext()`. I am however not sure how that fits into the as far posted information in the question. – BalusC Nov 11 '09 at 17:02
  • Yes, you're correct. I had looked into this a while back and remember that I ran into some confusion about it. Sorry about that. Should have looked into it a little more before posting the suggestion. – Eric Nov 11 '09 at 18:40