Java 如何从我的类中以字符串形式获取引用类记录器消息
我创建了一个名为“a”的类,它有其引用类“B”。我希望使用控制台appender以字符串形式获取所有记录器消息,包括引用类“B”。注意-B类作为第三方类,无法更新 例如:Java 如何从我的类中以字符串形式获取引用类记录器消息,java,logging,Java,Logging,我创建了一个名为“a”的类,它有其引用类“B”。我希望使用控制台appender以字符串形式获取所有记录器消息,包括引用类“B”。注意-B类作为第三方类,无法更新 例如: A类{ 公共静态void main(字符串[]args){ final java.util.logging.Logger Logger=java.util.logging.Logger.getLogger(A.getClassName()); logger.setLevel(level); ConsoleHandler han
A类{
公共静态void main(字符串[]args){
final java.util.logging.Logger Logger=java.util.logging.Logger.getLogger(A.getClassName());
logger.setLevel(level);
ConsoleHandler handler=新的ConsoleHandler();
handler.setLevel(Level.ALL);
setFormatter(新的SimpleFormatter(){
@重写公共字符串格式(日志记录){
返回“Test--”+record.getMessage();
}
});
addHandler(handler);
发射();
}
公共静态无效启动(){
B s=新的B();
s、 getData();
logger.info(“日志”);
}
}
B类{
final java.util.logging.Logger Logger=java.util.logging.Logger.getLogger(A.getClassName());
getData(){
logger.info(“B log”);
}
}
电流输出:
B log
Test---A log
预期产出:
Test---B log
Test---A log
使用反射可以修改其行为:
import java.lang.reflect.Field;
import java.util.logging.ConsoleHandler;
import java.util.logging.Level;
import java.util.logging.LogRecord;
import java.util.logging.Logger;
import java.util.logging.SimpleFormatter;
public class A {
final static java.util.logging.Logger logger = Logger.getLogger(A.class.getName());
public static void logFormater() {
ConsoleHandler handler = new ConsoleHandler();
handler.setLevel(Level.ALL);
handler.setFormatter(new SimpleFormatter() {
@Override
public String format(LogRecord record) {
return "Test---" + record.getMessage();
}
});
logger.addHandler(handler);
}
public static void main(String[] args) {
logFormater();
launch();
}
public static void launch() {
try {
B bClass= new B();
//using reflection get logger field of B class
Field aField= bClass.getClass().getDeclaredField("logger");
aField.setAccessible(true);
//inject new behavior here
aField.set(bClass, logger);
bClass.getData();
logger.info("A log");
} catch (Exception ex) {
//error msg
}
}
}
class B {
final java.util.logging.Logger logger = Logger.getLogger(B.class.getName());
void getData() {
logger.info("B log");
}
}
控制台输出:
Test---B logFeb 21, 2021 9:40:54 PM com.kawser.stackoverflow.problem.solution.B getData
INFO: B log
Test---A logFeb 21, 2021 9:40:54 PM com.kawser.stackoverflow.problem.solution.A launch
INFO: A log
使用反射可以修改其行为:
import java.lang.reflect.Field;
import java.util.logging.ConsoleHandler;
import java.util.logging.Level;
import java.util.logging.LogRecord;
import java.util.logging.Logger;
import java.util.logging.SimpleFormatter;
public class A {
final static java.util.logging.Logger logger = Logger.getLogger(A.class.getName());
public static void logFormater() {
ConsoleHandler handler = new ConsoleHandler();
handler.setLevel(Level.ALL);
handler.setFormatter(new SimpleFormatter() {
@Override
public String format(LogRecord record) {
return "Test---" + record.getMessage();
}
});
logger.addHandler(handler);
}
public static void main(String[] args) {
logFormater();
launch();
}
public static void launch() {
try {
B bClass= new B();
//using reflection get logger field of B class
Field aField= bClass.getClass().getDeclaredField("logger");
aField.setAccessible(true);
//inject new behavior here
aField.set(bClass, logger);
bClass.getData();
logger.info("A log");
} catch (Exception ex) {
//error msg
}
}
}
class B {
final java.util.logging.Logger logger = Logger.getLogger(B.class.getName());
void getData() {
logger.info("B log");
}
}
控制台输出:
Test---B logFeb 21, 2021 9:40:54 PM com.kawser.stackoverflow.problem.solution.B getData
INFO: B log
Test---A logFeb 21, 2021 9:40:54 PM com.kawser.stackoverflow.problem.solution.A launch
INFO: A log
从根记录器中删除所有处理程序,并将consolehander连接到根记录器。 默认情况下,所有日志消息都会传递到根记录器处理程序
A类{
私有静态final java.util.logging.Logger root=java.util.logging.Logger.getLogger(“”);
私有静态final java.util.logging.Logger Logger=java.util.logging.Logger.getLogger(A.class.getName());
公共静态void main(字符串[]args){
LogManager.getManager().reset();
logger.setLevel(level);
ConsoleHandler handler=新的ConsoleHandler();
handler.setLevel(Level.ALL);
setFormatter(新的SimpleFormatter(){
@重写公共字符串格式(日志记录){
返回“测试----”+格式消息(记录);
}
});
addHandler(handler);
发射();
}
公共静态无效启动(){
B s=新的B();
s、 getData();
logger.info(“日志”);
}
}
B类{
final java.util.logging.Logger Logger=java.util.logging.Logger.getLogger(B.class.getName());
getData(){
logger.info(“B log”);
}
}
从根记录器中删除所有处理程序,并将consolehander连接到根记录器。
默认情况下,所有日志消息都会传递到根记录器处理程序
A类{
私有静态final java.util.logging.Logger root=java.util.logging.Logger.getLogger(“”);
私有静态final java.util.logging.Logger Logger=java.util.logging.Logger.getLogger(A.class.getName());
公共静态void main(字符串[]args){
LogManager.getManager().reset();
logger.setLevel(level);
ConsoleHandler handler=新的ConsoleHandler();
handler.setLevel(Level.ALL);
setFormatter(新的SimpleFormatter(){
@重写公共字符串格式(日志记录){
返回“测试----”+格式消息(记录);
}
});
addHandler(handler);
发射();
}
公共静态无效启动(){
B s=新的B();
s、 getData();
logger.info(“日志”);
}
}
B类{
final java.util.logging.Logger Logger=java.util.logging.Logger.getLogger(B.class.getName());
getData(){
logger.info(“B log”);
}
}
谢谢您提供详细信息。我不确定他们在B类中可能使用的字段是什么,因为它是第三方类,我得到了以下错误:java.lang.NoSuchFieldException:logger。即使我尝试使用反射获取所有字段,它也会返回空数组。如果您不介意,可以共享您的库/第三方类。我会设法解决这个问题。org.mule.services mule service weave 2.3.0 mule service。Logger类是“2021年2月21日11:16:13 AM org.mule.weave.v2.model.service.DefaultLoggingService$logInfo”谢谢,让我检查一下。Logger被定为最终版本正是因为库作者不想允许用户更改它。通过反射覆盖这一点会破坏封装和Java保证。作者可以在任何时候更改B.logger,它将破坏您的程序。一定要考虑到这个风险。谢谢你提供的详细信息。我不确定他们在B类中可能使用的字段是什么,因为它是第三方类,我得到了以下错误:java.lang.NoSuchFieldException:logger。即使我尝试使用反射获取所有字段,它也会返回空数组。如果您不介意,可以共享您的库/第三方类。我会设法解决这个问题。org.mule.services mule service weave 2.3.0 mule service。Logger类是“2021年2月21日11:16:13 AM org.mule.weave.v2.model.service.DefaultLoggingService$logInfo”谢谢,让我检查一下。Logger被定为最终版本正是因为库作者不想允许用户更改它。通过反射覆盖这一点会破坏封装和Java保证。作者可以在任何时候更改B.logger,它将破坏您的程序。一定要考虑到这个风险。谢谢,它起作用了。我能够得到的记录器,因为它的工作。我能够以字符串形式获取记录器