Skip to content

Commit 761baa3

Browse files
committed
contrib eventdb: add to_json script
Extract data from the IntelMQ EventDB and convert it to JSON to use it with intelmqctl
1 parent c8b9785 commit 761baa3

File tree

2 files changed

+64
-2
lines changed

2 files changed

+64
-2
lines changed

contrib/eventdb/README.md

+12-2
Original file line numberDiff line numberDiff line change
@@ -10,8 +10,8 @@ EventDB Utilities
1010
- Apply Malware Name Mapping: Applies the malware name mapping to the eventdb. Source and destination columns can be given, also a local file. If no local file is present, the mapping can be downloaded on demand.
1111
It queries the database for all distinct malware names with the taxonomy "malicious-code" and sets another column to the malware family name.
1212
- Apply Domain Suffix: Writes the public domain suffix to the `source.domain_suffix` / `destination.domain_suffix` columns, extracted from `source.fqdn` / `destination.fqdn`.
13-
- PostgreSQL trigger keeping track of the oldest inserted/updated "time.source" data. This can be useful to (re-)generate statistics or aggregation data.
14-
- SQL queries to set up a separate `raws` table, described in https://docs.intelmq.org/latest/admin/database/postgresql/#separating-raw-values-in-postgresql-using-view-and-trigger
13+
- `trigger_oldest_time.source.sql`: PostgreSQL trigger keeping track of the oldest inserted/updated "time.source" data. This can be useful to (re-)generate statistics or aggregation data.
14+
- `to_json.py`: Export EventDB data to JSON, to use it in IntelMQ again.
1515

1616
Usage
1717
-----
@@ -22,6 +22,16 @@ See `--help` for more information:
2222
```
2323
apply_mapping_eventdb.py -h
2424
apply_domain_suffix.py -h
25+
to_json.py -h
2526
```
2627

2728
The SQL script can be executed in the database directly.
29+
30+
### `to_json.py`
31+
32+
33+
- Get an event by ID: `~intevation/to_json.py --id $id`
34+
- You can give multiple IDs
35+
- Pretty printed: Add `--pretty`
36+
- Inject the data into an IntelMQ bot (dry run):
37+
- `intelmqctl run $botid process --dry-run --show-sent --msg '$jsondata'`

contrib/eventdb/to_json.py

+52
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
#!/usr/bin/python3
2+
3+
# SPDX-FileCopyrightText: 2025 Institute for Common Good Technology
4+
#
5+
# SPDX-License-Identifier: AGPL-3.0-or-later
6+
7+
from argparse import ArgumentParser
8+
from datetime import datetime
9+
import json
10+
from sys import exit, stderr
11+
from pprint import pprint
12+
13+
from psycopg2 import connect
14+
from psycopg2.extras import RealDictCursor
15+
16+
parser = ArgumentParser(
17+
prog='EventDB to JSON',
18+
description='Extract data from the IntelMQ EventDB')
19+
parser.add_argument('-v', '--verbose', action='store_true')
20+
parser.add_argument('-i', '--id', help='Get events by ID')
21+
parser.add_argument('-p', '--pretty', action='store_true', help='Pretty print JSON output')
22+
parser.add_argument('--dsn', help='A complete libpg conninfo string. If not given, it will be loaded from /etc/intelmq/eventdb-serve.conf')
23+
args = parser.parse_args()
24+
25+
if args.dsn:
26+
conninfo = args.dsn
27+
else:
28+
try:
29+
with open('/etc/intelmq/eventdb-serve.conf') as fody_config:
30+
conninfo = json.load(fody_config)['libpg conninfo']
31+
except FileNotFoundError as exc:
32+
print(f'Could not load database configuration. {exc}', file=stderr)
33+
exit(2)
34+
35+
if args.verbose:
36+
print(f'Using DSN {conninfo!r}.')
37+
db = connect(dsn=conninfo)
38+
cur = db.cursor(cursor_factory=RealDictCursor)
39+
cur.execute ('SELECT * FROM events WHERE id = %s', (args.id, ))
40+
41+
for row in cur.fetchall():
42+
del row['id']
43+
for key in list(row.keys()):
44+
if isinstance(row[key], datetime):
45+
# data from the database has TZ information already included
46+
row[key] = row[key].isoformat()
47+
elif row[key] is None:
48+
del row[key]
49+
if args.pretty:
50+
print(json.dumps(row, indent=2))
51+
else:
52+
print(json.dumps(row))

0 commit comments

Comments
 (0)