简体   繁体   中英

parse json objects from a log file

I want to parse the JSON objects from my log file. For using JSON Parser my complete files has to be in JSON format which is not the case with me. Is there any way I can parse the file line by line and get the JSON objects. Below is my log file format:

2015-10-19 11:24:35:701 INFO  BrokerTcpClient:28 - Set destination 
2015-10-19 11:24:35:929 DEBUG BrokerTcpClient:32 - received data: {type=data,  payload={

    "core" : [ {
      "id" : {
        "datatype" : "http://www.w3.org/2001/hk#long",
        "type" : "gh",
        "value" : "gh"
      },
      "entity" : {
        "type" : "uri",
        "value" : "http://fg.fg.com/ext/g/fg"
      },
      "Sno" : {
        "type" : "literal",
        "value" : "fg"
      }]
2015-10-19 11:24:35:701 INFO  BrokerTcpClient:28 - Set destination 
2015-10-19 11:24:35:929 DEBUG BrokerTcpClient:32
    "core" : [ {
      "id" : {
        "datatype" : "http://www.w3.org/2001/hk#long",
        "type" : "gh",
        "value" : "gh"
      },
      "entity" : {
        "type" : "uri",
        "value" : "http://fg.fg.com/ext/g/fg"
      },
      "Sno" : {
        "type" : "literal",
        "value" : "fg"
      }]

Can any one please help how should I get my JSON objects. When I am trying to parse a single line of JSON objects throwing an exception.

Here is a solution that works for the sample log that is posted.

import java.io.*;
import com.fasterxml.jackson.databind.*;
public class JSONTest {
    public static void main(String[] args) {
        String logFilename = "C://Temp/sample.log";
        String line, json = "";

        try (BufferedReader br = new BufferedReader(new FileReader(logFilename))) {
            while ((line = br.readLine()) != null) {
                if (isLogLine(line)) {
                    if (!json.isEmpty()) {
                        parseJson(json);
                        json = "";
                    }
                } else {
                    json += line;
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    public static boolean isLogLine(String line) {
        return line.matches("^\\d{4}\\-\\d{2}\\-\\d{2}\\s\\d{2}:\\d{2}:\\d{2}:\\d{3}.+$");
    }

    public static void parseJson(String json) throws Exception {
        if (!json.startsWith("{") && !json.endsWith("}")) json = "{" + json + "}";
        ObjectMapper om = new ObjectMapper();
        System.out.println(om.readValue(fixJson(json), Object.class));
    }

    public static String fixJson(String json) {
        return "{" + json.replace("}]", "}}]") + "}";
    }
}

Notes:

  1. the regex that identifies log line is checking for timestamp at the begining of the line. this will not work in case the log message spans multiple lines (for example if the message contains new line)
  2. there is a method that attempts to "fix" the incomplete json from the log file, it may need additional logic, if there are more cases of incomplete json along the way
  3. I used Jackson Json parser and let ObjectMapper figure out what data structure to parse into

Have you looked into logstash ( https://www.elastic.co/products/logstash )? It can solve this problem and perhaps other problems you will come across when trying to parse logs.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM