用Java登录怎么办?[关闭]


117

为什么一个将使用以下软件包之一而不是另一个?

  • Java记录
  • 共用记录
  • Log4j
  • SLF4j
  • 退回

4
您可能想要stackoverflow.com/questions/873051,它将SLF4j与Commons Logging进行比较。
James McMahon

24
为什么Ceki创建了3个日志记录框架!多数民众赞成在疯狂...
议员。

6
@mP。-首先是log4j,然后出现了分歧,并编写了slf4j + logback。slf4j是该API并重新登录该API的实现。不管其他一切,slf4j都非常有用。
托尔比约恩Ravn的安德森

3
有关为何CekiGülcü确实创建SLF4J + Logback的详细信息,请参见以下Devoxx演讲:parleys.com/#st=5&id=1701
bitek 2012年

最好的选择是slf4j API,希望它将统一日志记录世界。我认为,logback尚未达到开发人员的要求。
托尔比约恩Ravn的安徒生

Answers:


86

按照api出现的时间顺序(据我所知):

  • Log4j,因为大多数人都使用它(以我的经验)
  • Commons Logging,因为开源项目使用它(因此它们可以与集成解决方案中使用的任何日志记录框架集成);如果您使用的是API / Framework / OSS,并且依赖于使用Commons Logging的其他软件包,则特别有效。
  • Commons Logging是因为您不想“锁定”到特定的日志记录框架(因此,您只能锁定Commons Logging为您提供的功能)-我认为决定使用这一点作为理由并不明智。
  • Java日志记录,因为您不想添加额外的jar。
  • SLF4j,因为它比Commons Logging更新并且提供了参数化日志记录:

logger.debug("The entry is {}.", entry);
//which expands effectively to
if (logger.isDebugEnabled()){
    // Note that it's actually *more* efficient than this - see Huxi's comment below...
    logger.debug("The entry is " + entry + "."); 
}
  • Logback,因为它比log4j更新,并且再次支持参数化日志记录,因为它直接实现SLF4j
  • SLF4j / Logback,因为它是由做log4j的同一个人编写的,所以他做得更好(根据Ken G-谢谢。在查看他们早期的新闻时,它似乎很合适)
  • SLF4j,因为它们还发布了log4j适配器,因此您不必在旧代码中“切换” log4j-只需使log4j.properties使用SLF4j及其配置即可

3
据我所知,公共记录背后的想法是应该在库中使用它。这样,库可以始终使用托管应用程序使用的相同日志记录框架(通过Commons日志记录)。
约阿希姆·绍尔

感谢Loki提出这个问题。我现在知道我将不再使用log4j作为默认框架。SLF4j FTW!也感谢Ken G指出SLF4j与log4j是由同一个人编写的
Stephen

3
您的代码示例中的注释不是100%正确。消息的实际格式设置由Logback延迟执行,因此只有在事件由附加程序真正处理附加程序要求已格式化的消息时才会发生-在例如SocketAppender的情况下不会发生,因为该事件使用不变的消息模式+参数为字符串。我想这只是取决于您如何定义“有效”。它肯定会发出相同的消息(至少如果入口和对象相同;),所以请原谅我的挑剔。
湖西

6
SLF4J实际上只是位于其他日志记录框架之上的API。与Commons Logging的目标相似,但从我的经验来看更为直观。
James McMahon

36

我发现用Java登录会造成混乱,前后不一致,文档记录不清,尤其是偶然。此外,这些日志记录框架之间存在大量相似之处,从而导致工作重复,并且使您对实际使用的日志记录环境感到困惑。特别是,如果您在认真的Java Web应用程序堆栈中工作,则通常一次记录环境;(例如,休眠可能使用log4j和tomcat java.util.logging)。Apache Commons旨在桥接不同的日志记录框架,但实际上只会增加更多的复杂性。如果您不提前知道这一点,那将非常令人困惑。为什么我的日志消息没有打印到控制台等?哦,因为我正在查看Tomcat日志,而不是log4j。增加了另一层复杂性,应用程序服务器可能具有全局日志记录配置,这些配置可能无法识别特定Web应用程序的本地配置。最后,所有这些日志记录框架都太复杂了。登录Java混乱无序,使像我这样的开发人员感到沮丧和困惑。

Java的早期版本没有导致这种情况的内置日志记录框架。


19
这是答案吗?它看起来更像是在咆哮。
迈克尔·迈尔斯

15
对不起。这胡说八道的一点点。但这也是对“用Java记录怎么办?”的有力回应。简而言之,答案是它被深深地打断了。
朱利安·查斯顿

1
好吧,这不值得-1票; P但是值得深思。
guyumu

