disabling log4j in the common jar file - java

I have problem with log4j.xml. I am using one common jar in my standalone application. The commom jar has its own log4j.xml file. The problem is my Unix server is not having the file structure specified in the common jar log4j.xml file so i am getting file not found error , when it tries to create log file.
I have tried to override the log4j.xml file by writing a new log4j.xml file in my application. But still common jar is using its own log4j configuration. I am running my Application using a shell script. Can you please help in disabling or overriding log4 configuration in the common jar .either from java side or any shell script command.
Thank you.

Start the java application with -Dlog4j.configuration=com/foo/bar/log4j.xml in order to use a specific config file, overriding the one found in your jar, or make sure another log4j.xml is at the root of the classpath, before common.jar:
java -cp aDirectoryContainingLog4jXml;common.jar com.foo.bar.Main

Related

Unexpected classpath behaviour remote deployment of Java application with Netbeans 13

Can anyone help me understand the classpath logic when deploying Java applications to remote hosts?
Netbeans will build, deploy and execute my Java application correctly on a remote Linux (Ubutntu 20.x) host.
Lets say that the executable JAR is deployed and executed in:
/home/user/project/dist
With any supporting library files copied to:
/home/user/project/dist/lib
This all makes sense to me.
However, I wish to read application and log4j2 configuration files. I would think that these should be placed in the same directory as the jar file. However they must be placed in the parent directory:
/home/user/project
Okay... BUT...
If I amend my code to write out a text file (to the executable directory) the resulting text file is written to:
/home/user/project/
<Edited 19Jun22>
I want my deployed application to read the log4j2.xml and configuration files from the same directory that my application writes to. What configuration settings must I change in Netbeans?
Alternatively is there a way to make Netbeans deploy to /home/user/project instead of /home/user/project/dist?

Spring: Configure PropertyPlaceHolder when Property File outside Jar File

I have a SPRING 2.5.6 based project and my properties file is outside executable Jar file like
./
|---MyApplication.Jar
|---MyApplication.properties
I don't know how to configure PropertyPlaceholderConfigurer so that it can pick the file outise of JAR file or any other way by which spring can know the location of properties file. In other words How to put Jar root path in class-path because spring can automatically pick the properties file from class-path.
I have read the following Questions but it did not exactly tell how to configure PropertyPlaceholderConfigurer.
Read properties file outside JAR file
Add properties file to build path of runnable jar
java -jar -cp . ./main.jar
I know this way of adding root path into class-path but my client do not want to run jar by command line or batch file. So is there a way to configure Spring somehow?
I think of possible solution is to make JAVA base configuration alongside xml base configuration.
java -jar -cp . ./main.jar
Change run command.
Solution- To get the directory where jar is located, spel can be used.
The following should get you going.
<context:property-placeholder location="file:///#{T(java.lang.Object. getClass().getProtectionDomain().getCodeSource().getLocation‌​())}/ application.properties"/>
You can use Maven or Gradle to manage your project, he can help you automatically add dependencies, you do not need to manually import Jar package.

log4j likes its properties in a jar file?

I have a Java application which I'm executing on Linux direct from an executable jar file
java -cp .:./lib -Duser.timezone=GMT -Dlog4j.debug -jar programName.jar
The program uses a number of other jar files which are all in one directory and 4 properties files all of which are in another directory (the current directory). Both directories are included in the CLASSPATH.
Simple enough right.
It would be, except that Log4j fails to find log4j.properties. The only way I have managed to make it find log4j.properties is to include it in programName.jar
This is not what I want, I want to have it using log4j.properties residing in the same directory as all the other properties files, they are in the CLASSPATH and are found as you would expect.
The other jar files being used are:
jdom-2.0.5.jar
log4j-1.2.17.jar
ojdbc7.jar
quartz-2.2.1.jar
slf4j-api-1.7.7.jar
slf4j-log4j12-1.7.7.jar
I'm wondering if slf4j-log4j12-1.7.7.jar does some configuration which prevents log4j from scanning the CLASSPATH when looking for the properties file. My code does not include any instructions which aim to specify the location of the properties file.
I've not yet tried executing the program without the -jar option, I will try that next.
Does this ring any bells so far ?
Add an argument to jvm (log4j.configuration). e.g.:
java -cp .:./lib -Dlog4j.configuration=file:log4j.properties -Duser.timezone=GMT ...
You may want to see this answer for more options.

log4j.xml in current directory not found

