我正在使用在Tomcat 8.0容器中运行的Liferay 7.0。
在启动期间,我正在为Liferay挂钩注册特定的类。此类必须在Tomcat的系统类路径中。因此.jar文件位于CATALINA_BASE/lib/ext
我需要该类的日志输出,但是我无法弄清楚如何通过Tomcat配置文件正确配置Java的日志。
我对Tomcat的logging.properties
进行了如下修改(粗体字更改)
首先,我定义了一个附加处理程序:
handlers = 1catalina.org.apache.juli.AsyncFileHandler, 2myhandler.org.apache.juli.AsyncFileHandler, java.util.logging.ConsoleHandler .handlers = 1catalina.org.apache.juli.AsyncFileHandler, java.util.logging.ConsoleHandler
The handler is configured as follows:
2myhandler.org.apache.juli.AsyncFileHandler.level = FINE 2myhandler.org.apache.juli.AsyncFileHandler.directory = ${catalina.base}/logs 2myhandler.org.apache.juli.AsyncFileHandler.prefix = my-class. 2myhandler.org.apache.juli.AsyncFileHandler.formatter = java.util.logging.SimpleFormatter 2myhandler.java.util.logging.SimpleFormatter.format=%1$tF %1$tT %4$s [%2$s] %5$s %6$s %n
And the link between the handler and my class is done like this:
com.mypackage.MyClass.level = ALL com.mypackage.MyClass.handlers = 2myhandler.org.apache.juli.AsyncFileHandler com.mypackage.MyClass.useParentHandlers=false
My class uses
private static final LOGGER = Logger.getLogger("com.mypackage.MyClass");
Tomcat启动时,将创建文件
my-hook.log
(文件名中带有时间戳)。但是我的日志消息都没有出现在文件中。
在代码中我有构造函数中的以下内容:
logger.log(Level.INFO, "MyClass initialized");
System.out.println("*** MyClass loaded ***");
启动Liferay时,我可以在控制台窗口中看到
*** MyClass loaded ***
消息,但是日志消息未写入(现有)文件中。我在这里想念什么?
请注意,我无法切换到Log4J(在Liferay Portlet中使用),因为这会在Liferay提供的Log4j和
lib/ext
中的Log4j之间产生类加载器冲突。
最佳答案
因此.jar文件位于CATALINA_BASE / lib / ext中
在安装Tomcat 8时,我可以看到CATALINA_BASE / lib,但没有名为ext的子目录。我想您应该确保common.loader
的系统属性在路径中显示ext。在我的机器上没有扩展路径:
common.loader="${catalina.base}/lib","${catalina.base}/lib/*.jar","${catalina.home}/lib","${catalina.home}/lib/*.jar"
当我启动Liferay时,我可以在控制台窗口中看到* MyClass loading *消息,但是日志消息未写入(现有)文件中。
那么,类加载器便可以找到您的类,并且因为文件存在而创建了处理程序。修改
MyClass
以包括来自DebugLogging的代码。包括辅助函数,并将main方法的主体复制到MyClass构造函数中。这将跟踪记录器树的外观。在答案中包括输出。package com.mypackage;
import java.io.PrintStream;
import java.util.Enumeration;
import java.util.logging.Handler;
import java.util.logging.Level;
import java.util.logging.LogManager;
import java.util.logging.Logger;
public class MyClass {
private static final String CLASS_NAME = MyClass.class.getName();
private static final Logger logger = Logger.getLogger(CLASS_NAME);
public static void main(String[] args) {
new MyClass();
}
public MyClass() {
logger.log(Level.INFO, "MyClass initialized");
System.out.println("*** MyClass loaded ***");
logger.log(Level.FINEST, "Finest");
logger.log(Level.FINER, "FINER");
logger.log(Level.FINE, "FINE");
logger.log(Level.CONFIG, "CONFIG");
logger.log(Level.INFO, "INFO");
logger.log(Level.WARNING, "WARNING");
logger.log(Level.SEVERE, "SEVERE");
logger.finest("Finest Log");
logger.finer("Finer Log");
logger.fine("Fine Log");
logger.config("Config Log");
logger.info("Info Log");
logger.warning("Warning Log");
logger.severe("Severe Log");
printConfig(System.out);
}
private static void printConfig(PrintStream ps) {
LogManager lm = LogManager.getLogManager();
ps.append("LogManager=").append(lm.getClass().getName());
ps.append("@");
printLoader(lm, ps);
ps.println();
synchronized (lm) {
Enumeration<String> e = lm.getLoggerNames();
while (e.hasMoreElements()) {
Logger l = lm.getLogger(e.nextElement());
if (l != null) {
print(l, ps);
}
}
}
}
private static void print(Logger l, PrintStream ps) {
ps.append("scn=").append(l.getClass().getSimpleName());
ps.append("@");
printLoader(l, ps);
ps.append(", n=").append(String.valueOf(l.getName()));
ps.append(", uph=").append(String.valueOf(l.getUseParentHandlers()));
ps.append(", l=").append(String.valueOf(l.getLevel()));
ps.append(", fl=").println(String.valueOf(l.getFilter()));
for (Handler h : l.getHandlers()) {
ps.append("\t").append(l.getName()).append("->");
ps.append(h.getClass().getName());
ps.append("@");
printLoader(h, ps);
ps.append(", h=")
.append(String.valueOf(h.getLevel())).append(", fl=")
.append(String.valueOf(h.getFilter())).println();
}
}
private static void printLoader(Object o, PrintStream ps) {
if (o != null) {
Object cl = o.getClass().getClassLoader();
if (cl != null) {
ps.append(cl.getClass().getSimpleName());
} else {
ps.append("null");
}
} else {
ps.append("null");
}
}
}
您的处理程序在handlers中声明。这样就足以使用处理程序。文件的存在表明处理程序已构建。
在我的机器上,调试输出显示处理程序已设置:
scn=Logger@null, n=com.mypackage.MyClass, uph=false, l=ALL, fl=null
com.mypackage.MyClass->org.apache.juli.AsyncFileHandler@AppClassLoader, h=FINE, fl=null
文件日志包含:
2020-02-15 11:48:55 INFO [com.mypackage.MyClass <init>] MyClass initialized
2020-02-15 11:48:55 FINE [com.mypackage.MyClass <init>] FINE
2020-02-15 11:48:55 CONFIG [com.mypackage.MyClass <init>] CONFIG
2020-02-15 11:48:55 INFO [com.mypackage.MyClass <init>] INFO
2020-02-15 11:48:55 WARNING [com.mypackage.MyClass <init>] WARNING
2020-02-15 11:48:55 SEVERE [com.mypackage.MyClass <init>] SEVERE
2020-02-15 11:48:55 FINE [com.mypackage.MyClass <init>] Fine Log
2020-02-15 11:48:55 CONFIG [com.mypackage.MyClass <init>] Config Log
2020-02-15 11:48:55 INFO [com.mypackage.MyClass <init>] Info Log
2020-02-15 11:48:55 WARNING [com.mypackage.MyClass <init>] Warning Log
2020-02-15 11:48:55 SEVERE [com.mypackage.MyClass <init>] Severe Log
根据文档,您可以为Tomcat指定系统属性
org.apache.juli.ClassLoaderLogManager.debug=true
,该属性将配置信息发送到System.err
。这可能会帮助您进一步排除故障。
关于java - 无法让Tomcat的java.util日志记录与特定类一起使用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/60209810/