Logger类:
1记录特定系统或应用程序组件的日志消息,一般使用圆点分隔的层次名称来命名Logger。和包的命名类似。
2.每个logger都有一个与其相关的“level”,如果他的logger级别为空,则他的有效级别继承自父logger。
3.可以通过配置文件来配置日志级别,也可以通过Logger.setLevel方法动态修改,但是它的变化会影响其子logger的变化。
4.在每次日志记录调用时,他都会按照自己的有效日志级别来对请求级别进行检查,如果低于日志级别则返回日志记录调用。
5.在经过初始化后,Logger将会分配一个LogRecord来描述日志记录消息,在接着调用Filter进行详细的检查,如果检查通过则发布到输出Handler。
6.每个Logger都有一个与其相关联的ResourceBundle名称,该指定用于本地化日志消息。
LogManager类:
存在一个全局的LogManager对象,用于维护Logger和日志服务的一组共享状态。
1管理Logger对象的层次结构名称空间,所有指定的Logger都存储在此命名空间中。
2 管理一组日志控制属性,这些事供Handler及其他日志对象用于自我配置的简单键值对。
注意:
1 LogManager对象是在类初始化是创建,过后就不可更改了。
2在默认情况下,LogManager会从JRE目录属性文件lib/logging.properties中获取最初的配置信息。
3在LogManager配置期间加载的所有类,他们的搜索顺序是先从系统路劲中搜索,在从用户类中搜索。
4 初始化的整个过程
static
{
AccessController.doPrivileged(new PrivilegedAction<Object>() {
public Object run()
{
String cname = null;
try
{
cname = System.getProperty("java.util.logging.manager");
if (cname != null)
{
try
{
Class clz = ClassLoader.getSystemClassLoader().loadClass(cname);
manager = (LogManager) clz.newInstance();
}
catch (ClassNotFoundException ex)
{
Class clz = Thread.currentThread().getContextClassLoader().loadClass(cname);
manager = (LogManager) clz.newInstance();
}
}
}
catch (Exception ex)
{
System.err.println("Could not load Logmanager \"" + cname + "\"");
ex.printStackTrace();
}
if (manager == null)
{
manager = new LogManager();
}
manager.rootLogger = manager.new RootLogger();
manager.addLogger(manager.rootLogger);
manager.systemContext.addLocalLogger(manager.rootLogger);
Logger.global.setLogManager(manager);
manager.addLogger(Logger.global);
return null;
}
});
}
LogRecord类:
重点要理解下面三个类属性:
private static long globalSequenceNumber;
private static int nextThreadId = 10;
private static ThreadLocal threadIds = new ThreadLocal();
public LogRecord(Level level, String msg)
{
level.getClass();
this.level = level;
message = msg;
synchronized (LogRecord.class)
{
sequenceNumber = globalSequenceNumber++;
Integer id = (Integer) threadIds.get();
if (id == null)
{
id = new Integer(nextThreadId++);
threadIds.set(id);
}
threadID = id.intValue();
}
millis = System.currentTimeMillis();
needToInferCaller = true;
}
与 logger 的关系如下,以 info 方法为例:
public void info(String msg)
{
if (Level.INFO.intValue() < levelValue)
{
return;
}
log(Level.INFO, msg);
}
public void log(Level level, String msg)
{
if (level.intValue() < levelValue || levelValue == offValue)
{
return;
}
LogRecord lr = new LogRecord(level, msg);
doLog(lr);
}
转载自: http://www.strutshome.com/index.php/archives/577