本文介绍如何通过日志服务 Log4j2 Appender 上传日志到日志服务。
Log4j2 是 log4j 的升级版本。借助 Log4j2,您可以控制日志信息输送的目的端,包括控制台、文件、GUI 组件、套接口服务器、NT 的事件记录器、UNIX Syslog 守护进程等;您也可以控制每一条日志的输出格式;您还可以定义每一条日志信息的级别,更加细致地控制日志的生成过程。您只需通过一个配置文件即可实现上述功能,无需修改应用的代码。
通过 TLS Log4j2 Appender,您可以控制日志的输出目的端为火山引擎日志服务,上传的日志样式如下:
说明
TLS Log4j2 Appender 不支持设置日志的输出格式。
level: ERROR location: example.com.volcengine.service.tls.log4j2.Log4j2AppenderExample.main(Log4j2AppenderExample.java:16) message: error log throwable: java.lang.RuntimeException: xxx thread: main time: 2018-01-02T03:15+0000 log: 2018-01-02 11:15:29,682 ERROR [main] example.com.volcengine.service.tls.log4j2.Log4j2AppenderExample: error log __source__: xxx
字段 | 说明 |
---|---|
| 日志级别。 |
| 日志打印语句的代码位置。 |
| 日志内容。 |
| 日志异常信息。 |
| 线程名称。 |
| 日志打印时间。 |
| 自定义日志格式。 |
| 日志来源。 |
volc-sdk-java 1.0.188,该版本主要适配于 Log4J 2.X 以上版本。
参考如下示例,在 Maven 工程中添加依赖。
<dependency> <groupId>com.volcengine</groupId> <artifactId>ve-tls-log4j2-appender</artifactId> <version>1.0.0</version> </dependency>
以配置文件 log4j2.xml 为例(不存在则在项目根目录创建),配置 Loghub 相关的 appender 与 Logger。示例代码如下:
<Appenders> <Loghub name="Loghub" topicId="your topicId" endpoint="your project endpoint" region="your region" accessKeyId="your accessKey id" accessKeySecret="your accessKey secret" totalSizeInBytes="104857600" maxBlockMs="0" maxThreadCount="8" maxBatchSizeBytes="524288" maxBatchCount="4096" lingerMs="2000" retryCount="3" maxReservedAttempts="3" source="your source" timeFormat="yyyy-MM-dd'T'HH:mmZ" timeZone="UTC" ignoreExceptions="true"> <PatternLayout pattern="%d %-5level [%thread] %logger{0}: %msg"/> </Loghub> </Appenders> <Loggers> <Root level="warn"> <AppenderRef ref="Loghub"/> </Root> </Loggers>
其中,level 是日志记录的优先级,优先级从高到低分别是 ERROR、WARN、INFO、DEBUG。通过定义日志级别,您可以控制应用程序中相应级别的日志信息开关。例如定义了 WARN 级别,则应用程序中所有 INFO、DEBUG 级别的日志信息将不被打印出来。
TLS Log4j2 Appender 可供配置的属性(参数)如下,其中如果可选参数未配置,则使用默认值。
#日志服务的服务地址,必选参数 endpoint = [your project endpoint] #日志服务所在地域,必选参数 region = [your region] #访问密钥,必选参数 accessKeyId = [your accesskey id] accessKeySecret = [your accessKeySecret] #指定日志主题ID,必选参数 topicId = [your topicId] #单个 Producer 实例能缓存的日志大小上限,默认为 100MB。 totalSizeInBytes=104857600 #如果 Producer 可用空间不足,调用者在 send 方法上的最大阻塞时间,默认为 0 秒。为了不阻塞打印日志的线程,强烈建议将该值设置成 0。 maxBlockMs=0 #执行日志发送任务的线程池大小,默认为可用处理器个数。 maxThreadCount=8 #当一个 ProducerBatch 中缓存的日志大小大于等于 maxBatchSizeBytes 时,该 batch 将被发送,默认为 512 KB,最大可设置成 5MB。 maxBatchSizeBytes=524288 #当一个 ProducerBatch 中缓存的日志条数大于等于 maxBatchCount 时,该 batch 将被发送,默认为 4096,最大可设置成 40960。 maxBatchCount=4096 #一个 ProducerBatch 从创建到可发送的逗留时间,默认为 2 秒,最小可设置成 100 毫秒。 lingerMs=2000 #如果某个 ProducerBatch 首次发送失败,能够对其重试的次数,默认为 10 次。 #如果 retryCount 小于等于 0,该 ProducerBatch 首次发送失败后将直接进入失败队列。 retryCount=3 #该参数越大能让您追溯更多的信息,但同时也会消耗更多的内存。 maxReservedAttempts=3 #指的日志来源,默认为应用程序所在宿主机的 IP,可选参数 source = [your source] #输出到日志服务的时间的格式,默认是 yyyy-MM-dd'T'HH:mm:ssZ,可选参数 timeFormat = yyyy-MM-dd'T'HH:mm:ssZ #输出到日志服务的时间的时区,默认是 UTC,可选参数(如果希望 time 字段的时区为东八区,可将该值设定为 Asia/Shanghai) timeZone = UTC
项目中提供了一个名为 com.volcengine.service.tls.log4j2.example.Log4j2AppenderExample
的实例,它会加载 resources 目录下的 log4j2-example.xml
文件进行 Log4j2 配置。log4j2.xml
样例说明如下:
com.volcengine.service.tls.log4j2.example.Log4j2AppenderExample
示例如下:
package com.volcengine.service.tls.log4j2.example; import org.apache.logging.log4j.LogManager; import org.apache.logging.log4j.Logger; public class Log4j2AppenderExample { private static final Logger LOGGER = LogManager.getLogger(Log4j2AppenderExample.class); public static void main(String[] args) { LOGGER.trace("log4j2 trace log"); LOGGER.debug("log4j2 debug log"); LOGGER.info("log4j2 info log"); LOGGER.warn("log4j2 warn log"); LOGGER.error("log4j2 error log", new RuntimeException("Runtime Exception")); } }
og4j2-example.xml
示例如下:
<?xml version="1.0" encoding="UTF-8"?> <Configuration status="WARN"> <Appenders> <Loghub name="loghubAppender1" topicId="topic1" endpoint="" region="" accessKeyId="" accessKeySecret="" totalSizeInBytes="104857600" maxBlockMs="0" maxThreadCount="8" maxBatchSizeBytes="524288" maxBatchCount="4096" lingerMs="2000" retryCount="3" maxReservedAttempts="3" source="source1" timeFormat="yyyy-MM-dd'T'HH:mm:ssZ" timeZone="UTC" ignoreExceptions="true"> </Loghub> <Loghub name="loghubAppender2" topicId="topic2" endpoint="" region="" accessKeyId="" accessKeySecret="" totalSizeInBytes="104857600" maxBlockMs="0" maxThreadCount="8" maxBatchSizeBytes="524288" maxBatchCount="4096" lingerMs="2000" retryCount="3" maxReservedAttempts="3" source="source2" timeFormat="yyyy-MM-dd'T'HH:mm:ssZ" timeZone="Asia/Shanghai" ignoreExceptions="true"> <PatternLayout pattern="%d{HH:mm:ss.SSS} %-5level %class{36} %L %M - %msg%xEx"/> <Filters> <!-- Now deny warn, error and fatal messages --> <ThresholdFilter level="warn" onMatch="DENY" onMismatch="NEUTRAL"/> <ThresholdFilter level="error" onMatch="DENY" onMismatch="NEUTRAL"/> <ThresholdFilter level="fatal" onMatch="DENY" onMismatch="NEUTRAL"/> <!-- This filter accepts info, warn, error, fatal and denies debug/trace --> <ThresholdFilter level="info" onMatch="ACCEPT" onMismatch="DENY"/> </Filters> </Loghub> <Console name="STDOUT" target="SYSTEM_OUT"> <PatternLayout pattern="%d{HH:mm:ss.SSS} [%t] %-5level %logger{36} - %msg%n"/> </Console> </Appenders> <Loggers> <Root level="DEBUG"> <AppenderRef ref="loghubAppender1" level="WARN"/> <AppenderRef ref="loghubAppender2"/> <AppenderRef ref="STDOUT"/> </Root> </Loggers> </Configuration>
如果您遇到数据未成功写入日志服务的情况,可通过如下步骤进行排查。
log4j2.xml
是否限定了 Appender 只输出特定级别的日志。例如是否设置了 root,logger 或 appender 的 Level 属性,是否在 Appender 中使用了 filter。org.apache.logging.log4j.status.StatusLogger
进行记录。默认情况下 Log4j2 框架会为 StatusLogger 注册一个 StatusConsoleListener,因此 TLS Log4j2 Appender 运行过程中产生的异常会被打印到控制台。是否支持自定义日志格式?
0.1.9 及以上版本新增了 log
字段,您可以通过配置 layout 来自定义日志格式,示例如下:
<PatternLayout pattern="%d %-5level [%thread] %logger{0}: %msg"/>
输出的日志样例如下:
log: 2018-07-15 21:12:29,682 INFO [main] TestAppender: info message.
如何采集宿主机 IP 地址?
支持自动采集宿主机 IP 地址。无需在 log4j2.xml
中设置 source
字段的值,否则 source
字段会被设置成应用程序所在宿主机的 IP 地址。
是否支持自定义 source
字段的取值?
支持,您可以参考上面的配置文件指定 source
的取值。
在网络发生异常的情况下,ve-tls-log4j2-appender
会如何处理待发送的日志?ve-tls-log4j2-appender
底层使用 tls-log-producer-java
发送数据。Producer 会根据您在配置文件中设置的 retryCount
进行重试,如果超过 retryCount
次数据仍没有发送成功,会将错误信息输出,并丢弃该条日志。关于如何查看错误输出,请参考错误排查。
如何关闭某些类输出的日志?
您可以通过在 log4j2.xml
文件中添加 <Logger name="packname" level="OFF"/>
来屏蔽相应包下的日志输出。例如,当您在 log4j2.xml
文件中添加如下内容,将屏蔽包名为 com.volcengine.service.tls.log.producer.inner
下所有类的日志输出。
<Loggers> <Root level="DEBUG"> <AppenderRef ref="Loghub"/> </Root> <Logger name="com.volcengine.service.tls.log.producer.inner" level="OFF"/> </Loggers>
如果想设置 time
字段的时区为东八区或其他时区,应如何指定 timeZone
的取值?
当您将 timeZone
指定为 Asia/Shanghai
时,time
字段的时区将为东八区。timeZone
字段取值请参考 java-util-timezone。