Я пытаюсь записывать трассировки стека в Logstash.Отправить трассировку стека log4j2 по syslog
Стек протоколирования - ELK (ElasticSearch, Logstash, Kibana).
Журналы, производящие приложения, представляют собой приложение Java, используя slf4j
в качестве интерфейса ведения журнала и log4j2
в качестве реализации ведения журнала.
log4j2.xml
объявляет эту syslog
Appender, с форматом RFC5424
:
<Appenders>
<Syslog name="RFC5424" format="RFC5424" host="localhost" port="8514"
protocol="TCP" appName="MyApp" includeMDC="true" mdcId="mdc"
facility="LOCAL0" enterpriseNumber="18060" newLine="true"
messageId="Audit" id="App">
<LoggerFields>
<KeyValuePair key="thread" value="%t"/>
<KeyValuePair key="priority" value="%p"/>
<KeyValuePair key="category" value="%c"/>
<KeyValuePair key="exception" value="%ex{full}"/>
</LoggerFields>
</Syslog>
</Appenders>
Я вхожу Throwable из приложения Java, как так:
org.slf4j.LoggerFactory.getLogger("exception_test").error("Testing errors", new RuntimeException("Exception message"));
Когда исключение регистрируется, Logstash отслеживает что-то вроде этого, чтобы показать мне, что он сохраняется:
{
"@timestamp":"2016-11-08T11:08:10.387Z",
"port":60397,
"@version":"1",
"host":"127.0.0.1",
"message":"<131>1 2016-11-08T11:08:10.386Z MyComputer.local MyApp - Audit [[email protected] category=\"exception_test\" exception=\"java.lang.RuntimeException: Exception message",
"type":"syslog",
"tags":[
"_grokparsefailure"
]
}
И я подтверждаю, что Kibana отображает точно такой же JSON в поле _source
одной из своих записей в журнале.
Здесь есть проблема: трассировка стека не сохраняется. И сообщение «Ошибки тестирования» теряется.
"tags":["_grokparsefailure"]
несчастливо, но не имеет отношения к этому вопросу.
Я попытался добавить <ExceptionPattern/>
, чтобы увидеть, если это изменит что-нибудь:
<Syslog name="RFC5424" format="RFC5424" host="localhost" port="8514"
protocol="TCP" appName="MyApp" includeMDC="true" mdcId="mdc"
facility="LOCAL0" enterpriseNumber="18060" newLine="true"
messageId="Audit" id="App">
<LoggerFields>
<KeyValuePair key="thread" value="%t"/>
<KeyValuePair key="priority" value="%p"/>
<KeyValuePair key="category" value="%c"/>
<KeyValuePair key="exception" value="%ex{full}"/>
</LoggerFields>
<ExceptionPattern>%ex{full}</ExceptionPattern>
</Syslog>
<ExceptionPattern/>
заменяет сообщение журнала, а также (к сожалению) не включает все loggerFields
. Но это дает мне название класса и номер строки:
{
"@timestamp":"2016-11-08T11:54:03.835Z",
"port":60397,
"@version":"1",
"host":"127.0.0.1",
"message":"at com.stackoverflow.LogTest.throw(LogTest.java:149)",
"type":"syslog",
"tags":[
"_grokparsefailure"
]
}
Снова: нет трассировки стека. И снова: сообщение «Ошибки тестирования» теряется.
Как я могу использовать log4j2
войти трассировки стека в Logstash? Мне необязательно использовать приложение syslog
.
По существу ограничения:
- Не быть заблокирован в какой-либо конкретной лесозаготовительной инфраструктуры (именно поэтому я использовал системный журнал)
- стек Многоканальный прослеживает нужно понимать как единый журнал запись. Нежелательно, чтобы «каждая строка трассировки стека» была «отдельным сообщением журнала»
- Следы стека должны быть подвергнуты фильтрам. Типичное исключение моей может иметь трассировку стека страниц. Я хочу отфильтровать рамки, такие как Spring.