**Apache Log4j**是一个基于Java的日志记录工具。它是由瑞士程式設計師Ceki Gülcü於2001年开发的，现在则是Apache软件基金会的一个项目。 Log4j是几种Java日志框架（英语：）之一。

Gülcü此后开创了SLF4J和Logback 项目，想使其成为Log4j的继任者。

Log4j团队创建了Log4j的继任者，版本号为2.0的新版本。Log4j 2.0着重于Log4j 1.2、1.3、java.util.logging和logback中的问题，并解决这些框架中的架构问题。此外，Log4j 2.0提供了一个插件架构，这使得其更可扩展。Log4j 2.0不是与1.x向后兼容的版本，虽然有一个"适配器"可用。

2021年12月9日，Log4j 2.0的一个零日远程代码执行漏洞被报告，其被称为"Log4Shell"，公共漏洞和暴露編號為CVE-2021-44228。它被定性为"过去十年来最大、最关键的漏洞"。

log4j 1的日志等级
------------

下表中定义的log4j 1的日志级别和消息，以严重性递减排序。左栏列出了log4j的日志级别定义，右列提供了每个日志级别的简要说明。

| **级别** | **描述** |
| --- | --- |
| **OFF** | 最高级别，用于关闭日志记录。 |
| **FATAL** | 导致应用程序提前终止的严重错误。一般这些信息将立即呈现在状态控制台上。 |
| **ERROR** | 其他运行时错误或意外情况。一般这些信息将立即呈现在状态控制台上。 |
| **WARN** | 使用已过时的API，API的滥用，潜在错误，其他不良的或意外的运行时的状况（但不一定是错误的）。一般这些信息将立即呈现在状态控制台上。 |
| **INFO** | 令人感兴趣的运行时事件（启动/关闭）。一般这些信息将立即呈现在状态控制台上，因而要保守使用，并保持到最低限度。 |
| **DEBUG** | 流经系统的详细信息。一般这些信息只记录到日志文件中。 |
| **TRACE** | 最详细的信息。一般这些信息只记录到日志文件中。自版本1.2.12。 |

配置Log4j 1.2
-----------

有三种方法来配置log4j：通过.properties文件，通过XML文件，通过Java代码。通过上述任意方法，你可以定义log4j的三个主要组件：Logger、Appender和Layout。通过文件配置log4j，具有无需修改应用即可打开或关闭日志的好处。例如，应用程序可以在日志关闭的情况下运行，直到问题出现后，再日志功能可以简单地通过修改配置文件重新打开。

**Logger**（记录器）是日志的逻辑文件名。其使用已知的Java应用程序的名称。每个记录器当前以什么日志记录级别（FATAL、ERROR等）记录是独立配置的。在log4j的早期版本中，这些被称为类别（category）和优先级（priority），但现在他们分别被称为logger（记录器）和level（级别）。

实际的输出是通过**Appender**（输出源）。有许多可用的Appender，比如FileAppender、ConsoleAppender、SocketAppender、SyslogAppender、NTEventLogAppender，甚至SMTPAppender。多个Appender可以被关联到任何Logger上，所以可以到多个输出文件上记录相同的信息，例如同时到一个本地文件和通过套接字监听器到另一台计算机上。

Appender使用**Layout**（布局）格式化日志条目。常用的格式化为"一次一行"式日志文件的布局是PatternLayout，其使用一个模式字符串，就像C/C++函数printf那样。此外还有HTMLLayout和XMLLayout，使用HTML或XML格式的时候会更方便。

要调试一个表现异常的配置文件，使用Java VM参数`-Dlog4j.debug`通过标准输出输出Log4j自身的信息。要获知log4j.propeties的路径，检查`getClass().getResource("/log4j.properties")`或`getClass().getResource("/log4j.xml")`。

log4j还有一个隐含的"未配置"配置，即一个缺乏log4j的配置但使用了log4j的Java应用程序。这将把一个警告（该程序未配置log4j）打印到标准输出，并提供log4j网站的URL，在那里可以找到警告和配置的详细信息。除了打印此警告，未配置的log4j的应用程序不会打印INFO、DEBUG或TRACE级别的消息，而且还可能不输出更高级别的消息。

### log4j 1.2 配置示例

