From 71fe4f6ebe0a89046540edd9a2aa74b8e565d266 Mon Sep 17 00:00:00 2001 From: stark4n6 <48143894+stark4n6@users.noreply.github.com> Date: Wed, 11 Jan 2023 11:43:21 -0500 Subject: [PATCH] Timelining Updates - Small fixes to display proper times in timeline - Remove entries that aren't timelined --- scripts/artifacts/WhatsApp.py | 18 ++++++++---- scripts/artifacts/downloads.py | 4 ++- scripts/artifacts/mewe.py | 13 ++++++--- scripts/artifacts/snapchat.py | 53 +++++++++++++++++++++------------- 4 files changed, 58 insertions(+), 30 deletions(-) diff --git a/scripts/artifacts/WhatsApp.py b/scripts/artifacts/WhatsApp.py index 7d9c2832..b581f268 100755 --- a/scripts/artifacts/WhatsApp.py +++ b/scripts/artifacts/WhatsApp.py @@ -144,7 +144,7 @@ def get_WhatsApp(files_found, report_folder, seeker, wrap_text): SELECT datetime(messages.timestamp/1000,'unixepoch') AS message_timestamp, case messages.received_timestamp - WHEN 0 THEN 'N/A' + WHEN 0 THEN '' ELSE datetime(messages.received_timestamp/1000,'unixepoch') end as received_timestamp, messages.key_remote_jid AS id, @@ -212,9 +212,13 @@ def get_WhatsApp(files_found, report_folder, seeker, wrap_text): try: cursor.execute(''' SELECT - datetime(message.timestamp/1000,'unixepoch') AS "Message Time", CASE - WHEN datetime(message.received_timestamp/1000,'unixepoch')="1970-01-01 00:00:00" THEN "N/A" + WHEN message.timestamp = 0 then '' + ELSE + datetime(message.timestamp/1000,'unixepoch') + END AS "Message Time", + CASE + WHEN message.received_timestamp = 0 then '' ELSE datetime(message.received_timestamp/1000,'unixepoch') END AS "Time Message Received", @@ -295,9 +299,13 @@ def get_WhatsApp(files_found, report_folder, seeker, wrap_text): try: cursor.execute(''' SELECT - datetime(message.timestamp/1000,'unixepoch') AS "Message Time", CASE - WHEN datetime(message.received_timestamp/1000,'unixepoch')="1970-01-01 00:00:00" THEN "N/A" + WHEN message.timestamp = 0 then '' + ELSE + datetime(message.timestamp/1000,'unixepoch') + END AS "Message Time", + CASE + WHEN message.received_timestamp = 0 then '' ELSE datetime(message.received_timestamp/1000,'unixepoch') END AS "Time Message Received", diff --git a/scripts/artifacts/downloads.py b/scripts/artifacts/downloads.py index 5d0376bf..1ebc405a 100644 --- a/scripts/artifacts/downloads.py +++ b/scripts/artifacts/downloads.py @@ -15,7 +15,9 @@ def get_downloads(files_found, report_folder, seeker, wrap_text): for file_found in files_found: file_found = str(file_found) if not os.path.basename(file_found) == 'downloads.db': # skip -journal and other files - continue + continue + else: + break db = open_sqlite_db_readonly(file_found) diff --git a/scripts/artifacts/mewe.py b/scripts/artifacts/mewe.py index 63cf141a..ba588c65 100755 --- a/scripts/artifacts/mewe.py +++ b/scripts/artifacts/mewe.py @@ -40,7 +40,7 @@ def _perform_query(cursor, query): return 0, None -def _make_reports(title, data_headers, data_list, report_folder, db_file_name): +def _make_reports(title, data_headers, data_list, report_folder, db_file_name, tl_bool): report = ArtifactHtmlReport(title) report.start_artifact_report(report_folder, title) report.add_script() @@ -49,7 +49,8 @@ def _make_reports(title, data_headers, data_list, report_folder, db_file_name): tsv(report_folder, data_headers, data_list, title, db_file_name) - timeline(report_folder, title, data_list, data_headers) + if tl_bool == True: + timeline(report_folder, title, data_list, data_headers) def _parse_xml(xml_file, xml_file_name, report_folder, title, report_name): @@ -73,7 +74,9 @@ def _parse_xml(xml_file, xml_file_name, report_folder, title, report_name): data_list.append((node.attrib['name'], value)) - _make_reports(f'{APP_NAME} - {report_name}', data_headers, data_list, report_folder, xml_file_name) + tl_bool = False + + _make_reports(f'{APP_NAME} - {report_name}', data_headers, data_list, report_folder, xml_file_name, tl_bool) def _parse_chat_messages(messages_count, rows, report_folder, db_file_name): @@ -89,7 +92,9 @@ def _parse_chat_messages(messages_count, rows, report_folder, db_file_name): row[6], row[7], row[8] if row[8] else '', row[9] ) for row in rows] - _make_reports(f'{APP_NAME} - Chat', data_headers, data_list, report_folder, db_file_name) + tl_bool = True + + _make_reports(f'{APP_NAME} - Chat', data_headers, data_list, report_folder, db_file_name, tl_bool) def _parse_app_database(db_file, db_file_name, report_folder): diff --git a/scripts/artifacts/snapchat.py b/scripts/artifacts/snapchat.py index 21b51426..64ce7b8a 100755 --- a/scripts/artifacts/snapchat.py +++ b/scripts/artifacts/snapchat.py @@ -32,15 +32,15 @@ # field indicates when the user was created FRIEND_QUERY = ''' SELECT + case addedTimestamp + when 0 then '' + else datetime(addedTimestamp/1000, 'unixepoch', 'localtime') + end, username, userId, displayName, phone, - birthday, - case addedTimestamp - when 0 then '' - else datetime(addedTimestamp/1000, 'unixepoch', 'localtime') - end + birthday FROM Friend WHERE addedTimestamp IS NOT NULL; ''' @@ -86,10 +86,10 @@ SNAP_MEDIA_QUERY = ''' SELECT + DATETIME(create_time/1000, 'unixepoch', 'localtime'), memories_snap._id, media_id, memories_entry_id, - DATETIME(create_time/1000, 'unixepoch', 'localtime'), time_zone_id, format, width, @@ -155,7 +155,7 @@ def _perform_query(cursor, query): return 0, None -def _make_reports(title, data_headers, data_list, report_folder, db_file_name): +def _make_reports(title, data_headers, data_list, report_folder, db_file_name, tl_bool): report = ArtifactHtmlReport(title) report.start_artifact_report(report_folder, title) report.add_script() @@ -163,9 +163,8 @@ def _make_reports(title, data_headers, data_list, report_folder, db_file_name): report.end_artifact_report() tsv(report_folder, data_headers, data_list, title, db_file_name) - - timeline(report_folder, title, data_list, data_headers) - + if tl_bool == True: + timeline(report_folder, title, data_list, data_headers) def _parse_feeds(feeds_count, rows, report_folder, db_file_name): logfunc(f'{feeds_count} feeds found') @@ -178,22 +177,26 @@ def _parse_feeds(feeds_count, rows, report_folder, db_file_name): data_list = [( row[0], row[1], row[2], row[3], row[4], row[5], row[6], row[7] ) for row in rows] + + tl_bool = True - _make_reports(f'{APP_NAME} - Feeds', data_headers, data_list, report_folder, db_file_name) + _make_reports(f'{APP_NAME} - Feeds', data_headers, data_list, report_folder, db_file_name, tl_bool) def _parse_friends(friends_count, rows, report_folder, db_file_name): logfunc(f'{friends_count} friends found') data_headers = ( - 'Username', 'User ID', 'Display Name', 'Phone Nr', - 'Birthday', 'Added Timestamp' + 'Added Timestamp', 'Username', 'User ID', 'Display Name', 'Phone Nr', + 'Birthday' ) data_list = [( row[0], row[1], row[2], row[3], row[4], row[5] ) for row in rows] + + tl_bool = True - _make_reports(f'{APP_NAME} - Friends', data_headers, data_list, report_folder, db_file_name) + _make_reports(f'{APP_NAME} - Friends', data_headers, data_list, report_folder, db_file_name, tl_bool) def _parse_messages(messages_count, rows, report_folder, db_file_name): @@ -208,7 +211,9 @@ def _parse_messages(messages_count, rows, report_folder, db_file_name): _get_text_from_blob(row[6], 0x2c, 0x28, row[5]) ) for row in rows] - _make_reports(f'{APP_NAME} - Messages', data_headers, data_list, report_folder, db_file_name) + tl_bool = True + + _make_reports(f'{APP_NAME} - Messages', data_headers, data_list, report_folder, db_file_name, tl_bool) def _parse_memories_entry(memories_count, rows, report_folder, db_file_name): @@ -222,7 +227,9 @@ def _parse_memories_entry(memories_count, rows, report_folder, db_file_name): row[3], _get_text_from_blob(row[4], 0x20, 0x1c) ) for row in rows] - _make_reports(f'{APP_NAME} - Memories', data_headers, data_list, report_folder, db_file_name) + tl_bool = True + + _make_reports(f'{APP_NAME} - Memories', data_headers, data_list, report_folder, db_file_name, tl_bool) def _parse_meo(meo_count, rows, report_folder, db_file_name): @@ -237,15 +244,17 @@ def _parse_meo(meo_count, rows, report_folder, db_file_name): data_list = [( row[0], row[1], _decrypt_meo_code(row[1]), row[2], row[3] ) for row in rows] + + tl_bool = False - _make_reports(f'{APP_NAME} - MEO (My Eyes Only)', data_headers, data_list, report_folder, db_file_name) + _make_reports(f'{APP_NAME} - MEO (My Eyes Only)', data_headers, data_list, report_folder, db_file_name, tl_bool) def _parse_snap_media(snap_media_count, rows, report_folder, db_file_name): logfunc(f'{snap_media_count} Snap Media found') data_headers = ( - 'ID', 'Media ID', 'Memories Entry ID', 'Create Time', 'Time Zone ID', 'Format', + 'Create Time', 'ID', 'Media ID', 'Memories Entry ID', 'Time Zone ID', 'Format', 'Width', 'Heigth', 'Duration', 'Has Overlay', 'Overlay Size', 'Overlay Info', 'Front Facing', 'Size', 'Has Location Info', 'Latitude', 'Longitude', 'Snap User Agent', 'Thumbnail Size', 'Thumbnail Info' @@ -255,8 +264,10 @@ def _parse_snap_media(snap_media_count, rows, report_folder, db_file_name): row[8], row[9], row[10], row[11], row[12], row[13], row[14], row[15], row[16], row[17], row[18], row[19] ) for row in rows] + + tl_bool = True - _make_reports(f'{APP_NAME} - Snap Media', data_headers, data_list, report_folder, db_file_name) + _make_reports(f'{APP_NAME} - Snap Media', data_headers, data_list, report_folder, db_file_name, tl_bool) def _parse_main_db(db_file, db_file_name, report_folder): @@ -334,7 +345,9 @@ def _parse_xml(xml_file, xml_file_name, report_folder, title, report_name): data_list.append((node.attrib['name'], value)) - _make_reports(f'{APP_NAME} - {report_name}', data_headers, data_list, report_folder, xml_file_name) + tl_bool = False + + _make_reports(f'{APP_NAME} - {report_name}', data_headers, data_list, report_folder, xml_file_name, tl_bool) def get_snapchat(files_found, report_folder, seeker, wrap_text):