OpenJPA logging with slf4j on WebSphere - websphere

My Java EE 6 application uses slf4j with logback as logging framework.
Now I want to add the SQL traces of OpenJpa to my log files. The OpenJpa-Documentation says, I can use a parameter to this:
<property name="openjpa.Log" value="slf4j"/>
I use the WebSphere Application Server v8.0.0.1 as Java EE container. If I deploy my application to the server, this parameter does not change anything. I can change log levels in WebSphere Admin Console and this works fine. But a cannot bypass the OpenJpa logging to my slf4j framework.
Does anyone uses such configuration and solved the problem?
Btw. I know, that the InformationCenter-Article http://publib.boulder.ibm.com/infocenter/wasinfo/v8r0/index.jsp?topic=%2Fcom.ibm.websphere.nd.doc%2Finfo%2Fae%2Fae%2Ftejb_jpatroubleshoot.html
says, that the parameter will be ignored, but everything should be possible, eh?

I don't know what version of OpenJPA is embedded in WAS 8.0.
In OpenJPA 1.x there was no possibility to use "slf4j". A workaround was copying the class org.apache.openjpa.lib.log.SLF4JLogFactory from OpenJPA 2.x sources to your application and using it directly:
<property name="openjpa.Log" value="org.apache.openjpa.lib.log.SLF4JLogFactory"/>
You can always specify the factory class name directly, the short name is only a convenience trick.
In OpenJPA 2.x the SLF4JLogFactory is present, so it should work with your current settings; perhaps you set it in a place that is overridden by other configuration? For example, if you configure JPA through EntityManagerFactory's propertyMap, it takes precedence over the settings in persistence.xml.

I solved it.
There are four things to do:
Say that OpenJpa logs the statements. That is done by the property entry in the persistence.xml.
Say Slf4j that it has to fetch the logs from JUL too. This can be done by installing the SLF4JBridgeHandler by SLF4J. I installed the bridge via a ServletContextListener which is called at application start.
Configure Logback that it does not log ALL logs from JUL but only the needed Logs. This is done by adding the LevelChangePropagator in the logBack-test.xml
Ask the WebSphere TraceService to hand down the logs from OpenJPA to the application. This is a setting in the WebSphere Administration Console

Related

Application using jboss-logging when it should use log4j

I'm upgrading a Spring MVC application from Spring 3.1 to 4.3, and Hibernate 3.6 to 5.2. I'll be running this in Wildfly 8. Dependencies are managed by Maven.
Spring uses commons-logging, which looks at the classpath of the application and attempts to choose a suitable logging framework. In my case, it seems to be choosing the wrong one. I have included log4j in my pom.xml, and checking the dependency hierarchy I can see that jboss-logging is not there. Here is the error message I'm getting:
Invocation of init method failed; nested exception is java.lang.NoSuchMethodError: org.jboss.logging.Logger.debugf
So even though I don't have jboss logging in my project, commons-logging is finding it somewhere and attempting to use it, but unsuccessfully. After some searching I found jboss-logging-3.1.4.GA.jar in Wildfly.
The reason for the error is that this is an old version of jboss-logging. I added a newer jar to the server and edited module.xml to point to it, and the error went away. That proves that commons-logging is finding jboss-logging on the server.
The problem is that I don't want jboss-logging, I want log4j. How do I force commons-logging to use log4j and ignore what is on the server?
Edit: I followed the link chrisharm put up and added these lines to the standalone.xml file :
<add-logging-api-dependencies value="false"/>
<use-deployment-logging-config value="false"/>
I also changed the module.xml to point to the older jar again, since I would rather see an error if jboss is used. When I run now I get this:
Caused by: java.lang.NoClassDefFoundError: org/jboss/logging/Logger
This may be a step in the right direction, since now Spring doesn't have access to jboss-logging, but it is still trying to use it for some reason.
https://docs.jboss.org/author/display/WFLY8/How+To#HowTo-HowdoIusemyownversionoflog4j%3F
If you need/want to include your version of log4j then you need to do the following two steps.
Disable the adding of the logging dependencies to all your deployments with the add-logging-api-dependencies attribute and disable the use-deployment-logging-config attribute OR exclude the logging subsystem in a jboss-deployment-structure.xml.
Then need to include a log4j library in your deployment.
This only works for logging in your deployment. Server logs will continue to use the logging subsystem configuration.

Best alternative to Weblogic startup classes in Websphere?

