何时使用不同的日志级别


520

记录消息的方式有多种(按致命程度排序):

  1. FATAL

  2. ERROR

  3. WARN

  4. INFO

  5. DEBUG

  6. TRACE

我该如何决定何时使用哪个?

有什么好的启发式方法?


11
相当广泛的问题。因此,根据记录的实际情况,可能有多个答案。有人会错过notice这个收藏集中的人,而别人却不会……
Wolf

@Wolf将“通知”归入此层次结构的何处?只是为了记录...
pgblu

1
notice可能会丢失,因为某些流行的日志记录服务(例如log4j)不使用它。
pgblu

Answers:


749

我通常同意以下约定:

  • 跟踪 -仅当我要“跟踪”代码并尝试专门查找功能的一部分时。
  • 调试 -对开发人员(IT,系统管理员等)不但对人员有诊断意义的信息。
  • 信息 -通常有用的日志信息(服务启动/停止,配置假设等)。我想一直提供的信息,但通常情况下通常不关心。这是我开箱即用的配置级别。
  • 警告 -可能导致应用程序异常的任何事情,但我会自动对其进行恢复。(例如从主服务器切换到备份服务器,重试操作,丢失辅助数据等)
  • 错误 -对操作致命的任何错误,但对服务或应用程序不是致命的错误(无法打开所需的文件,丢失数据等)。这些错误将迫使用户(管理员或直接用户)进行干预。这些通常是在我的应用程序中保留的,用于不正确的连接字符串,缺少服务等。
  • 致命 -导致关闭服务或应用程序以防止数据丢失(或进一步的数据丢失)的任何错误。我仅将这些保留给最令人发指的错误,以及那些肯定会导致数据损坏或丢失的情况。

2
为什么您不能合并信息并发出警告!并不是关于实际上是“信息”的警告...
mP。

35
@mP您可以合并信息并发出警告,我想通常由于“恐慌”原理它们是分开的。如果我有一堆常规的信息并且只是列出状态,那么它就不值得首先关注“警告”,但是如果有大量的“警告”,那么我想看看这些警告的优先级(在“错误和致命”之后),因此我可以调查一下他们。我将对许多警告而不是许多信息消息感到“惊慌”。
GrayWizardx 2011年

3
@dzieciou,这取决于您的特定需求。有时可能是致命的,有时只是警告。如果我从一项关键服务中获得了4xx,我将无法继续下去,那对我的设计将是一个错误/致命的错误。如果我试图缓存一些数据以备后用,但如果没有它可以生存,那将是一个警告。我唯一看到的是信息,例如监视应用程序正在报告其URL检查的状态。因此,我将在INFO日志中从URL获得4xx并继续前进。
GrayWizardx

2
@GrayWizardx,我认为另一个因素是这是接收4xx的客户端还是发送它的服务器。在第一种情况下,我将更愿意使用ERROR(OMG,这是我的错,我无法准备正确的请求),而在后一种情况下,我会记录WARN(这是客户的错,他们无法正确地提出请求)
dzieciou

4
我怀疑这是真的- Debug - Information that is diagnostically helpful to people more than just developers (IT, sysadmins, etc.).。Logger.Debug仅用于开发人员跟踪生产中的非常棘手的问题,例如If you want to print the value of a variable at any given point inside a for loop against a condition
RBT

303

您是否希望该消息使系统管理员在半夜醒来?

  • 是->错误
  • 否->警告

11
除非大多数人不在乎他们是否让人们在晚上起床。我们已经让客户举起了严重性为1的集群(意味着100%断电,即全国性),因为一个站点无法完成其工作(他们的理由是该站点是该站点的100%)。从那以后,我们就对该分数“进行了教育”。
paxdiablo

53
FATAL是系统管理员醒来时确定自己为此支付的费用不足,然后返回睡眠状态。
Mateen Ulhaq'5

134

我发现从查看日志文件的角度考虑严重性会更有用。

致命/严重:应立即调查整个应用程序或系统故障。是的,唤醒SysAdmin。由于我们更喜欢SysAdmins警报,并且需要充分休息,因此应该很少使用这种严重性。如果它每天都在发生,而且不是BFD,那它就失去了意义。通常,致命错误在流程生命周期中仅发生一次,因此,如果日志文件与流程相关联,则通常是日志中的最后一条消息。

错误:绝对是应该研究的问题。SysAdmin应该会自动得到通知,但无需将其拖出床。通过过滤日志以查看错误以及上面的内容,您可以大致了解错误发生的频率,并可以快速识别可能导致一系列其他错误的初始故障。跟踪错误率与应用程序使用情况的对比,可以得出有用的质量指标,例如MTBF,可以用来评估整体质量。例如,此指标可能有助于在发布之前就是否需要另一个Beta测试周期提供决策依据。

警告:这可能是问题,也可能不是。例如,预期的瞬态环境条件(例如,网络或数据库连接的短暂丢失)应记录为“警告”而不是“错误”。查看经过筛选以仅显示警告和错误的日志,可以快速了解早期提示,以了解后续错误的根本原因。警告应谨慎使用,以免变得毫无意义。例如,失去网络访问权限应该是警告,甚至是服务器应用程序中的错误,但可能仅仅是为偶尔断开连接的笔记本电脑用户设计的台式机应用程序中的信息。

信息:这是重要的信息,在正常情况下(例如成功初始化,服务启动和停止或成功完成重要交易)应记录下来。查看显示“信息”及以上信息的日志,应快速概述过程中的主要状态变化,并提供顶层上下文,以了解也可能发生的任何警告或错误。没有太多的信息消息。与Trace相比,我们通常有<5%的Info消息。

跟踪:跟踪是迄今为止最常用的严重性,应提供上下文以了解导致错误和警告的步骤。具有适当密度的Trace消息可以使软件更加易于维护,但需要进行尽职调查,因为随着程序的发展,各个Trace语句的值可能会随着时间而变化。实现此目标的最佳方法是使开发团队养成定期查看日志的习惯,这是解决客户报告的问题的标准步骤。鼓励团队删除不再提供有用上下文的跟踪消息,并在需要的地方添加消息以了解后续消息的上下文。例如,登录用户输入(例如更改显示或选项卡)通常会很有帮助。

调试:我们考虑调试<跟踪。区别在于Debug消息是从Release版本中编译出来的。也就是说,我们不鼓励使用Debug消息。允许Debug消息往往会导致越来越多的Debug消息被添加,而从未删除。随着时间的流逝,日志文件几乎变得毫无用处,因为很难过滤掉噪声中的信号。这导致开发人员不使用继续死亡螺旋的日志。相反,不断修剪Trace消息会鼓励开发人员使用它们,从而导致良性循环。而且,这消除了由于发行版本中未包含的调试代码中的所需副作用而导致引入错误的可能性。是的,我知道这不应该在良好的代码中发生,但是安全起见,对不起。


2
我喜欢这样强调听众。任何交流(日志消息是交流的一种形式)的关键是要考虑您的听众及其需求。
sleske

18
关于Debug <-> Trace:请注意,至少在Java领域中,优先级顺序为“ debug> trace”。这是我知道使用的所有日志记录框架的约定(SLF4J,Logback,log4j,Apache Commons Logging,Log4Net,NLog)。所以Debug <Trace对我来说似乎很不寻常。
sleske

1
@杰伊·辛科塔(Jay Cincotta)好的答案。我认为Debug / Trace是一个优先选择的问题,但是这些细节肯定是特定于应用程序/公司的,因此很高兴看到不同的意见。
GrayWizardx

5
我刚刚对几种语言的7个日志记录框架进行了调查。在包括“跟踪”严重性级别的三个中,所有这些都具有比调试不那么严重的级别。即trace <debug; 在现实世界中,没有相反的情况。@RBT不一定总能闯入调试器。例如,Web服务器必须在有限的时间内处理请求,或者存在于可能难以检测的多线程和/或服务器环境中,或者该错误可能非常罕见,因此无法选择调试器。或者您不知道要寻找什么。
Thanatos

