“JUL 执行原理和流程”的版本间的差异
跳到导航
跳到搜索
Jihongchang(讨论 | 贡献) (→调试跟踪) |
Jihongchang(讨论 | 贡献) (→调试跟踪) |
||
第17行: | 第17行: | ||
=== 调试跟踪 === | === 调试跟踪 === | ||
{| class="wikitable" | {| class="wikitable" | ||
− | | colspan=" | + | | colspan="4" |class JULTest<syntaxhighlight lang="java"> |
Logger logger = Logger.getLogger("io.github.jihch"); | Logger logger = Logger.getLogger("io.github.jihch"); | ||
</syntaxhighlight> | </syntaxhighlight> | ||
|- | |- | ||
− | | colspan=" | + | | colspan="4" |class java.util.logging.Logger<syntaxhighlight lang="java"> |
@CallerSensitive | @CallerSensitive | ||
public static Logger getLogger(String name) { | public static Logger getLogger(String name) { | ||
第28行: | 第28行: | ||
</syntaxhighlight> | </syntaxhighlight> | ||
|- | |- | ||
− | | colspan=" | + | | colspan="4" |class java.util.logging.Logger<syntaxhighlight lang="java"> |
private static Logger demandLogger(String name, String resourceBundleName, Class<?> caller) { | private static Logger demandLogger(String name, String resourceBundleName, Class<?> caller) { | ||
LogManager manager = LogManager.getLogManager(); | LogManager manager = LogManager.getLogManager(); | ||
第49行: | 第49行: | ||
} | } | ||
</syntaxhighlight> | </syntaxhighlight> | ||
+ | | | ||
|class java.util.logging.LogManager | |class java.util.logging.LogManager | ||
|- | |- | ||
第96行: | 第97行: | ||
} | } | ||
</syntaxhighlight> | </syntaxhighlight> | ||
+ | | | ||
!manager.demandLogger(name, resourceBundleName, caller); | !manager.demandLogger(name, resourceBundleName, caller); | ||
|- | |- | ||
第134行: | 第136行: | ||
super("", null, null, LogManager.this, true); | super("", null, null, LogManager.this, true); | ||
} | } | ||
+ | </syntaxhighlight> | ||
+ | |class java.util.logging.LogManager<syntaxhighlight lang="java"> | ||
+ | public boolean addLogger(Logger logger) { | ||
+ | final String name = logger.getName(); | ||
+ | if (name == null) { | ||
+ | throw new NullPointerException(); | ||
+ | } | ||
+ | drainLoggerRefQueueBounded(); | ||
+ | LoggerContext cx = getUserContext(); | ||
+ | if (cx.addLocalLogger(logger)) { | ||
+ | // Do we have a per logger handler too? | ||
+ | // Note: this will add a 200ms penalty | ||
+ | loadLoggerHandlers(logger, name, name + ".handlers"); | ||
+ | return true; | ||
+ | } else { | ||
+ | return false; | ||
+ | } | ||
+ | } | ||
</syntaxhighlight> | </syntaxhighlight> | ||
! | ! | ||
第147行: | 第167行: | ||
} | } | ||
</syntaxhighlight> | </syntaxhighlight> | ||
+ | | | ||
! | ! | ||
|- | |- | ||
+ | | | ||
| | | | ||
| | | | ||
! | ! | ||
|} | |} |
2023年2月23日 (四) 09:05的版本
https://www.bilibili.com/video/BV1iJ411H74S?p=10
日志原理解析
- 初始化 LogManager
- Log Manager 加载 logging.properties 配置
- 添加 Logger 到 logManager
- 从单例 LogManager 获取 Logger
- 设置级别 Level,并指定日志记录 LogRecord
- Filter 提供了日志级别之外更细粒度的控制
- Handler 处理日志输出位置
- Formatter 用来格式化 LogRecord
调试跟踪
class JULTestLogger logger = Logger.getLogger("io.github.jihch");
| |||
class java.util.logging.Logger @CallerSensitive
public static Logger getLogger(String name) {
return demandLogger(name, null, Reflection.getCallerClass());
}
| |||
class java.util.logging.Logger private static Logger demandLogger(String name, String resourceBundleName, Class<?> caller) {
LogManager manager = LogManager.getLogManager();
SecurityManager sm = System.getSecurityManager();
if (sm != null && !SystemLoggerHelper.disableCallerCheck) {
if (caller.getClassLoader() == null) {
return manager.demandSystemLogger(name, resourceBundleName);
}
}
return manager.demandLogger(name, resourceBundleName, caller);
}
| |||
class java.util.logging.LogManager public static LogManager getLogManager() {
if (manager != null) {
manager.ensureLogManagerInitialized();
}
return manager;
}
|
class java.util.logging.LogManager | ||
class java.util.logging.LogManager final void ensureLogManagerInitialized() {
final LogManager owner = this;
if (initializationDone || owner != manager) {
return;
}
synchronized(this) {
final boolean isRecursiveInitialization = (initializedCalled == true);
assert initializedCalled || !initializationDone
: "Initialization can't be done if initialized has not been called!";
if (isRecursiveInitialization || initializationDone) {
return;
}
initializedCalled = true;
try {
AccessController.doPrivileged(new PrivilegedAction<Object>() {
@Override
public Object run() {
assert rootLogger == null;
assert initializedCalled && !initializationDone;
// Read configuration.
owner.readPrimordialConfiguration();
// Create and retain Logger for the root of the namespace.
owner.rootLogger = owner.new RootLogger();
owner.addLogger(owner.rootLogger);
if (!owner.rootLogger.isLevelInitialized()) {
owner.rootLogger.setLevel(defaultLevel);
}
@SuppressWarnings("deprecation")
final Logger global = Logger.global;
owner.addLogger(global);
return null;
}
});
} finally {
initializationDone = true;
}
}
}
|
manager.demandLogger(name, resourceBundleName, caller); | ||
---|---|---|---|
class java.util.logging.LogManager private void readPrimordialConfiguration() {
if (!readPrimordialConfiguration) {
synchronized (this) {
if (!readPrimordialConfiguration) {
if (System.out == null) {
return;
}
readPrimordialConfiguration = true;
try {
AccessController.doPrivileged(new PrivilegedExceptionAction<Void>() {
@Override
public Void run() throws Exception {
readConfiguration();
// Platform loggers begin to delegate to java.util.logging.Logger
sun.util.logging.PlatformLogger.redirectPlatformLoggers();
return null;
}
});
} catch (Exception ex) {
assert false : "Exception raised while reading logging configuration: " + ex;
}
}
}
}
}
|
class java.util.logging.LogManager.RootLogger extends Logger private RootLogger() {
// We do not call the protected Logger two args constructor here,
// to avoid calling LogManager.getLogManager() from within the
// RootLogger constructor.
super("", null, null, LogManager.this, true);
}
|
class java.util.logging.LogManager public boolean addLogger(Logger logger) {
final String name = logger.getName();
if (name == null) {
throw new NullPointerException();
}
drainLoggerRefQueueBounded();
LoggerContext cx = getUserContext();
if (cx.addLocalLogger(logger)) {
// Do we have a per logger handler too?
// Note: this will add a 200ms penalty
loadLoggerHandlers(logger, name, name + ".handlers");
return true;
} else {
return false;
}
}
|
|
class java.util.logging.Logger Logger(String name, String resourceBundleName, Class<?> caller, LogManager manager, boolean isSystemLogger) {
this.manager = manager;
this.isSystemLogger = isSystemLogger;
setupResourceInfo(resourceBundleName, caller);
this.name = name;
levelValue = Level.INFO.intValue();
}
|
|||