This post is about allowing your jsp web application to be installed in different folders. Lets say the web application is called myapp and the domain is www.acmewebapps.com. We could have different locations for the application:
- The default folder: www.acmewebapps.com/myapp/index.jsp
- The root folder: www.acmewebnapps.com/index.jsp
- Custom folder: www.acmewebapps.com/myapp2/index.jsp
We can move the location of the web application by changing the "Context" entry in the tomcat servers.xml:
- Default: <Context docBase="myapp" path="myapp" reloadable="true"="org.eclipse.jst.j2ee.server:myapp" />
- Root: <Context docBase="myapp" path="" reloadable="true"="org.eclipse.jst.j2ee.server:myapp" />
- Custom: <Context docBase="myapp" path="myapp2" reloadable="true"="org.eclipse.jst.j2ee.server:myapp" />
The trouble is that changing the location of the application changes the references to pages within the application. Probably the links in your application use relative references, but these can be tricky to get just right.
On the client side we might have different types of link like:
- Css resource: <link type="text/css" href="includes/style.css">
- Script link: <script type="text/javascript" src="includes/util.js">
- Regular hyperlink: <a href="about.jsp>About</a>
We could also have server side includes like:
- <jsp:include page="/includes/header.jsp">
The server side links are easy, just include a leading slash and tomcat will look for the page in the context root folder of the web application.
For client side includes add "<%=request.getContextPath()%>/" and then use the relative path in your web app. This will allow your web app to be redeployed to any folder.
Why this way? For client side links the full path is created by the web browser. If the relative url starts with a slash then it is added to the domain of the referring page. If the relative url doesn't start with a slash then the it is added to the path of the referring page. Lets assume that we want to link to a style sheet with url:
www.acmewebapps.com/myapp/includes/style.css
For example consider these links from the page www.acmewebapps.com/myapp/index.jsp:
- href="/includes/style.css" gives www.acmewebapps.com/includes/style.css Incorrect, missing web application folder
- href="includes/style.css" gives www.acmewebapps.com/myapp/includes/style.css Correct
The first style without a leading slash works, since the context root of the web application is kept. But note that the second style, with the leading slash only works if the web application root is in the root of the domain - in this example the myapp folder is missing.
However, the first style also has drawbacks if referencing a page from a different subfolder, consider links from a page in the admin subfolder www.acmewebapps.com/admin/config.jsp:
- href="includes/style.css" gives www.acmewebapps.com/myapp/admin/includes/style.css Incorrect, extra folder in path
- href="/includes/style.css" still gives www.acmewebapps.com/includes/style.css Incorrect, missing web application folder
- href="../includes/style.css" gives www.acmewebapps.com/myapp/includes/style.css Correct
This would work, but we have to always remember to add the correct number of ".." entries to the path. Which means that we can't use server side include of standard 'boiler-plate' includes, such as menu.jsp, because the paths will change depending on where the server side include is used.
The way to do client side includes in a way that works anywhere is to explicitly refer to the web application context root in your server side generation of the include, as follows:
<%=request.getContextPath()%>
So that the full include for the style.css example looks like:
href="<%=request.getContextPath()%>/includes/style.css"
To recap - for server side includes, just start with a slash and use the relative path in your web app. For client side includes add "<%=request.getContextPath()%>/" and then use the relative path in your web app. This will allow your web app to be redeployed to any folder.
Recent Comments