```
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE log4j:configuration PUBLIC "-//LOGGER" "http://logging.apache.org/log4j/1.2/apidocs/org/apache/log4j/xml/doc-files/log4j.dtd">
<log4j:configuration>
 <!-- 
 appender指定输出目的地，如控制台或文件；
         appender的名称任意
 -->
 <appender name="stdout" class="org.apache.log4j.ConsoleAppender">
 <layout class="org.apache.log4j.PatternLayout">
 <param name="ConversionPattern"
 value="%d{ABSOLUTE} %5p %c{1}:%L - %m%n" />
 </layout>
 </appender>
 
 <!-- 
 category（类别）为'org.springframework'的logger只记录level为"info"或更高级别的消息；
         即：如果您使用的类名获取logger（如Logger.getLogger(AClass.class)）
         而且AClass是org.springframework包的一部分，则它属于这一category
 -->
 <logger name="org.springframework">
 <level value="info"/>
 </logger>

 <!-- 
 spring的所有日志消息都被设置为"info"等级，但对于类PropertyEditorRegistrySupport，
 我们想将其日志消息设置为"debug"等级
 -->
 <logger name="org.springframework.beans.PropertyEditorRegistrySupport">
 <level value="debug"/>
 </logger>
 
 <logger name="org.acegisecurity">
 <level value="info"/>
 </logger>
 
 
 <root>
 <!-- 
 所有日志消息的级别为"debug"或更高的将被记录，除非另有定义
 所有日志消息将都记录到appender "stdout"中，除非另有定义
 -->
 <level value="debug" />
 <appender-ref ref="stdout" />
 </root>
</log4j:configuration>

```

TTCC
----

TTCC是log4j使用的消息格式。TTCC是*Time Thread Category Component*（时间、线程、类别、组件）的缩写。例如，采用以下模式（pattern）：

```
 %r [%t] %-5p %c %x - %m%n
```

模式转换表为：

| 模式参数 | 描述 |
| --- | --- |
| %r | 用于输出从layout（布局）的构建到日志事件创建所经过的毫秒数。 |
| %t | 用来输出生成该日志事件的线程的名称。 |
| %p | 用于输出日志事件的优先级。 |
| %c | 用于输出日志事件的category（类别）。 |
| %x | 用于输出与产生该日志事件的线程相关联的NDC（嵌套诊断上下文，nested diagnostic context）。 |
| %X{key} | 用于输出与产生指定的key的日志事件的线程相关联的MDC （页面存档备份，存于）（映射诊断上下文，mapped diagnostic context） |
| %m | 用于输出与日志记录事件相关联的应用程序提供的消息。 |
| %n | 用来输出该其所在的特定平台的换行字符。 |

**示例输出**  

467 [main] INFO org.apache.log4j.examples.Sort - Exiting main method.

移植
--

* *log4c*——一个C语言下的移植。最新的版本为2013年发布的1.2.4版。该项目已不再活跃。
* *log4js*——一个JavaScript下的移植。最新的版本为2008年发布的1.1版。
* log4javascript （页面存档备份，存于）——JavaScript下的另一个移植。最新的版本为2014年5月发布的1.4.6版。
* JSNLog （页面存档备份，存于）——JavaScript下的另一移植。在2014年7月，最新的版本为2.7.1，并且定期更新。
* Apache Log4net——微软.NET Framework下的移植。最新的版本为2013年发布的1.2.13。
* log4perl （页面存档备份，存于）——log4j日志软件包在一个Perl下的移植。最新的版本为2014年5月发布的1.44。
* log4r——一个Ruby下的"移植"。
* PL-SQL-Logging-Utility （页面存档备份，存于）——log4j在PL/SQL下的一种实现。
* Log4db2 （页面存档备份，存于）——一个为使用SQL命令和SQL PL代码的DB2 LUW的日志记录工具

Apache Log4j 2
--------------

Apache Log4j 2是Log4j 1的继任者，2014年7月其GA版本（正式发布版）发布。该框架被从头重写，并从现有的日志解决方案中获得灵感（包括Log4j 1和JUL）。该版本与Log4j 1的主要差异是：

* 改进的配置语法
* 支持XML和JSON配置
* 改进的过滤器
* 属性（Property）支持
* 标记
* 提高速度
* 模块化：Log4j 2支持插件系统
* 提高了可靠性
* 配置自动重装