I am working on a Server Migration Project from Weblogic to Websphere. The problem is that in Weblogic, we are already using a class specified as Startup-class in Weblogic (and arguments to the class like log4j config file) which is present in a jar which is added to Weblogic classpath by editing the startup script. This jar initializes a global log4j file which is for all the apps deployed on the server and not for any particular app. Each app is distinguished by a category of log4j.
Now I could not find a similar thing in Websphere. So what is the best solution? I can create a new application which would do all initializations like that of the startup classes. I thought of using startup-beans but read in some IBM documentation that they are deprecated due to EJB 3.1 Session Beans. Also how to make sure this app loads first? By giving Websphere xml file startup weight 1 like here?
I am using Weblogic 6.3.2 and Websphere 8.5
The WebSphere migration toolkit suggests to replace the WebLogic T3StartupDef and T3ShutdownDef implementations with either a ServletContextListener implementation, session startup bean (Singleton), or a servlet that is configured to load at startup time. If you haven't used the WebLogic to WebSphere migration toolkit, check it out. It provides a lot of help especially with deployment descriptor extensions.
The #Singleton session bean in EJB 3.1 replaces the proprietary WebSphere startup bean.
The best approach depends on the type of module you need the startup logic.
If you are considering the custom services option, note that the com.ibm.websphere.runtime package is not available in Liberty if you are considering the Liberty server.
It sounds like custom services (or a custom feature on Liberty profile) are the best analog if you need to run logic during server startup. Otherwise, if you just need to add a library to every application, then create a shared library and then either associate it with the server or associate it with specific applications or modules.

Alternative of JTATransaction

I have an Spring based J2EE application which runs well on Weblogic, I wanted to move it to Tomcat.
It seems tomcat doesn't support JTA Transaction Manager without external jar help like Atomikos, JOTM, Bitronix, SimpleJTA.
I am reluctant to make changes into my application where i am already using annotation based JTA transaction manager.
Are there alternatives for JTA Transaction Manager which I can use so that I am able to switch from weblogic to tomcat or tomcat to weblogic or any other server without changing my configuration file each time?
All in all what's best for transaction manager configuration when you want to keep your application (war) independent of server(s).
You could try TomEE.
It's a Java EE 6 server that meets the Web Profile requirements and is based on Tomcat.
So it will support JTA transactions.
You can get it from http://tomitribe.com
Just to give you a more direct link to TomEE: http://tomee.apache.org/download/tomee-1.7.2.html
If your application is configured and developed to use Weblogic then chances are you are using JDNDI to lookup the JTA transaction manager and your datasources.
So any solution that supports the same lookups would work.
For Atomikos, we recently added (commercial) support for Tomcat's JNDI space - check out http://www.atomikos.com/Main/BuyOnline to learn more.
Hope this helps!

Jetty 8, Weld - Injection isn't working

I'm trying to setup a project using Jetty 8 as the server (jetty-maven-plugin:8.1.11.v20130520), Weld for CDI (weld-servlet:2.0.1.Final), Hibernate for JPA (hibernate-entitymanager:4.2.2.Final, hibernate-jpa-2.0-api:1.0.1.Final) and Jersey for JAX-RS.
It seems that injections isn't working at all.
I tested whether the EntityManager is being injected, and the value was null.
The log doesn't show any errors or warnings while executing the server.
Am I missing something ?
If needed, I will post the log file to gist.
Here is the gist of all relevant files: https://gist.github.com/StalkingKillah/e986474b6885d83c7f8d
This is how I got it working for Jetty 9, and it should be basically the same for Jetty 8.
http://www.eclipse.org/jetty/documentation/current/framework-weld.html
It is easier to have the weld jar outside of the webapp as then you don't have to mess with tweaking the classes exposed to the webapp classloader like you are here (with the -org.eclipse.jetty bit for the ServletContext). I suspect there are more classes that would have to be added to that in order to make it work. You should get a note in the logging that says it is all enabled and active though.

Spring, log4j and JBoss4

I'm running JBoss 4.2.3.GA, and have a web app that uses Spring and Log4j. I've set up Spring's Log4jConfigurer, but am having a problem since JBoss's log4j file is not on the classpath. It's at jboss.home/server/defaul/conf/jboss-log4j.xml. So, without hard-coding the path in Log4jConfigurer, how can I get Spring to use JBoss's log4j file?
You don't generally modify JBoss's log4j config via the applications, that's a route to madness. JBoss uses a shared configuration amongst all apps.
You can, however, programmatically alter log4j's runtime configuration, such as adding custom appenders or loggers. This isn't what Spring's Log4jConfigurer is for, however - you use that to configure a standalone log4j config.
Do answer your question: JBoss usually sets additional system properties that point to the server directory and configuration directories. You should be able to access these from your application or let them be resolved from the spring contexts.
In your case, it should be ok to access ${jboss.server.home.dir}/conf/jboss-log4j.xml
As skaffman correctly pointed out in a comment, there is no need to configure Spring to read JBoss' log4j configuration unless you have otherwise adapted something in the packaging. You will only have to take care that no log4j.[properties,xml] lies somewhere in the root of the classpath or that a component tries to configure Log4J "manually".
Hope this could help,
Kariem

Resources