Java:如何将原始JSON记录为JSON并避免在使用logback/slf4j进行记录期间进行转义 [英] Java: How to log raw JSON as JSON and avoid escaping during logging with logback / slf4j

查看:753
本文介绍了Java:如何将原始JSON记录为JSON并避免在使用logback/slf4j进行记录期间进行转义的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我在JAX-RS应用程序中将SLF4J与Logback结合使用...我想以这样的方式登录到JSON:我的消息不再被编码,而是原始打印到日志文件中:

I'm using SLF4J with Logback in a JAX-RS application... I want to log to JSON in such a way that my message is not encoded again but printed raw into the logfile:

此刻,它看起来像这样:

At the moment it looks like this:

{"@timestamp":1363834123012,"@message":"{\"text\":\"From MLK to Barack 
Ob...\n\"}"

但是我想要这个:

  {"@timestamp":1363834123012,"@message": { "text ": "From MLK to Barack 
Ob...\n\}

原因是我想再次解析JSON,并希望避免数据转义.

The reason is I want to parse the JSON again and want to avoid the unescaping of the data.

我已经编写了一个自定义的logback编码器,但是我发现没有办法避免转义.是否可以将对象传递回登录并根据对象的类型更改设置?

I've written a custom logback encoder but I found no way to avoid the escaping. Can I pass a object to logback and change the settings based on the type of the object?

我找到了一种方法-不太优雅-按照SSCE的要求:

I've found a way - not exactly elegant - as requested a SSCE:

在我的申请中

// SLF4J Logger
private static Logger logger = LoggerFactory.getLogger(MyClass.class);
// A logback? Marker
private Marker foo = MarkerFactory.getMarker("foo");
// Jackson ObjectMapper()
ObjectMapper mapper = new ObjectMapper();

// Log something... 
logger.info(foo, mapper.writeValueAsString(json));

我使用了在这里找到的Logstash-Encoder的变体: https://github.com/logstash/logstash -logback-encoder

I've used a variation of the Logstash-Encoder found here: https://github.com/logstash/logstash-logback-encoder

package my.package;

import static org.apache.commons.io.IOUtils.*;

import java.io.IOException;
import java.util.Map;
import java.util.Map.Entry;

import org.codehaus.jackson.JsonGenerator.Feature;
import org.codehaus.jackson.JsonNode;
import org.codehaus.jackson.map.ObjectMapper;
import org.codehaus.jackson.node.ObjectNode;
import org.slf4j.Marker;

import ch.qos.logback.classic.spi.ILoggingEvent;
import ch.qos.logback.classic.spi.IThrowableProxy;
import ch.qos.logback.classic.spi.ThrowableProxyUtil;
import ch.qos.logback.core.CoreConstants;
import ch.qos.logback.core.encoder.EncoderBase;

public class JsonEncoder extends EncoderBase<ILoggingEvent> {

    private static final ObjectMapper MAPPER = new ObjectMapper().configure(
        Feature.ESCAPE_NON_ASCII, true);
    private static Marker M;

    private boolean immediateFlush = true;

@Override
public void doEncode(ILoggingEvent event) throws IOException {

    M = event.getMarker();

    ObjectNode eventNode = MAPPER.createObjectNode();

    eventNode.put("@timestamp", event.getTimeStamp());
    //
    if (M != null) {
        if (M.getName().equals("foo")) {
            JsonNode j = MAPPER.readTree(event.getFormattedMessage());
            eventNode.put("@foo", j);
        }
    } else {
        eventNode.put("@message", event.getFormattedMessage());
    }
    eventNode.put("@fields", createFields(event));

    write(MAPPER.writeValueAsBytes(eventNode), outputStream);
    write(CoreConstants.LINE_SEPARATOR, outputStream);

    if (immediateFlush) {
        outputStream.flush();
    }

}

private ObjectNode createFields(ILoggingEvent event) {
         // not important here
    return fieldsNode;

}

@Override
public void close() throws IOException {
    write(LINE_SEPARATOR, outputStream);
}

public boolean isImmediateFlush() {
    return immediateFlush;
}

public void setImmediateFlush(boolean immediateFlush) {
    this.immediateFlush = immediateFlush;
}
}

现在可以使用!是的!但我想这不是最好的方法(序列化,反序列化JSON ...)

It's works now! Yeah! But I guess it's not the best way to do it (serialize, deserialize the JSON...)

推荐答案

Logback对JSON并没有做任何异常.这只是一个正常记录的字符串.除非您正在谈论某种以这种格式写出的JSON Appender,否则转义可能会发生在您的一端.我很确定Logback本身没有这样的东西,所以如果您遇到问题,那么您想看看从哪里买到Appender都可以. SSCCE 有助于进一步进行故障排除.

Logback doesn't do anything unusual with JSON. It's just a string that gets logged as normal. The escaping is probably happening on your end, unless you're talking about some kind of JSON Appender that's writing it out in that format. I'm pretty sure Logback itself doesn't have anything like that, so you'd want to look at wherever you got the Appender from instead if that's your problem. An SSCCE would help with further troubleshooting.

这篇关于Java:如何将原始JSON记录为JSON并避免在使用logback/slf4j进行记录期间进行转义的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