5
@RBT我已经使用Java系统已有4年以上了。我可以告诉你,你的要求是完全不切实际的。IDE调试只能带您到此为止。在某一时刻,您仅需要来自另一个系统(通常是生产服务器)的调试日志,以了解正在发生的情况并修复该错误。您可能认为它应该可以在本地IDE中重现,但是如果您使用的是真实系统,则会发现许多错误通常是生产服务器所独有的。
ADTC

30

这是“记录器”所具有的清单。


Apache log4j:§1§2

  1. FATAL

    [ v1.2:..]非常严重的错误事件,可能会导致应用程序中止。

    [ v2.0:..]严重错误,将阻止应用程序继续运行。

  2. ERROR

    [ v1.2:..]错误事件,可能仍然允许应用程序继续运行。

    [ v2.0:..]应用程序中的错误,可能是可以恢复的。

  3. WARN

    [ v1.2:..]潜在有害情况。

    [ V2.0:..]事件可能可能[ 原文 ]导致错误。

  4. INFO

    [ v1.2:..]信息性消息,以粗粒度级别突出显示应用程序的进度。

    [ v2.0:..]事件,仅供参考。

  5. DEBUG

    [ v1.2:..]细粒度的信息事件,对于调试应用程序最有用。

    [ v2.0:..]常规调试事件。

  6. TRACE

    [ v1.2:..]的信息事件比的要细DEBUG

    [ v2.0:..]细粒度的调试消息,通常捕获通过应用程序的流。


Apache Httpd(像往常一样)喜欢过度使用:§

  1. 能源

    紧急情况-系统无法使用。

  2. 警告

    必须立即采取措施[但系统仍然可用]。

  3. 暴击

    紧急情况[但不必立即采取措施]。

    • 套接字:无法获取套接字,退出子进程
  4. 错误

    错误条件[但不是关键]。

    • 脚本头过早结束
  5. 警告

    警告条件。[接近错误,但不是错误]

  6. 注意

    正常但明显的[ 显着 ]情况。

    • httpd:被捕获SIGBUS,试图将内核转储到...
  7. 信息

    信息性(且不明显)。

    • [“ 服务器已经运行了x个小时。 ”]
  8. 调试

    调试级消息[,即消息记录为起见去窃听)。

    • “正在打开配置文件...
  9. 轨迹1轨迹6

    跟踪消息[,即为跟踪而记录的消息]。

    • 代理:FTP:控制连接完成
    • 代理:CONNECT:将CONNECT请求发送到远程代理
    • openssl:握手:开始
    • 从缓冲的SSL旅读取,模式0,17个字节
    • 地图查找失败:map=rewritemap key=keyname
    • 缓存查找失败,强制进行新的地图查找
  10. trace7trace8

    跟踪消息,转储大量数据

    • | 0000: 02 23 44 30 13 40 ac 34 df 3d bf 9a 19 49 39 15 |
    • | 0000: 02 23 44 30 13 40 ac 34 df 3d bf 9a 19 49 39 15 |

Apache Commons日志记录:§

  1. 致命的

    导致过早终止的严重错误。希望它们在状态控制台上立即可见。

  2. 错误

    其他运行时错误或意外情况。希望它们在状态控制台上立即可见。

  3. 警告

    使用不推荐使用的API,API使用不当,“几乎”错误,其他运行时情况是不希望的或意外的,但不一定是“错误的”。希望它们在状态控制台上立即可见。

  4. 信息

    有趣的运行时事件(启动/关闭)。希望这些内容在控制台上立即可见,因此请保持保守并尽量减少。

  5. 调试

    有关流经系统的详细信息。期望这些仅写入日志。

  6. 跟踪

    更详细的信息。期望这些仅写入日志。

Apache Commons记录的企业最佳实践“最佳实践” 根据调试信息之间的界限来区分它们。

边界包括:

  • 外部边界-预期的例外。

  • 外部边界-意外的异常。

  • 内部边界。

  • 重要的内部边界。

