I deployed a war file onto a Tomcat 7 instance running on a remote Linux machine and I'm getting FileNotFoundExceptions.
One of the referenced jars in the project, which contains code that I did not write, uses several files (which I have included, but it is not finding). These files are located in the classes folder. It appears the classpath I have set for the project is being ignored by this jar. These files that it uses, e.g. .properties files are external to the jar.
Here is an example of how it is invoking the files:
FileOutputStream fos = new FileOutputStream("Key.ser");
I was getting these errors when developing the source project in Eclipse. I was able to configure the project to tell it where to find these files via Run Configurations -> Arguments -> Other but the exported .war file appears to not have this bundled with it, only the source project has it. Now I'm seeing them again when trying to deploy the application to Tomcat on another server via war file.
How do I configure the deployed jar file in the deployed Tomcat 7 webapp to find these files that the jar uses? I am loathe to change the code since I did not write it so am really hoping to avoid this.
I am able to get this to work on a local Tomcat 7 running on Windows instance integrated with Eclipse as explained earlier so I'm wondering if maybe this can be duplicated?
You will not be able to find the file by simply referencing the file name using FileOutputStream. You are correct to place the file in the 'WEB-INF/classes' directory, which will allow it to be located on the classpath.
To load the file, you need to load it as a classpath resource using something similar to this:
String classpathLocation = ""Key.ser"";
URL classpathResource = Thread.currentThread().getContextClassLoader().getResource(classpathLocation);
// Or if you want it as an inputstream:
InputStream input = Thread.currentThread().getContextClassLoader().getResourceAsStream(classpathLocation);
Related
I created one java micro service using spring boot. The application requires some data from static xml files (kept together in a folder, lets name it X) in src/main/resources folder.(I am using STS IDE)
It is working fine when I run it in the IDE itself.
Now when I pack it in a jar and try running it using CLI (java -jar jarFileName.jar) it works and access the folder X from the target/classes folder.
Now my problem is, when I try to deploy this small app on Pivotal Cloud Foundry using either CLI or STS plugin, I have to give a path to the jar file so it uploads only the respective jar file and starts the container with the application. But the application cannot access folder X which contains its resources.
Though I confirmed that the jar file contains the folder X in BOOT-INF/classes but it tries to find the folder X on its own path - not inside itself.
Does anyone have some idea how can a jar file deployed on PCF can access its resources kept inside itself.
I tried using
InputStream is = this.getClass().getClassLoader().getResourceAsStream("X/abc.xml")
but it didn't work. It is unable to find the path during runtime.
why do not try Apache Abdera.
your XML is obtained from an API.
just another way, btw.
In your main class(usually Application.java) add #ImportResource annotation at class level.
Example: #ImportResource("classpath:myfile.xml")
This question already has answers here:
getResourceAsStream() vs FileInputStream
(6 answers)
Closed 7 years ago.
I am currently writing a servlet based application (the client side). I tried to get a text file inside the same package where the code is located. All of the methods that I have come across used either MyClass.class.getResourceAsStream("Words.txt") or classLoader.getResourceAsStream("Words.txt") to get the text file (eg: SO1, SO2). But I have tried FileInputStream("./src/package/Words.txt") and the text file can still be successfully loaded.
What are the differences? And why is the method getResourceAsStream encouraged?
At the moment, you're on your developer workstation, and are probably running your app from your IDE. Tomcat happens to be started from the IDE project root directory, and thus using
new FileInputStream("./src/package/Words.txt")
allows reading the file stored in your project src directory.
But that's not how the project will be run in production. In production, you'll have a Tomcat server started from a totally different directory, using a shell script. And the production server won't have the source project at all. All it will have is Tomcat, and the war file constituting the artifact built from the project.
So there will be no src directory at all, and the file Words.txt won't even be anywhere on the file system. It will only be en entry of the war file (which is in fact a zip file), located under WEB-INF/classes/package along with the .class files produced by the compiler from your Java source files.
So, in order to be able to read that "file", you can't use file IO: the "file" doesn't exist in the file system. You need to use the ClassLoader that will locate the "file" inside the war file and load it from there.
That will also go fine during development, when the app is run from an exploded war structure: the class loader will find the class under the target directory used by your IDE to store the class files and resource files.
Note that what you need to load that resource, if it's in the package com.foo and MyClass is in that same package, is
MyClass.class.getResourceAsStream("Words.txt")
or
AnyOtherOfYourClassesWhateverThePackageIs.class.getResourceAsStream("/com/foo/Words.txt")
or
classLoader.getResourceAsStream("com/foo/Words.txt")
I previously used the following to get my context path on Tomcat-5.0.28 and earlier:
String context_path = context.getRealPath("/WEB-INF/");
This worked to return the path to that folder.
But on OpenShift (Tomcat 6 - JBoss EWS 1.0) this returns
/var/lib/openshift/53.*context_id_here*..18/jbossews/null
The null should be:
work/Catalina/localhost/_/WEB-INF
How can I get the path to the WEB-INF folder on OpenShift using JBOSS/Tomcat?
A little background information: When I ran this struts webapp on my own Tomcat server, I deployed a appname.war file in the webapps directory and waited for it to expand (since I had set that option in the server.xml file). Then I move a folder to webapps/appname/ folder with xml files I need to read and write to for my app to work. On OpenShift I used jar xvf appname.war to extract the war file by hand (because that's the default and I don't know how to change it), and then moved the files folder (from the same directory as the war file in my folder after a git add and push) to work/Catalina/localhost/_/WEB-INF/
This is causing a NullPointerException for me when trying to use that path as shown above.
I think you should be using something like getServletContext or getRealPath, and reading it from the web root instead of trying to find the file on the physical disk. That way your war file can run anywhere without issue. Try looking up both of those and see if one fits your use case.
I have recently moved a webapp I have been developing to a new machine running 64bit Eclipse Helios (Service Release 2) and I am using Maven plugin M2Eclipse.
I have deployed on a local tomcat install through Eclipse and everything is ok (more or less), but I want to select the option "Serve Modules without publishing", but when I select this option I get errors:
log4j:ERROR Could not read configuration file from URL [file:/C:/butterfly/svn/trunk/micro/src/main/webapp/WEB-INF/classes/log4j.properties].
java.io.FileNotFoundException: C:\butterfly\svn\trunk\micro\src\main\webapp\WEB-INF\classes\log4j.properties (The system cannot find the file specified)
The log4j.properties file is not there, as in my source directories in lives in src/main/resources - at build it then gets copied over to target/WEB-INF/classes/..
Eclipse seems to be mixing the expected target directory with the src directory so not finding it.
Im not sure if this is happening for just the properties file or if the same problem will occur looking for all built resources.
I have seen these issues:
https://bugs.eclipse.org/bugs/show_bug.cgi?id=318449
http://www.eclipse.org/forums/index.php?t=msg&goto=661045&S=25bafd85b11e042c169ecf1752bfa479
but they seem to be slightly different or already fixed (My Helios is a new download from last weekend)
Anyone experience this or know how to resolve?
From here: "The Serve modules without publishing option does what it says. Web content will be served directly from the "WebContent" folder of the Dynamic Web Project. A customized context is used to make the project's dependencies available in the Web application's classloader". I would expect eclipse to emulate serving every class / resource file (including log4j.properties) from WEB-INF/classes after you build the project. As a workaround, what about creating a "classes" folder inside WebContent, copy log4j.properties file here and see if the classloader gets happy?
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.