【发布时间】:2019-07-17 17:37:15
【问题描述】:
我正在编写一个 cronjob,它以 lumberjack/beats 格式摄取日志并将传入日志转换为 JSON。
输入是一个包含由=分隔的键/值(嵌套)列表的字符串我想使用Javascript将其解析/映射到JSON
我已经写了这个 sn-p 来转换这个部分工作。
我的方法的唯一问题是它将嵌套对象映射到第一级,如果一个值包含= 符号,那么它也会拆分该值。
const parsedLog = {};
// Spit string by comma
log.split(", ").map(item => {
// Split string by equal to
let items = item.split("=");
// First element is the key and second one is the value. Applicable for single level JSON
if (items.length === 2) {
parsedLog[items[0].replace(/[^\w\s]/gi, '')] = items[1].replace(/[{}]/g, "");;
}
// First element is ommited and second element is the key from which we remove all special characters
// and third one is the value from which we remove curly braces. Applicable for second level JSON
if (items.length === 3) {
parsedLog[items[1].replace(/[^\w\s]/gi, '')] = items[2].replace(/[{}]/g, "");;
}
});
输入字符串:
"{@timestamp=2019-07-12T12:19:03.547Z, @metadata={beat=winlogbeat, type=doc, version=6.1.3}, level=Information, brand=test, opcode=Info, activity_id={B49D73AE-01D7-0001-C273-9DB4D701D501}, provider_guid={54849625-5478-4994-A5BA-3E3B0328C30D}, index_type=Test, type=AD, message=An account failed to log on. Subject: Security ID: S-1-0-0 Account Name: - Account Domain: - Logon ID: 0x0 Logon Type: 3 Account For Which Logon Failed: Security ID: S-1-0-0 Account Name: test Account Domain: test Failure Information: Failure Reason: Unknown user name or bad password. Status: 0xC000006D Sub Status: 0xC000006A Process Information: Caller Process ID: 0x0 Caller Process Name: - Network Information: Workstation Name: test Source Network Address: 0.0.0.0 Source Port: 0 Detailed Authentication Information: Logon Process: NtLmSsp Authentication Package: NTLM Transited Services: - Package Name (NTLM only): - Key Length: 0 This event is generated when a logon request fails. It is generated on the computer where access was attempted. The Subject fields indicate the account on the local system which requested the logon. This is most commonly a service such as the Server service, or a local process such as Winlogon.exe or Services.exe. The Logon Type field indicates the kind of logon that was requested. The most common types are 2 (interactive) and 3 (network). The Process Information fields indicate which account and process on the system requested the logon. The Network Information fields indicate where a remote logon request originated. Workstation name is not always available and may be left blank in some cases. The authentication information fields provide detailed information about this specific logon request. - Transited services indicate which intermediate services have participated in this logon request. - Package name indicates which sub-protocol was used among the NTLM protocols. - Key length indicates the length of the generated session key. This will be 0 if no session key was requested., event_data={ProcessId=0x0, IpAddress=0.0.0.0, LogonProcessName=NtLmSsp , KeyLength=0, SubjectUserSid=S-1-0-0, SubjectUserName=-, SubjectLogonId=0x0, LmPackageName=-, FailureReason=%%2313, TargetUserName=test, TargetDomainName=test, SubStatus=0xc000006a, IpPort=0, ProcessName=-, LogonType=3, WorkstationName=test, TransmittedServices=-, SubjectDomainName=-, TargetUserSid=S-1-0-0, Status=0xc000006d, AuthenticationPackageName=NTLM}, task=Logon, company=Test, tags=[windows, workstations], beat={name=test, hostname=test, version=6.1.3}, source_name=Microsoft-Windows-Security-Auditing, thread_id=4128, event_id=4625, log_name=Security, record_number=367542159, process_id=596, computer_name=test, keywords=[Audit Failure]}"
预期输出:
{
"@timestamp":"2019-07-12T12:19:03.547Z",
"@metadata":{
"beat":"winlogbeat",
"type":"doc",
"version":"6.1.3"
},
"level":"Information",
"brand":"test",
"opcode":"Info",
"activity_id":"{00-0000-00000-0000-00000}",
"provider_guid":"{54849625-5478-4994-A5BA-3E3B0328C30D}",
"index_type":"Test",
"type":"AD",
"message":"An account failed to log on. Subject: Security ID: S-1-0-0 Account Name: - Account Domain: - Logon ID: 0x0 Logon Type: 3 Account For Which Logon Failed: Security ID: S-1-0-0 Account Name: test Account Domain: test Failure Information: Failure Reason: Unknown user name or bad password. Status: 0xC000006D Sub Status: 0xC000006A Process Information: Caller Process ID: 0x0 Caller Process Name: - Network Information: Workstation Name: test Source Network Address: 0.0.0.0 Source Port: 0 Detailed Authentication Information: Logon Process: NtLmSsp Authentication Package: NTLM Transited Services: - Package Name (NTLM only): - Key Length: 0 This event is generated when a logon request fails. It is generated on the computer where access was attempted. The Subject fields indicate the account on the local system which requested the logon. This is most commonly a service such as the Server service, or a local process such as Winlogon.exe or Services.exe. The Logon Type field indicates the kind of logon that was requested. The most common types are 2 (interactive) and 3 (network). The Process Information fields indicate which account and process on the system requested the logon. The Network Information fields indicate where a remote logon request originated. Workstation name is not always available and may be left blank in some cases. The authentication information fields provide detailed information about this specific logon request. - Transited services indicate which intermediate services have participated in this logon request. - Package name indicates which sub-protocol was used among the NTLM protocols. - Key length indicates the length of the generated session key. This will be 0 if no session key was requested.",
"event_data":{
"ProcessId":"0x0",
"IpAddress":"0.0.0.0",
"LogonProcessName":"NtLmSsp",
"KeyLength":"0",
"SubjectUserSid":"S-1-0-0",
"SubjectUserName":"-",
"SubjectLogonId":"0x0",
"LmPackageName":"-",
"FailureReason":"%%2313",
"TargetUserName":"test",
"TargetDomainName":"test",
"SubStatus":"0xc000006a",
"IpPort":"0",
"ProcessName":"-",
"LogonType":"3",
"WorkstationName":"test",
"TransmittedServices":"-",
"SubjectDomainName":"-",
"TargetUserSid":"S-1-0-0",
"Status":"0xc000006d",
"AuthenticationPackageName":"NTLM"
},
"task":"Logon",
"company":"Test",
"tags":"[windows, workstations]",
"beat":{
"name":"test",
"hostname":"test",
"version":"6.1.3"
},
"source_name":"Microsoft-Windows-Security-Auditing",
"thread_id":"4128",
"event_id":"4625",
"log_name":"Security",
"record_number":"367542159",
"process_id":"596",
"computer_name":"test",
"keywords":"[Audit Failure]"
}
【问题讨论】:
-
这真的很难完成。您基本上需要实现具有条件前瞻功能的手动滑动窗口,以确保编码符号(“=”,“”)实际上不是值的一部分。它仍然有可能不是 100% 准确的。真的没有办法发送格式正确的 JSON 吗?
-
您是否搜索过现有的解析器库?
-
@Barmar 我已经搜索了现有的库,但没有运气
-
@Travis J 我尝试了所有发送格式化 JSON 的选项。现在尝试用正则表达式解决这个问题
-
这无法可靠解析。它使用逗号作为字段之间的分隔符,但
message字段也可以包含逗号。
标签: javascript json