Log4j 2的最被认可的特点之一是"异步记录器"的性能。Log4j 2利用了LMAX Disruptor （页面存档备份，存于）。例如，在相同的环境下，Log4j 2可以写每秒超过18,000,000条信息，而其他框架（像Logback和Log4j 1）每秒只能写< 2,000,000条消息。

Log4j 2提供对SLF4J、Commons Logging、Apache Flume和Log4j 1的支持。

Log4Shell漏洞
-----------

阿里巴巴集团于2021年11月24日发现并报告给 Apache ，并于12月9日在推文中发布了一个涉及 Log4j 2 中远程代码执行的零日漏洞，其描述符为"Log4Shell"（CVE -2021-44228 （页面存档备份，存于）），受影响的服务包括Cloudflare、iCloud、我的世界：Java版、 Steam、腾讯QQ和推特。 Apache软件基金会分配了最大CVSS Log4Shell 的严重等级为10，因为数百万台服务器可能容易受到该漏洞的攻击。网络安全公司Tenable（英语：）将该漏洞描述为"过去十年中最大、最关键的漏洞" ，Lunasec 的 Free Wortley 将其描述为"灾难性的设计失败"。

在美国，网络安全和基础设施安全局（英语：）主任Jen Easterly（英语：）称该漏洞利用"至关重要"，并建议供应商优先考虑软件更新，和德国机构联邦信息安全办公室(BSI)将该漏洞指定为处于最高威胁级别，称其为"极其严重的威胁情况"（翻译）。加拿大网络安全中心（英语：）呼吁各组织立即采取行动。

可以通过配置设置禁用导致漏洞的功能，该设置已在 Log4j 版本 2.15.0-rc1（2021年12月6日正式发布，漏洞发布前三天）中删除 ，并替换为各种设置限制远程查找，从而减轻漏洞。为提高安全性，此漏洞所基于的所有使用JNDI的功能将默认禁用，并且从版本 2.16.0 开始删除对消息查找的支持。

官方的Minecraft：Java 版启动器已修补此漏洞。使用自定义启动器或自定义 Java 版本可能意味着客户端尚未打补丁。在没有修补此漏洞的服务器上玩游戏将允许服务器上的任何玩家在另一个客户端的计算机上执行潜在的恶意代码。在 1.18.1 以上的版本上玩单人游戏或多人游戏将防止此漏洞。低于 1.7 的版本不受影响。如果游戏服务器主机运行的是 1.7-1.18 版本，则必须专门修补其服务器，如果不这样做，任何玩家都可以使用此漏洞。

参考文献
----

1. ↑ . apache.org. Apache Software Foundation.  [2014-09-02]. （原始内容存档于2020-12-02）.
2. ↑ . 2023年11月20日  [2023年12月19日].
3. ↑ . Apache Software Foundation.  [2014-07-14]. （原始内容存档于2020-11-21）.
4. ↑ . Lawfare. December 10, 2021  [2021-12-12]. （原始内容存档于2022-04-26）.
5. ↑  Press, Associated.. the Guardian. December 11, 2021  [2021-12-12]. （原始内容存档于2022-04-15）.
6. ↑ . Apache Software Foundation.  [2014-07-14]. （原始内容存档于2020-08-03）.
7. ↑  MDC内部使用了类似map的机制来存储相关信息，信息是以它的key值存储在"map"中。
8. ↑ . SourceForge.  [2014-07-16]. （原始内容存档于2019-04-30）.
9. ↑ .  [2017-09-05]. （原始内容存档于2013-09-07）.
10. ↑  Tim Down..  [2014-07-16]. （原始内容存档于2020-07-31）.
11. ↑  Mattijs Perdeck..  [2014-07-16]. （原始内容存档于2020-12-03）.
12. ↑ . . Apache Software Foundation.  缺少或`|url=`为空 (帮助); 使用`|accessdate=`需要含有`|url=` (帮助); 外部链接存在于`|work=` (帮助)
13. ↑ .  [2014-07-14]. （原始内容存档于2013-01-23）.
14. ↑ .  [2017-09-05]. （原始内容存档于2012-12-25）.
15. ↑  Christian Grobmeier..  [2014-07-14]. （原始内容存档于2015-11-23）.

延展阅读
----

