}
// very simple rfc3164 parser
@Override
protected SyslogEvent convert(Event event) {
SyslogEvent sle = new SyslogEvent();
// Stringify body so it's easy to parse.
// This is a pretty inefficient way to do it.
String msg = new String(event.getBody(), Charsets.UTF_8);
// parser read pointer
int seek = 0;
// Check Flume headers to see if we came from SyslogTcp(or UDP) Source,
// which at the time of this writing only parses the priority.
// This is a bit schizophrenic and it should parse all the fields or none.
Map<String, String> headers = event.getHeaders();
boolean fromSyslogSource = false;
if (headers.containsKey(SyslogUtils.SYSLOG_FACILITY)) {
fromSyslogSource = true;
int facility = Integer.parseInt(headers.get(SyslogUtils.SYSLOG_FACILITY));
sle.setFacility(facility);
}
if (headers.containsKey(SyslogUtils.SYSLOG_SEVERITY)) {
fromSyslogSource = true;
int severity = Integer.parseInt(headers.get(SyslogUtils.SYSLOG_SEVERITY));
sle.setSeverity(severity);
}
// assume the message was received raw (maybe via NetcatSource)
// parse the priority string
if (!fromSyslogSource) {
if (msg.charAt(0) == '<') {
int end = msg.indexOf(">");
if (end > -1) {
seek = end + 1;
String priStr = msg.substring(1, end);
int priority = Integer.parseInt(priStr);
int severity = priority % 8;
int facility = (priority - severity) / 8;
sle.setFacility(facility);
sle.setSeverity(severity);
}
}
}
// parse the timestamp
String timestampStr = msg.substring(seek, seek + 15);
long ts = parseRfc3164Date(timestampStr);
if (ts != 0) {
sle.setTimestamp(ts);
seek += 15 + 1; // space after timestamp
}
// parse the hostname
int nextSpace = msg.indexOf(' ', seek);
if (nextSpace > -1) {
String hostname = msg.substring(seek, nextSpace);
sle.setHostname(hostname);
seek = nextSpace + 1;
}
// everything else is the message
String actualMessage = msg.substring(seek);
sle.setMessage(actualMessage);
logger.debug("Serialized event as: {}", sle);
return sle;
}