21
当Sun实际上将java.util.logging添加到Java 1.4时,问题就开始了。在此之前,LOG4J已经建立并广泛使用。之后,包装器必须同时支持LOG4J和java.util.logging。另外,由于jul包含在java。*包中,因此无法通过交换JAR来替换-这是SLF4J桥接其他框架的方式。这可能是有史以来最糟糕的Sun想法……最终导致错误的假设,即“良好的Java公民”应该使用jul。
湖西

4
@Huxi,我认为Calendar API较差。捍卫Sun的不是他们的代码,而是来自Taglient。
托尔比约恩Ravn的安徒生

22

有一个之前没有提到的重要点:

SLF4J(以及Logback和LOG4J作为日志记录后端)都支持所谓的“映射诊断上下文”(MDC,请参阅javadoc文档)。

本质上,这是线程本地的Map <String,String>,可用于将其他上下文信息添加到日志事件。MDC的当前状态附加到每个事件。

如果将诸如用户名和请求的URL之类的东西(如果是webapp)放入其中,这将非常有用。例如,可以使用过滤器自动完成此操作。


2
从技术上讲,它是线程局部Map <String,String>。
pdxleif 2012年


4

在我们的公司项目中,我们使用LOG4j,并且使用非常简单,就像Stephen在他的示例中所示。我们还为LOG4j编写了自己的模式类,因此您可以创建自己的输出文件模式。您可以描述您的日志文件的外观。可以增强原始的log4j类。

您可以在log4j.properties文件中更改所有LOG4j属性,因此可以将不同的文件用于不同的项目。

Java日志记录不是我的最爱,但这可能是因为我从一开始就使用log4j。


4

共享日志记录概述给出了其存在的理由:从库中的代码记录,当你拥有了潜在的日志框架没有控制权。对于将链接到外部应用程序的各种Apache项目非常重要。对于您拥有完全控制权的内部IT项目,可能并不那么重要。

就是说,我写了Commons Logging,就像我认识的许多其他开发人员一样。原因是最大程度地减少了心理负担:您可以更改项目或职位,而不必学习新的框架(前提是新的职位/项目也使用CL,并且/或者您可以说服他们继续使用)。

同样,围绕使用的任何框架创建自己的包装器也有一些价值。如上所述这里,我喜欢用LogWrapper目的是提供自定义的字串(重要),并最大限度地减少日志报表(不那么重要)的视觉混乱。


1
还有一个commons.logging => SLF4J网桥,可用于通过SLF4J路由所有CL日志记录。SLF4J支持桥接commons.logging,LOG4J和java.util.logging(有点麻烦,但要尽可能好),因此所有日志最终都将存储在您将使用的SLF4J后端中。请参阅slf4j.org/legacy.html。我会使用Logback,顺便说一句,但您可能会说我有偏见。
湖西

2

通常,我会默认使用Log4J。

如果我不介意对Java 1.4的依赖,我将使用Java Logging,但是我仍然会优先使用Log4J。

如果要增强已经使用的功能,我将使用Commons Logging。


介意不依赖1.4吗?甚至1.4都已经达到使用寿命。
Tom Hawtin-大头针

2
@Tom他的意思是jdk1.4 +不要傻。
mP。

实际上,我最近在一个仍在jdk 1.3下运行的系统中完成了一些工作:-(,而且不到两年前,我最后一次维护jdk 1.2系统。除非有绝对的地方,否则很多地方都不会升级,他们只是拒绝安装升级
Michael Rutherfurd 2010年

0

我建议创建一个可以写入任何日志记录框架的瘦日志记录外观,这时选择支持引擎几乎是一个有争议的话题。


2
那就是普通伐木的目的,那么为什么要重新发明轮子呢?另外,您的立面还必须解决一些常见的日志记录问题。
James AN Stauffer

+1为了对抗Commons Logging参数,某些企业应用程序使用自定义Logger。隐藏底层实现始终是一个好主意。“薄”包装器无需再包装另一个罐子,并且不像重新发明那样多。
Questzen

1
最近,当我们将框架移植到Compact Framework(在.Net中)时,这为我节省了很多。如果我们对nLog进行了硬编码的依赖关系,那我们就被搞砸了。因为我们使用了这种方法,所以我们能够使用null记录器并感到高兴。有人将我的票数提高到0,请:-)
tsimon

3
一个已经存在-看一下slf4j。这是一个公认的瘦包装器,它允许您通过在运行时类路径上切换jar来在应用程序启动时切换日志记录框架。
威慑

1
阻塞有其自己的方式来发现它将使用的框架-它不是很好,而是很混乱。Ceki创建了多少个日志记录框架。即使您自己的日志记录阻塞了一个实现,也应该始终努力争取一定程度的交互性并隐藏实现。如Travis所述,您可以在幕后插入所需的任何f / w。
mP。
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.