/
json2db.py
executable file
·151 lines (127 loc) · 5.29 KB
/
json2db.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
#!/usr/bin/python
import json
import sys
import os
import init_db
from datetime import datetime
from pytz import timezone
__author__ = 'SimonSK'
def add_predefined_tag(connection, key_dict):
with connection.cursor() as cursor:
for tag in key_dict.itervalues():
sql = "INSERT IGNORE INTO Tag (tag, type) " \
"VALUES (%s, %s)"
cursor.execute(sql, (tag, "SRC"))
cursor.execute(sql, (tag, "DST"))
def add_pcap(connection, pcapid, pcaptime):
with connection.cursor() as cursor:
# new pcap entry. ignore if the primary key already exists.
sql = "INSERT IGNORE INTO PacketCapture (pcapid, pcaptime)" \
"VALUES (%s, %s)"
cursor.execute(sql, (pcapid, pcaptime))
connection.commit()
print('new pcap added!')
def add_packet(connection, pcapid, packets):
with connection.cursor() as cursor:
# Insert a row for every packet. ignore if the primary key already exists.
for packet in packets:
sql = "INSERT IGNORE INTO Packet (pcapid, pin, packettime, src, dst, protocol, len, payload)" \
"VALUES (%s, %s, %s, %s, %s, %s, %s, %s)"
cursor.execute(sql, (pcapid, packet['PIN'], convert_time(packet['time']), packet['src'], packet['dest'],
packet['protocol'], packet['length'], packet['Load'])
)
if "tag" in packet:
tags = packet['tag']
for type, tag in tags.items():
if not tag:
continue
sql = "INSERT IGNORE INTO Tagged (tagid, pcapid, pin)" \
"SELECT DISTINCT Tag.tagid, %s, %s " \
"FROM Tag " \
"WHERE Tag.type = %s AND Tag.tag = %s"
cursor.execute(sql, (pcapid, packet['PIN'], type, tag))
connection.commit()
auto_tag(cursor, pcapid, packet)
connection.commit()
print('new packets added!')
def auto_tag(cursor, pcapid, packet):
pin = packet['PIN']
dst = packet['dest']
src = packet['src']
tag_query = "SELECT DISTINCT Tag.tagid, Tag.tag, Tag.type " \
"FROM Tag, Tagged, Packet " \
"WHERE Tag.tagid = Tagged.tagid " \
"AND Tagged.pcapid = Packet.pcapid " \
"AND Tagged.pin = Packet.pin " \
"AND NOT (Packet.pcapid = %s AND Packet.pin = %s) " \
"AND ((Tag.type = 'SRC' AND Packet.src = %s) OR (Tag.type = 'DST' AND Packet.dst = %s))"
cursor.execute(tag_query, (pcapid, pin, src, src))
src_tag = cursor.fetchall()
if len(src_tag) > 0:
sql = "INSERT IGNORE INTO Tag (tag, type) " \
"VALUES (%s, %s)"
cursor.execute(sql, (src_tag[0][1], "SRC"))
sql = "SELECT tagid FROM Tag " \
"WHERE tag = %s " \
"AND type = %s"
cursor.execute(sql, (src_tag[0][1], "SRC"))
src_tagid = cursor.fetchone()
sql = "INSERT IGNORE INTO Tagged (tagid, pcapid, pin) VALUES (%s, %s, %s)"
cursor.execute(sql, (src_tagid, pcapid, pin))
cursor.execute(tag_query, (pcapid, pin, dst, dst))
dst_tag = cursor.fetchall()
if len(dst_tag) > 0:
sql = "INSERT IGNORE INTO Tag (tag, type) " \
"VALUES (%s, %s)"
cursor.execute(sql, (dst_tag[0][1], "DST"))
sql = "SELECT tagid FROM Tag " \
"WHERE tag = %s " \
"AND type = %s"
cursor.execute(sql, (dst_tag[0][1], "DST"))
dst_tagid = cursor.fetchone()
sql = "INSERT IGNORE INTO Tagged (tagid, pcapid, pin) VALUES (%s, %s, %s)"
cursor.execute(sql, (dst_tagid, pcapid, pin))
#print('new packet tagged!!')
def convert_time(epoch):
time = datetime.fromtimestamp(epoch).strftime('%Y-%m-%d %H:%M:%S.%f')
datetime_obj = datetime.strptime(time, '%Y-%m-%d %H:%M:%S.%f')
time_utc = timezone('UTC').localize(datetime_obj)
time_cst = time_utc.astimezone(timezone('America/Chicago'))
return time_cst.strftime('%Y-%m-%d %H:%M:%S.%f')
def main(argv):
print("begin importing json to database")
if not argv[0] or not os.path.isfile(argv[0]):
print('need existing json file as the argument')
exit(1)
# load json
pcap = json.load(open(argv[0]))
# check if json is properly formatted
if not pcap['PcapID'] or not pcap['Packets']:
print('input is in unexpected format')
exit(1)
# variable for later use
pcapid = pcap['PcapID'].split('/')[-1]
packets = pcap['Packets']
pcaptime = convert_time(packets[0]['time'])
# connect to db
connection = init_db.connect_database()
if not connection:
print('database connection failed!')
exit(1)
# check tables
init_db.create_pcap(connection)
init_db.create_packet(connection)
init_db.create_tag(connection)
init_db.create_tagged(connection)
# add predefined tags if the list is provided
if "Keywords" in pcap:
key_dict = pcap['Keywords']
add_predefined_tag(connection, key_dict)
# add packets
add_pcap(connection, pcapid, pcaptime)
add_packet(connection, pcapid, packets)
# close connection
connection.close()
os.remove(argv[0])
if __name__ == "__main__":
main(sys.argv[1:])