(有关更多信息,请参见commons-logging指南。)


24

如果您可以从问题中恢复过来,那就是警告。如果它阻止继续执行,那就是错误。


5
但是,错误和致命错误之间有什么区别?
user192472

37
错误是您执行的操作(例如,读取不存在的文件),致命错误是您执行的操作(例如,内存不足)。
伊格纳西奥·巴斯克斯

@ IgnacioVazquez-Abrams我喜欢您的区分方式。但是您的评论基于什么呢?在iOS开发人员中,AFIAK通常编写一个断言,该断言与fatalError文件不存在的时间有关。基本上,这与您所说的相反。
蜂蜜

@Honey:在移动情况下,将丢失的文件视为致命错误是合理的。
伊格纳西奥·巴斯克斯

23

我建议采用Syslog严重级别:DEBUG, INFO, NOTICE, WARNING, ERROR, CRITICAL, ALERT, EMERGENCY
参见http://en.wikipedia.org/wiki/Syslog#Severity_levels

它们应为大多数用例提供足够的细粒度严重性级别,并被现有的日志分析器识别。当然,尽管您可以自由地仅实现子集,例如DEBUG, ERROR, EMERGENCY根据应用程序的要求。

让我们对已经存在了很多年的东西进行标准化,而不是针对我们制作的每个不同应用程序提出自己的标准。一旦您开始汇总日志并尝试检测不同日志之间的模式,它就会真正有用。


1
我需要跟踪日志,因为我想查看代码中的执行情况。syslog如何解决此问题?
莫里森

跟踪通常不是您想要通过syslog传输的东西,我想您可以为自己的交互式调试会话随意添加此级别?
kvz

2
所有这些扩展级别都增加了记录IMO的复杂性。最好坚持最简单的设置来满足特定应用程序的需求。对于我来说,你应该开始DEBUGINFOWARNINGERROR。开发人员应该看到所有级别。直到SysAdmins为止INFO,最终用户都可以看到警告和错误,但前提是有一个框架可以警告他们
ADTC

1
(续)随着应用程序的成熟,如果需要,您可以扩展到更多级别。既喜欢DEBUGTRACE供开发商控制粒度。并ERROR扩大到其他级别一样CRITICALALERTEMERGENCY辨别错误的严重性,并决定根据严重程度的作用。
ADTC

17

您可以从中恢复的警告。错误不能。那是我的启发,其他人可能有其他想法。

例如,假设您将名称输入/导入"Angela Müller"到应用程序中(请注意上的变音符号u)。您的代码/数据库可能仅是英文(尽管现在不应该是英文),因此可能会警告所有“不寻常的”字符都已转换为常规英语字符。

与尝试将信息写入数据库并连续60秒钟返回网络中断消息形成对比。与其说警告,不如说是错误。


如果数据库的某个字符集不包含变音符号,则必须拒绝此输入。
Cochise Ruhulessin

Cochise,世界很少有黑白两色的:-)
paxdiablo 18/12/13

6

正如其他人所说的那样,错误就是问题。警告是潜在的问题。

在开发中,我经常在警告中使用等同于断言失败的警告,但是应用程序可以继续工作。这使我能够确定这种情况是否真的发生了,或者是我的想象。

但是是的,它取决于可恢复性和实际情况。如果可以恢复,可能是警告。如果它导致某事实际失败,那就是错误。


5

我认为SYSLOG级别的NOTICE和ALERT / EMERGENCY在应用程序级别的日志记录中是多余的-CRITICAL / ALERT / EMERGENCY对于可能触发不同操作和通知的操作员而言可能是有用的警报级别,对于应用程序管理员来说,它与致命。我只是无法充分区分是收到通知还是提供一些信息。如果这些信息不值得关注,那不是真正的信息:)

我最喜欢杰伊·辛科塔(Jay Cincotta)的解释-跟踪代码的执行在技术支持中非常有用,应鼓励将跟踪语句自由地放入代码中-尤其是与动态过滤机制结合使用,以记录来自特定应用程序组件的跟踪消息。但是,对我而言,DEBUG级别表明我们仍在弄清发生的情况-我将DEBUG级别的输出视为仅开发选项,而不是应在生产日志中显示的东西。

