slf4j查看
2015-10-10 10:20
260 查看
###slf4j查看
先从LoggerFactory这个类入手,起始于getLogger方法
getILoggerFactory调用后找寻的是类路中StaticLoggerBinder的实现类。
进入到findPossibleStaticLoggerBinderPathSet方法:
通过classLoader加载的类是org/slf4j/impl/StaticLoggerBinder.class是否在类路径存在。如果有多个会或者0个会提示报错信息。
最后间接使用的loggerFactory是Log4jLoggerFactory
通过getLogger方法得到是log4j jar包里面的org.apache.log4j.Logger log4jLogger
ConcurrentMap会多一个方法putIfAbsent相对于普通map。不存在的时候插入,存在的时候不改变。--相对也是线程安全的。
logger返回时候 还是要包装一下成org.slf4j.Logger接口,方便通用。
举出其中一个的例子,logger.isDebugEnabled代替了以前代码里面很繁琐的判断过程。使用装饰器对log4j的logger进行了加强。还支持message占位符支持。也算是一个不错的优点了。
先从LoggerFactory这个类入手,起始于getLogger方法
public static Logger getLogger(String name) { ILoggerFactory iLoggerFactory = getILoggerFactory(); return iLoggerFactory.getLogger(name); }
getILoggerFactory调用后找寻的是类路中StaticLoggerBinder的实现类。
private final static void bind() { try { Set staticLoggerBinderPathSet = findPossibleStaticLoggerBinderPathSet(); reportMultipleBindingAmbiguity(staticLoggerBinderPathSet); // the next line does the binding StaticLoggerBinder.getSingleton(); INITIALIZATION_STATE = SUCCESSFUL_INITIALIZATION; reportActualBinding(staticLoggerBinderPathSet); emitSubstituteLoggerWarning(); } catch (NoClassDefFoundError ncde) { String msg = ncde.getMessage(); if (messageContainsOrgSlf4jImplStaticLoggerBinder(msg)) { INITIALIZATION_STATE = NOP_FALLBACK_INITIALIZATION; Util.report("Failed to load class \"org.slf4j.impl.StaticLoggerBinder\"."); Util.report("Defaulting to no-operation (NOP) logger implementation"); Util.report("See " + NO_STATICLOGGERBINDER_URL + " for further details."); } else { failedBinding(ncde); throw ncde; } } catch (java.lang.NoSuchMethodError nsme) { String msg = nsme.getMessage(); if (msg != null && msg.indexOf("org.slf4j.impl.StaticLoggerBinder.getSingleton()") != -1) { INITIALIZATION_STATE = FAILED_INITIALIZATION; Util.report("slf4j-api 1.6.x (or later) is incompatible with this binding."); Util.report("Your binding is version 1.5.5 or earlier."); Util.report("Upgrade your binding to version 1.6.x."); } throw nsme; } catch (Exception e) { failedBinding(e); throw new IllegalStateException("Unexpected initialization failure", e); } }
进入到findPossibleStaticLoggerBinderPathSet方法:
private static Set findPossibleStaticLoggerBinderPathSet() { // use Set instead of list in order to deal with bug #138 // LinkedHashSet appropriate here because it preserves insertion order during iteration Set staticLoggerBinderPathSet = new LinkedHashSet(); try { ClassLoader loggerFactoryClassLoader = LoggerFactory.class .getClassLoader(); Enumeration paths; if (loggerFactoryClassLoader == null) { paths = ClassLoader.getSystemResources(STATIC_LOGGER_BINDER_PATH); } else { paths = loggerFactoryClassLoader .getResources(STATIC_LOGGER_BINDER_PATH); } while (paths.hasMoreElements()) { URL path = (URL) paths.nextElement(); staticLoggerBinderPathSet.add(path); } } catch (IOException ioe) { Util.report("Error getting resources from path", ioe); } return staticLoggerBinderPathSet; }
通过classLoader加载的类是org/slf4j/impl/StaticLoggerBinder.class是否在类路径存在。如果有多个会或者0个会提示报错信息。
最后间接使用的loggerFactory是Log4jLoggerFactory
private StaticLoggerBinder() { loggerFactory = new Log4jLoggerFactory(); try { @SuppressWarnings("unused") Level level = Level.TRACE; } catch (NoSuchFieldError nsfe) { Util.report("This version of SLF4J requires log4j version 1.2.12 or later. See also http://www.slf4j.org/codes.html#log4j_version"); } }
通过getLogger方法得到是log4j jar包里面的org.apache.log4j.Logger log4jLogger
public Logger getLogger(String name) { Logger slf4jLogger = loggerMap.get(name); if (slf4jLogger != null) { return slf4jLogger; } else { org.apache.log4j.Logger log4jLogger; if (name.equalsIgnoreCase(Logger.ROOT_LOGGER_NAME)) log4jLogger = LogManager.getRootLogger(); else log4jLogger = LogManager.getLogger(name); Logger newInstance = new Log4jLoggerAdapter(log4jLogger); Logger oldInstance = loggerMap.putIfAbsent(name, newInstance); return oldInstance == null ? newInstance : oldInstance; } }
ConcurrentMap会多一个方法putIfAbsent相对于普通map。不存在的时候插入,存在的时候不改变。--相对也是线程安全的。
logger返回时候 还是要包装一下成org.slf4j.Logger接口,方便通用。
public void debug(String format, Object arg) { if (logger.isDebugEnabled()) { FormattingTuple ft = MessageFormatter.format(format, arg); logger.log(FQCN, Level.DEBUG, ft.getMessage(), ft.getThrowable()); } }
举出其中一个的例子,logger.isDebugEnabled代替了以前代码里面很繁琐的判断过程。使用装饰器对log4j的logger进行了加强。还支持message占位符支持。也算是一个不错的优点了。
相关文章推荐
- Erlang的调度原理
- 使用ngrok让微信公众平台通过80端口访问本机
- quick-cocos2dx3.5 mac模拟器改进
- 热点链接空白时点击崩溃问题
- Android 代码重构
- iOS 9对前端做了什么?
- (论文阅读)2015.10.8图像识别中的深度学习
- Android之发送短信的两种方式
- C语言数据结构-顺序表
- leetcode 6 : ZigZag Conversion
- <iOS>在哪里删除Provisioning Profiles
- 深入理解C++中public、protected及private用法
- Thinkphp子查询问题总结
- locate: can not stat () `/var/lib/mlocate/mlocate.db': No such file or directory
- hibernate学习笔记(1)hibernate基本步骤
- iOS发送信息功能(生成信息内容)
- HttpClient 教程 (六)
- 软件工程之软工文档总结
- MyCAT全局表描述及示例
- ASP.NET RegularExpressionValidator 控件