Tomcat updates context.xml but should not - java

Tomcat documentation (http://tomcat.apache.org/tomcat-6.0-doc/config/context.html)
Only if a context file does not exist for the application in the
$CATALINA_BASE/conf/[enginename]/[hostname]/, in an individual file at
/META-INF/context.xml inside the application files. If the web
application is packaged as a WAR then /META-INF/context.xml will be
copied to $CATALINA_BASE/conf/[enginename]/[hostname]/ and renamed to
match the application's context path. Once this file exists, it will
not be replaced if a new WAR with a newer /META-INF/context.xml is
placed in the host's appBase.
Text in bold is clear. But I notify as not true. (I need exactly this behaviour)
Here are steps:
aaa.war with context.xml included into META-INF
copy to webapps. tomcat deploys. File conf\Catalina\localhost\aaa.xml OK
change aaa.war by changing META-INF/context.xml
copy to webapps
File conf\Catalina\localhost\aaa.xml is changed!!!
What is wrong? Is it a bug or a hidden feature?
Background - the issue I want to resolve:
Configuration independent build and installation. I plant to ship war file. Client per-configures his Tomcat using his own settings. when I ship a new release I just delivery the war without config and when deployed it will use client specific configuration.
By documentation the best place is the context.xml But if it overwritten each time it make no sense to use at all. (why would I use JNDI and such a things if new deliverable has to created? Changing something in build-time is not a big configuration advantage.)
Environment: windows, tomcat 6.0.33

I've run into the same problem and the documentation is at least inadequate, if not directly misleading.
The problem is, that if you copy a new version of an already deployed WAR file to the webapps directory, Tomcat will not redeploy the existing application but undeploy the old application and then deploy the new application. The difference may first seem insignificant, but the problem is that during undeployment of the old application, any context files in conf/Catalina/localhost are deleted as well. Then, the new context file from the current WAR file will be copied to conf/Catalina/localhost during deployment of the new application.
The only feasible solution I've found is not to deploy the new application as a WAR file, but to replace or overwrite the expanded directory, e.g. not to copy aaa.war to webapps/ but to unpack aaa.war directly into webapps/aaa/.

Related

Tomcat, change name of deploy dir for war file

This may not be a difficult question, but I probably do not have the right terminology and am not finding the answer.
When I deploy a war file in Tomcat (7), say, myapp-1.0.war, a new directory, myapp-1.0, is created under webapps. Is there a way to change the name of the new directory? e.g. When I deploy myapp-1.0.war, the new directory is named myapp? Is this configurable inside the war file somehow?
I have implemented this by adding a symlink to the webapps directory and placing my war file in a directory outside of the appBase. This way I was able to standardize the docBase in the server.xml. Now all I have to do is update the symlink when new versions are posted (and maybe restart the server). My configuration is posted at another question:
Tomcat 7 symbolic link to war file

When does Tomcat unpack a war file to a ROOT folder?

I'm trying to deploy a war on Tomcat 7.0, and in the server.xml file, I've set unpackWARs = true and autoDeploy = true.
Since I want this war file to be the default web application, I have deleted the ROOT folder inside ...Tomcat7.0/webapps. Then on, when I try to start the Tomcat service, I see a behavior that I have yet failed to identify a pattern in:
Sometimes, the war is unpacked to a newly created folder named
'ROOT'.
Some other times, it is unpacked to a folder that is named
the same as the name of the war file. E.g. if the war file is
'MyWebApp.war', it's unpacked to a folder named 'MyWebApp'.
It seems to be completely erratic and random, but I am sure there is method behind this apparent madness. As a rule, I am not sure if there is anything that dictates the creation of a ROOT folder. I have tried to edit the server.xml file and add context to my web application in it, but it doesn't seem to make a difference.
What am I missing? Thanks in advance!
Name your war file ROOT.war. It will unpack to ../webapps/ROOT and map to / context

Deploying war file to Tomcat with a different path

If I deploy a war file to Tomcat, called for example foo-bar-1.1.2.war, how can I deploy it so that it is extracted to webapps/bar and its URL root is /bar/...?
My intention here is to keep the war file in the webapps server with its version information so that I know which version is installed but have it overwrite a previous version of the app.
I could deploy the war file using PSI Probe. This would allow me to specify a target context for the web app. However, it means that I would lose any version information in the war file name.
Tomcat will always extract the contents of a war file, to a folder of the same name (when it's configured to deploy wars - as default etc.).
You can extract it to a folder name of your choice. So if you unzip the contents of foo.war to a folder called bar/ manually, instead of just dropping the war into the web apps folder, it'll still load the web application.
However, this is totally unnecessary as you can specify the URL pattern of the application without messing with the folder / war file name at all by overriding the context root element for your application:
This is often set in the Tomcat server.xml - but that practice is fairly widely discouraged. Instead, I'd suggest you use context.xml in the META-INF folder of your web application / war file:
<Context path="/bar" .../>
When the application is deployed, the context.xml should be copied to /conf/Catalina/localhost but renamed to foo.xml
Note that conext roots must be unique and there are some additional considerations if you're using the autoDeploy or deployOnStartup operations (Source http://tomcat.apache.org/tomcat-7.0-doc/config/context.html).
Other options include:
Clean the web apps folder each deployment and drop your new foo-1.1.0 war in.
Include the version number in a flat file. foo/version1
Or simply include the version in a config / XML file.
You could also use Ant (or an equivalent tool) to automate your deployments (and perform any of the above).
There is an important point to emphasize about the path attribute of the context fragment definition. To cite the documentation on the topic:
When autoDeploy or deployOnStartup operations are performed by a Host, the name and context path of the web application are derived from the name(s) of the file(s) that define(s) the web application.
deployOnStartup is the default behavior of Tomcat hosts.
To follow the documentation, this has a very important consequence:
the context path may not be defined in a META-INF/context.xml
According to the ways of defining a Tomcat context, this lets only two solutions:
In individual files (with a ".xml" extension) in the $CATALINA_BASE/conf/[enginename]/[hostname]/ directory
Inside a Host element in the main conf/server.xml, which is a discouraged solution in a production environment as it requires restarting the server
Another solution takes advantage of the unpackWARs attribute.
In my point of view, for these reasons, the general and easy way to implement a subtle path in a production environment is taking advantage of the naming of war files (what could include versions management and be a solution to your problem). A single sharp (e.g. test#path.war) in the war file names implies a segment in the context path (e.g. /test/path). A double sharp introduces the version number (e.g. test#path##112.war). This works whether or not unpacking war files, hot deployment or not, is deployment agnostic (manager or file system) and manages multiples versions of a same archive.
But if there is the need to have a path distinct from the archive name, it seems the only solution is the descriptor in the /conf/[enginename]/[hostname]/ directory or the server.xml file. For these, you need an access to the server filesystem.
The relevant solution is highly related to the way Tomcat is configured and managed in the everyday.
If you just want to include a version info in your war file name, you can name it like: my-app##1.2.3.war. It gets unpacked to the directory my-app##1.2.3 but the context will be just my-app (i.e. http://host/my-app/).
Works at least with Tomcat 7.0.55

Tomcat context management

The tomcat 6.0 document at http://tomcat.apache.org/tomcat-6.0-doc/config/context.html says:
Only if a context file does not exist for the application in the $CATALINA_BASE/conf/[enginename]/[hostname]/, in an individual file at /META-INF/context.xml inside the application files. If the web application is packaged as a WAR then /META-INF/context.xml will be copied to $CATALINA_BASE/conf/[enginename]/[hostname]/ and renamed to match the application's context path. Once this file exists, it will not be replaced if a new WAR with a newer /META-INF/context.xml is placed in the host's appBase.
However I noticed that if you put new war file in webapp directory, the context.xml in META-INF directory replaces context.xml in $CATALINA_BASE/conf/[enginename]/[hostname].
Is there any configuration which makes sure that context.xml in $CATALINA_BASE/conf/[enginename]/[hostname]/ is not overwritten whenever new war file is deployed.
Edit: I am using autodeploy="true" From the comment of JoseK, I understand when tomcat sees new war file, it undeploys old application (leading to deletion of context file) and deploys the the new war file (leading to creation of new war file). In that case the above information from tomcat document is not relavant. The new question can there be any situation where the above thing can happen?
I agree that the documentation is misleading. Normally, this behaviour is actually welcomed since when you deploy a new version of your application, you want to have your updated context.xml file deployed as well. If you plan on editing your context.xml file manually on your production server, I suggest skip it altogether and copy its content to conf/server.xml file.
A quick patch/solution to your problem (wouldn't do it myself) is to mark the context.xml file as readonly after it has been deployed and updated the first time. This way Tomcat cannot delete/update it.
If you want to avoid overwriting of 'context.xml', you could go to Tomcat Manager url
and then uninstall the previous app and install the new war/ear.
This way you have more control on the installation process.

Problem retrieving properties file from webapp in tomcat

I've developed a web application that worked fine in JBoss 4. Now, I need to make it work in Tomcat 6, but I'm having trouble to access some properties file. I use the following code to read read these files:
InputStream is = Thread.currentThread().getContextClassLoader()
.getResourceAsStream(fileName);
if (is == null) {
throw new StartupError("Error loading " + fileName);
}
properties.load(is);
As I've said before, it works fine in JBoss 4. But when I deploy my app in tomcat, it doesn't find the file, assigning null to 'is' variable, causing the StartupError to be thrown. The file is located at WEB-INF/config directory, and the webapp is deployed as a war.
Any solution for this problem?
Thanks,
Alexandre
Put the properties files in WEB-INF/classes.
Or include them in the root of one of your webapp Jar files, although this makes it harder to edit them. This is good if you're selecting properties within a build script and don't want to edit them once deployed.
I assume that Tomcat does not add WEB-INF/config into your webapp classpath.
from http://tomcat.apache.org/tomcat-6.0-doc/class-loader-howto.html
WebappX - A class loader is created for each web application that is deployed in a single Tomcat 6 instance. All unpacked classes and resources in the /WEB-INF/classes directory of your web application archive, plus classes and resources in JAR files under the /WEB-INF/lib directory of your web application archive, are made visible to the containing web application, but to no others.

Categories

Resources