但是,当我戴着系统管理员的帽子时,我希望在错误日志中看到一个日志记录级别,该级别与技术支持甚至开发人员:OPER一样多,用于操作性消息。我将其用于记录时间戳,调用的操作类型,提供的参数(可能是(唯一)任务标识符)和任务完成。例如,当一个独立的任务被触发时,就使用它,这是从较大的长期运行的应用程序中进行的真正调用。无论是否出错,我都希望始终记录这种情况,因此我认为OPER的级别要高于FATAL,因此只能通过完全静音模式将其关闭。它不仅是INFO日志数据,而且还经常被滥用为垃圾邮件,而这些垃圾邮件带有没有历史价值的次要操作消息,它们经常被滥用。

视情况而定,此信息可以定向到单独的调用日志,也可以通过将其从记录更多信息的大日志中过滤掉而获得。但是,作为历史信息,始终需要知道正在执行的操作-在不降低到AUDIT级别的情况下,与故障或系统操作无关的另一个完全独立的日志级别实际上并不适合上述级别(因为它需要自己的控制开关,而不是严重性分类),并且肯定需要自己的单独日志文件。


5

从RFC 5424开始,系统日志协议(IETF)-第10页:

每个消息优先级还具有十进制严重性级别指示符。下表中描述了它们及其数值。严重性值必须在0到7之间(包括0和7)。

       Numerical         Severity
         Code

          0       Emergency: system is unusable
          1       Alert: action must be taken immediately
          2       Critical: critical conditions
          3       Error: error conditions
          4       Warning: warning conditions
          5       Notice: normal but significant condition
          6       Informational: informational messages
          7       Debug: debug-level messages

          Table 2. Syslog Message Severities

4

G'day,

作为此问题的必然结果,请传达您对日志级别的解释,并确保项目中的所有人员对日志级别的解释保持一致。

看到各种各样的日志消息,其中严重性和所选的日志级别不一致。

如果可能,提供不同日志记录级别的示例。并在要登录的信息中保持一致。

高温超导


4

我完全同意其他人的看法,并认为Gr​​ayWizardx说得最好。

我要补充的是,这些级别通常对应于其字典定义,因此并不难。如有疑问,请将其视为难题。对于您的特定项目,请考虑您可能想要记录的所有内容。

现在,您能找出可能致命的东西吗?你知道致命的意思,不是吗?因此,您列表上的哪些项目是致命的。

好的,这是致命的,现在让我们看看错误……冲洗并重复。

在致命以下,或者在错误以下,我建议更多的信息总比少的好,因此请“向上”。不确定是信息还是警告?然后发出警告。

我确实认为致命和错误对我们所有人都应该清楚。其他人可能会比较模糊,但可以说让他们正确无足。

这里有些例子:

致命 -无法分配内存,数据库等-无法继续。

错误 -无法回复邮件,交易中止,无法保存文件等。

警告 -资源分配达到X%(例如80%)-这表明您可能希望重新定义尺寸。

信息 -用户登录/注销,新交易,创建文件,新的d / b字段或已删除的字段。

调试 -内部数据结构,具有文件名和行号的任何跟踪级别的转储。
跟踪-操作成功/失败,更新d / b。


3

错误是错的,是完全错误的,无法解决,需要修复。

警告是一种模式的信号,该模式可能是错误的,但也可能不是错误的。

话虽如此,我不能提出一个很好的警告示例,它也不是错误。我的意思是,如果您遇到记录警告的麻烦,则不妨解决根本问题。

但是,诸如“ sql执行时间太长”之类的东西可能是一个警告,而“ sql执行死锁”则是一个错误,因此也许总有一些情况。


