How to use and configure logback in Adobe CQ5 projects? - java

I newbie in CQ5. I started my first project in CQ and I want to write any exceptions and debug info of project's components, services and servlets (in bundles) to log files in crx-repo (...\crx-quickstart\logs).
I want to use slf4j with logback implementation in my project.
I tried below steps:
Add dependencies in project's pom.xml
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>1.7.7</version>
</dependency>
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-classic</artifactId>
<version>1.1.3</version>
</dependency>
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-core</artifactId>
<version>1.1.3</version>
</dependency>
Add logback.xml with configuration (loggers and appenders) to
project's bundle resource package.
Try to instantiate new logger in service (for example):
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
.....
#Component(metatype = true, label = "Some", description = "Sone service" ,
immediate = true)
#Service(SomeService.class)
public class SomeService {
private final Logger logger = LoggerFactory.getLogger(MyDao.class);
.....
logger.debug("debug");
logger.info("info");
logger.error("error");
......
}
These steps (It isn't work, of course) I gave an example because i don't know how really work with logback in Adobe CQ5. Any suggestions? I would be grateful for any help!

CQ does log to crx-quickstart/logs/error.log with its default configuration, and the underlying Apache Sling framework provides the necessary bridge so you just need to acquire an slf4j Logger and write to that.
The Java code of your SomeService example looks correct to me but in the pom you only need the slf4j-api dependency, with scope provided, as API and implementation packages are provided by the CQ runtime.
You can also have a look at a Sling sample like Slingbucks which will log to that error.log if installed on a default CQ instance.

Related

Migrating JUL to log4j2, performance is not as expected. What went wrong?

I am a new user of log4j2. Based on Log4j2 performance tests introduction, and it may need to generate a large number of csv files for data processing. I plan to migrate a project from JUL to log4j2. This is a multi-threaded project that uses a lot of loggers. But the test results are not satisfactory . Where did I get it wrong?
the compare results
The dependency configuration is as follows:
<!-- Log4j2 api -->
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-api</artifactId>
<version>2.11.1</version>
</dependency>
<!-- Log4j2 impl.-->
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-core</artifactId>
<version>2.11.1</version>
</dependency>
<!-- for Log4j2 asynchronous logging-->
<dependency>
<groupId>com.lmax</groupId>
<artifactId>disruptor</artifactId>
<version>3.4.2</version>
</dependency>
<!-- for Log4j2 csvlayout-->
<dependency>
<groupId>org.apache.commons</groupId>
<artifactId>commons-csv</artifactId>
<version>1.5</version>
</dependency>
File "log4j2.xml" has multiple similar appenders and loggers, for example:
partial configuration for log4j2.xml
Java related code is as follows:
System.setProperty("log4j2.isThreadContextMapInheritable", "true");
String renameCsvFile = new String( inputDir.getName() + StaticUtils.SEPARATOR +"log"+ StaticUtils.SEPARATOR + "rename");
ThreadContext.put("module3", renameCsvFile);
rename_logger = LogManager.getLogger("myrenamelog");
rename_logger.info("rename logging", "Timestamp","Level", "OrignalPath","RenamedPath","Status", "Message", "Layer#", "Thread#");
rename_logger.info("rename logging...", Instant.now(),"info",file.getAbsolutePath(),newName.getAbsolutePath(),"success"," ","Layer#",Thread.currentThread().getName());
I would suggest you upgrade to the latest release. Specifically, LOG4J2-2644, which was addressed in Log4j 2.12.1, should impact some of your performance times. However, as in LOG4J2-2792, some applications that rely heavily on filters might need to disable eagerly obtaining the location.
If after testing with a newer version you still have problems please create a Jira issue with Log4j. Ideally you should either provide a sample test suite to demonstrate the problem and/or a snapshot created with a profiling tool such as YourKit that can help identify the problem areas.

How can we disable the hibernate logs?

I am working on Hibernate project, But I have to write the logs into a file then both will combined(Hibernate log added in file) How can we disable the hibernate logs.
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-core</artifactId>
<version>2.11.1</version>
</dependency>
Here are two approaches:
Setting the logging level to NONE should turn off all logging.
Since Hibernate uses the slf4j facade, you should be able to use the NOPLogger; see Get a dummy slf4j logger?.
Replace the log4j-core dependency with this:
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-nop</artifactId>
<version>1.7.30</version>
</dependency>
I've used this but its not working for me:
java.util.logging.Logger.getLogger("org.hibernate")
.setLevel(java.util.logging.Level.OFF);
Yea, that won't work. According the the dependency in your question, you have selected the log4j as the backend. The code snippet above is configuring the java.util.logging logger ...
Look at the javadocs for the log4j classes.
This worked for me..
static {
// Initialized log4j2 Property and disable hibernate log
Configurator.initialize("LOGS", "Projects/log4j.properties");
Configurator.setLevel("org.hibernate", org.apache.logging.log4j.Level.OFF);
}

Adding a Log4j logging to a Vaadin 8 application

I've tried to follow a documentation here Piping to Log4j using SLF4J, but still can't get a correct adapter used. So, how could one use aLog4j in Vaadin 8 application? What are the dependencies to be added to pom.xml?
There are multiple additions/changes required to get logging working.
Along the dependencies mentioned in the documentation to be added:
SLF4J
jul-to-slf4j
slf4j-log4j12-x.x.x.j
A log4j-core should be added as well. The relevant snippet of pom.xml looks like this:
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-core</artifactId>
<version>2.8.1</version>
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-log4j12</artifactId>
<version>1.7.29</version>
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>jul-to-slf4j</artifactId>
<version>1.7.29</version>
</dependency>
The next step is to add a log4j.properties file (in my case under src/main/resources/log4j.properties). Here you can configure your logging properties
As mentioned in the documentation, a SLF4JBridgeHandler should be added to a Servlet definition (in case, there is only one servlet)
#WebServlet(urlPatterns = "/*", name = "MyUIServlet", asyncSupported = true)
#VaadinServletConfiguration(ui = MyUI.class, productionMode = false)
public static class MyUIServlet extends VaadinServlet {
static {
SLF4JBridgeHandler.install();
}
}
Imports used for Logger and LoggerFactory are:
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.slf4j.bridge.SLF4JBridgeHandler;
To verify a correct implementation is picked for a logger its simple name is printed System.out.println("Adapter name:" + logger.getClass().getSimpleName());. Output should be : Log4jLoggerAdapter
Note: I've used a log4-core less than 2.9 since I am using Java 8 and jetty Error scanning entry .... You should upgrade to a newer version if your jre is > 8

Difference between slf4j-log4j12 vs log4j

In a project's pom.xml I am seeing a dependency like below
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>1.7.5</version>
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-log4j12</artifactId>
<version>1.7.5</version>
</dependency>
<dependency>
<groupId>log4j</groupId>
<artifactId>log4j</artifactId>
<version>1.2.17</version>
</dependency>
Can someone let me know what is the difference between slf4j-log4j12 & log4j ?
Log4j 1.2
slf4j-log4j12 provides a bridge between SLF4J and Log4j 1.2 so that SLF4J knows about how to log using Log4j.
You are using Log4j 1.2. That version's binding it is maintained by the SLF4J project. Here is a summary from the SLF4J docs:
SLF4J supports various logging frameworks. The SLF4J distribution ships with several jar files referred to as "SLF4J bindings", with each binding corresponding to a supported framework.
slf4j-log4j12-1.7.28.jar
Binding for log4j version 1.2, a widely used logging framework. You also need to place log4j.jar on your class path.
Log4j 2
If you are using Log4j 2 or later, you will need a different binding JAR than slf4j-log4j12. That binding is maintained by the Log4j project. According to the Log4j docs:
The Log4j 2 SLF4J Binding allows applications coded to the SLF4J API to use Log4j 2 as the implementation.
You must provide both dependencies if you want SLF4J to route logging to Log4j. Again, from the Log4j 2 docs:
Simply include the Log4j 2 SLF4J Binding jar along with the Log4j 2 jars and SLF4J API jar to cause all SLF4J logging to be handled by Log4j 2.
To summarize:
<dependency> <!--Facade for logging systems-->
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>1.7.25</version>
</dependency>
<dependency> <!--Log4j 2 implementation for slf4j-->
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-slf4j-impl</artifactId>
<version>2.12.0</version>
</dependency>
In addition make sure that you are using a log4j2 properties file. The mistake of using 'log4j.xml' did cost me quite some time
I'll post some points regarding these logger message.
log4j:
logger.debug("This is log message:" + msg);
log4j string is concatenated every time the line is evaluated even if log level is lower than debug so the string will never be used.
slf4j:
logger.debug("this is log slf4j message",msg);
slf4j string and parameters are passed through to the logger which only substitutes them if the log message is actually to be used.
The only difference is the performance. Where log4j will take more time because of string concatenation compare to slf4j.
Slf4j:
An abstract layer for the logging component.
We can change logging at point of time without much changes in code.
Log4j:
A logging component which provides core functionalities of logging.

Not able to use #Inject in eclipse 4

I am trying to use dependency injection in my eclipse project. I included maven dependency for org.eclipse.e4.core.di in my dependency management pom.
<dependency>
<groupId>org.eclipse.e4</groupId>
<artifactId>org.eclipse.e4.core.di</artifactId>
<version>1.5.0-SDK-4.5.0</version>
</dependency>
And also, in the plugin where I am using dependency injection with compile scope.
<dependency>
<groupId>org.eclipse.e4</groupId>
<artifactId>org.eclipse.e4.core.di</artifactId>
<version>compile</version>
</dependency>
After this, when I try to use the annotation #Inject, I am seeing error and I am not able to see any import suggestion also.
I have tried including the following in the pom also
<dependency>
<groupId>javax.annotation</groupId>
<artifactId>javax.annotation-api</artifactId>
<version>1.2</version>
</dependency>
What is causing this problem? I am using Java 8.
To use #Inject you must include javax.inject in the Require-Bundle or Import-Package entries in the MANIFEST.MF of your plug-in.
To do this in the MANIFEST.MF editor go to the Dependencies tab and add javax.inject to the Required Plug-ins or Imported Packages section.
When you have done this you should be able to use
import javax.inject.Inject;
in your code.
Note: Only classes created from entries in the e4 Application.e4xmi are injected unless you use ContextInjectionFactory to create the class.

Categories

Resources