* Gülcü, Ceki,  2nd, QOS.ch: 204, February 2010, ISBN 978-2-9700369-0-6
* Gupta, Samudra,  2nd, Apress: 224, June 22, 2005, ISBN 978-1-59059-499-5

参閱
--

* 自由软件主题
* Java主题

* Chainsaw（英语：）

外部链接
----

* log4j官方主页 （页面存档备份，存于）


|  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |
| --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- |
| 

| * 
* 论
* 编
Apache软件基金会 |
| --- |
|  |
| 顶级项目 | 
* Abdera（英语：）
* Accumulo（英语：）
* ActiveMQ
* Ambari（英语：）
* Ant
* Aries（英语：）
* Apache Arrow
* Apache HTTP Server
* APR
* Avro
* Axis
* Axis2
* Beam
* Bloodhound（英语：）
* Apache Brooklyn（英语：）
* Buildr（英语：）
* Calcite（英语：）
* Camel
* Cassandra
* Cayenne（英语：）
* Chemistry（英语：）
* CloudStack（英语：）
* Cocoon（英语：）
* Continuum（英语：）
* Cordova
* CouchDB
* cTAKES（英语：）
* CXF
* Deltacloud（英语：）
* Derby
* Directory（英语：）
* Drill（英语：）
* Empire-db（英语：）
* ECharts
* Felix（英语：）
* Flex
* Flink
* Flume（英语：）
* Forrest（英语：）
* Geronimo（英语：）
* Gora（英语：）
* Gump（英语：）
* Hadoop
* Hama（英语：）
* HBase
* Hive
* Jackrabbit（英语：）
* James（英语：）
* JMeter（英语：）
* Kafka
* Karaf（英语：）
* Kylin（英语：）
* Lucene
* Lenya（英语：）
* Mahout（英语：）
* Marmotta（英语：）
* Maven
* MINA（英语：）
* mod\_perl（英语：）
* MyFaces（英语：）
* Nutch（英语：）
* ODE（英语：）
* OFBiz（英语：）
* Oozie（英语：）
* OpenEJB（英语：）
* OpenJPA（英语：）
* OpenNLP
* OpenOffice
* PDFBox（英语：）
* Phoenix（英语：）
* POI
* Pig（英语：）
* Pivot（英语：）
* Qpid（英语：）
* River（英语：）
* Roller（英语：）
* RocketMQ
* Samza（英语：）
* ServiceMix（英语：）
* Shindig（英语：）
* Shiro
* Sling（英语：）
* Spark
* Stanbol（英语：）
* Storm
* SpamAssassin
* Sqoop
* Apache C++标准库（英语：）
* Struts
* Struts 2
* Subversion
* Tapestry
* Thrift
* Tiles（英语：）
* Tika（英语：）
* Tomcat
* Trafficserver
* Turbine
* Tuscany
* UIMA
* Velocity
* Wave
* Wicket
* Wink（英语：）
* Xalan（英语：）
* Xerces（英语：）
* XMLBeans（英语：）
* ZooKeeper

 | ASF logo |
|  |
| Commons项目 | 
* Apache Commons Logging（英语：）
* BCEL（英语：）
* BSF（英语：）
* Commons Daemon（英语：）
* Jelly（英语：）

 |
|  |
| Lucene项目 | 
* Lucene Java
* Lucene.Net（英语：）
* Nutch（英语：）
* Solr

 |
|  |
| Hadoop项目 | 
* HBase
* HDFS

 |
|  |
| 其他项目 | 
* Batik
* Chainsaw（英语：）
* FOP
* Log4j
* XAP（英语：）
* Log4Net
* Ivy（英语：）

 |
|  |
| 孵化器项目 | 
* XAP（英语：）
* Samza（英语：）
* Storm

 |
|  |
| Apache Attic | 
* AxKit（英语：）
* Beehive（英语：）
* Click（英语：）
* Bluesky（英语：）
* Cactus（英语：）
* Jakarta
* Excalibur（英语：）
* Harmony
* HiveMind（英语：）
* Lenya（英语：）
* Slide（英语：）
* Shale（英语：）
* Shindig（英语：）
* stdcxx（英语：）
* iBATIS
* XMLBeans（英语：）

 |
|  |
| 许可证标准 | 
* Apache许可证

 |
|  |
| 
* 分类 **分类**
* 共享资源页面 **维基共享**

 |

 |