1
一个很好的警告示例是,默认情况下,在MySQL中,如果您尝试在a中插入varchar比为其定义的字符更多的字符,则会警告您该值已被截断,但仍会插入。但是一个人的警告可能是另一个人的错误:就我而言,这是一个错误;这意味着我通过定义与数据库不一致的长度在验证代码中出错。如果另一个数据库引擎认为这是一个错误,我也不会感到非常惊讶,而且我也没有真正的愤慨之意,毕竟这是错误的。
Crast 2010年

我也认为这是一个错误。在某些情况下,内容为“文本”(而不是在数据类型的意思),这意味着,也许它是确定截断它。在另一种情况下,它是一个代码,将其切掉会破坏它或改变其含义,这是不正确的。我认为,由软件来猜测我的意思是不行的。如果我尝试将200个字符串强制放入仅包含150个字符的列中,那么我想知道这个问题。但是,就像其他人在这里所做的区分一样,我确实做到了,如果您可以恢复,那是一个警告,但是……您需要登录吗?
Lasse V. Karlsen 2010年

我能想到的一个例子是:某些消息处理时间比平常长得多。这可能表明出现了问题(可能是其他系统过载或暂时关闭了外部资源)。
拉拉达

3

我一直在考虑警告第一个日志级别,这肯定意味着存在问题(例如,配置文件不在应有的位置,并且我们将必须使用默认设置运行)。对我来说,一个错误意味着某些东西意味着该软件的主要目标现在无法实现,而我们将尝试彻底关闭。


1

在此之前,我已经建立了以下系统:

  1. 错误-表示严重错误,并且特定的线程/进程/序列无法进行。需要一些用户/管理员干预
  2. 警告-某些事情是不对的,但是该过程可以像以前一样继续进行(例如,每100个作业中的一个失败,但是其余的可以处理)

在我建立的系统中,管理员正在接受对错误做出反应的指示。另一方面,我们将注意警告并针对每种情况确定是否需要任何系统更改,重新配置等。


1

顺便说一句,我非常喜欢捕获所有内容并稍后过滤信息。

如果您在警告级别捕获并且想要一些与警告有关的调试信息,但无法重新创建警告,将会发生什么情况?

捕捉一切并稍后过滤!

即使对于嵌入式软件,这也适用,除非您发现处理器无法跟上,在这种情况下,您可能需要重新设计跟踪以使其更高效,或者跟踪会干扰时序(您可能会考虑在一个功能更强大的处理器,但是却打开了一大堆蠕虫病毒。

捕捉一切并稍后过滤!!

(顺便说一句,捕获所有内容也是很好的,因为它不仅可以显示调试跟踪,还可以让您开发工具做更多的事情(我从我的消息序列图中绘制了图表,并绘制了内存使用情况的直方图。它还为您提供了一个比较基础,以供您参考)将来(保留所有日志,无论是通过还是失败,并确保在日志文件中包含内部版本号)。


1

我的两分钱FATALTRACE错误日志级别。

ERROR 发生某些故障(异常)的时间。

FATAL 实际上是双重故障:处理异常时发生异常。

Web服务很容易理解。

  1. 请求来。事件记录为INFO
  2. 系统检测到磁盘空间不足。事件记录为WARN
  3. 调用了一些函数来处理请求。当处理被零除时。事件记录为ERROR
  4. 调用Web服务的异常处理程序来处理零除。Web服务/框架将发送电子邮件,但是不能,因为邮件服务现在处于脱机状态。第二个异常不能正常处理,因为Web服务的异常处理程序无法处理异常。
  5. 调用了不同的异常处理程序。事件记录为FATAL

TRACE是我们可以跟踪功能进入/退出的时间。这与日志无关,因为此消息可以由某些调试器生成,并且您的代码根本没有调用log。因此,不是来自您的应用程序的消息将被标记为TRACE级别。例如,您使用strace

所以,通常在程序中你做DEBUGINFOWARN记录。并且只有在编写某些Web服务/框架时,您才可以使用FATAL。而且,当您调试应用程序时,TRACE将从这种类型的软件进行日志记录。


0

我建议只使用三个级别

  1. 致命的-这将破坏应用程序。
  2. 信息-信息
  3. 调试-不太重要的信息
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.