I have a runnable jar file.
I have a log4j.xml file sitting in the same directory.
My classpath includes "."
env |grep CLASS
CLASSPATH=.;C:\Program Files (x86)\Java\jre6\lib\ext\QTJava.zip
But when I run java -jar myrunnable.jar I get the following message.
log4j:WARN No appenders could be found for logger (org.apache.commons.configuration.PropertiesConfiguration).
log4j:WARN Please initialize the log4j system properly.
log4j:WARN See http://logging.apache.org/log4j/1.2/faq.html#noconfig for more info.
Oddly enough, if I wrap that jar in a launch4j executable, it sees the log4j.xml file and uses it.
I did go to the FAQ page mentioned in the error message. It reads as follows:
This occurs when the default configuration files log4j.properties and log4j.xml can not be found and the application performs no explicit configuration. log4j uses Thread.getContextClassLoader().getResource() to locate the default configuration files and does not directly check the file system. Knowing the appropriate location to place log4j.properties or log4j.xml requires understanding the search strategy of the class loader in use.
I am at a bit of a loss in understanding what I need to do in order for my runnable jar to see the log4j.xml short of adding the -Dlog4j.configuration=file:\\\\my\crazy\long\path\to\my\eclipse\workspace\target\directory\log4j.xml to the command line which is a PITA to type out.
If I try something like java -Dlog4j.debug -Dlog4j.configuration=.\\log4j.xml -jar myrunnable.jar
log4j: Trying to find [.\\log4j.xml] using context classloader sun.misc.Launcher $AppClassLoader#265f00f9.
log4j: Trying to find [.\\log4j.xml] using sun.misc.Launcher$AppClassLoader#265f00f9 class loader.
log4j: Trying to find [.\\log4j.xml] using ClassLoader.getSystemResource().
log4j: Could not find resource: [.\\log4j.xml].
same results for different combinations log4j.xml and ./log4j.xml
If it makes a difference, this is windows 7/java 7/64 bit using log4j via the standard slf4j-log4j binding.
Additional notes:
tried java -cp . unsuccessfully
tried java -cp .\\ as well
examined jar file META-INF\MANIFEST.MF and there is no classpath entry
this particular jar was generated by maven using the maven shade plugin.
Solution (sort of)
Per Dave Newton's answer below, I changed my MANIFEST.MF file to include the following line:
Class-Path: ./
With this in place, my log4j.xml file was seen appropriately. I'm using the Maven Shade Plugin to build the jar file, so adding the Class-Path entry was a matter of configuring the ManifestResourceTransformer.
<transformer implementation="org.apache.maven.plugins.shade.resource.ManifestResourceTransformer">
<mainClass>my.runnable.Class</mainClass>
<manifestEntries>
<Class-Path>./</Class-Path>
</manifestEntries>
</transformer>
I say "Sort of" resolved because although it does output logging information configured from my desired log4j.xml file, it means hardcoding that path into my jar and anybody using my jar has to have log4j.xml or log4j.properties in the installation directory. I wish there was a better solution that provided the standard and expected results (where the log4j.xml/log4j.properties file could be placed anywhere on your classpath), but with all the searching I've done today it does not seem to be the case.
I think I've run into yet another one of those frustrating issues where Java does not behave intuitively and anything beyond a very simple explanation of why it behaves the way it does involves reading an entire book.
When you use -jar the classpath is ignored.
You could add the config file to your manifest's Class-Path entry, but consider providing the path. It probably needs to be a file resource otherwise it'll probably try to find it on the jar's classpath value.
For Eclipse testing in Maven the easiest thing I've found to do is to put the log4j.xml in src/test/resources. It will be added to the classpath when running unit tests, etc. When we actually install our application at a customer site we place the file in /etc/... and specify it with -Dlog4j.configuration.
My best guess as to why the current directory part isn't working for you is that Eclipse is probably setting the current directory to something other than what you think it is. Try following the instructions here to print the current working directory and check it matches what you think.
UPDATE: Almost forgot. When you specify -jar the classpath options (-cp -classpath) are ignored.
-jar
Execute a program encapsulated in a JAR file. The first argument
is the name of a JAR file instead of a startup class name. In order
for this option to work, the manifest of the JAR file must contain a
line of the form Main-Class: classname. Here, classname identifies the
class having the public static void main(String[] args) method that
serves as your application's starting point. See the Jar tool
reference page and the Jar trail of the Java Tutorial for information
about working with Jar files and Jar-file manifests. When you use this
option, the JAR file is the source of all user classes, and other user
class path settings are ignored.

how to write Java Code to let JPA/hibernate know where to look for Configuration files?

I'm a newbie to JPA, hibernate and Java itself.
I have somehow made my code work to access values from a DB.
When I extract my final jar of jars, I have a META-INF directory which has persistence.xml in it.
The hibernate.properties and hibernate.cfg.xml are also inside my jar.
So at runtime I'm unable to do any changes to these files since everything is inside jar.
I want to move persistence.xml, hibernate.cfg.xml and hibernate.properties outside jar and place them somewhere in deployment environment. I can do this but I don't know how to write Java Code to let hibernate know where to look for these files.
E.g. for log4j I can use PropertyConfigurator.configure("/opt/somepath/log4j.properties") and tell log4j where log4j.properties file is present.
Could anyone please help me and direct me to some links where I can learn to load configuration for JPA and hibernate at runtime ?
I want to point to different DBs at runtime and test them without changing my jar of jars.
jpa/hibernate scans classpath where looking for configuration files. You can always add to classpath directory/directories.
MY_DIR1 = path/to/my/dir1
My_DIR2 = /path/to/my/dir2
java -cp ${CLASSPATH}:${MY_DIR1}:${MY_DIR2} ...
Put META-INF directory to ${MY_DIR1} ( or/and ${MY_DIR2})
With the help of ajozwik Answer I solved my problem as follows ->
Created a /path/to/mydir directory at some place in my deployement system.
Moved META-INF and hibernate.properties and hibernate.cfg.xml to mydir.
Directory Structure->
mydir
META-INF
persistence.xml
hibernate.properties
hibernate.cfg.xml
Added mydir to class path while launching the executable.
Instead of launching the executable using
java -jar Myjar.jar
I launched it using
java -cp Myjar.jar:/path/to/mydir MyMainClass

Categories