From 9ab17138b46382de2c91da375305112f07f3f152 Mon Sep 17 00:00:00 2001 From: Brigs Date: Thu, 2 Jul 2026 12:49:08 -0400 Subject: [PATCH 1/2] HTML report: match runtime report names to artifact icons Some modules write HTML reports under runtime names that differ from the artifact metadata name the icon is registered under: chrome.py writes per-browser reports ("Chrome - Web History") while the icon is registered under "Web History", and sms.py writes "SMS & iMessage - Messages (Threaded)" vs "SMS". The sidebar icon lookup missed those names and fell back to alert-triangle, while the same artifacts looked fine in LAVA (which reads the icon from artifact metadata directly). On an exact-match miss, fall back to the longest registered artifact name that the report name starts or ends with. Per-browser Chromium reports and the threaded SMS report now show their artifact's icon; exact-name lookups are unchanged. --- scripts/report.py | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/scripts/report.py b/scripts/report.py index 5a73cb1a9..24c6332af 100644 --- a/scripts/report.py +++ b/scripts/report.py @@ -88,6 +88,17 @@ def generate_report(reportfolderbase, time_in_secs, time_hms, extraction_type, i nav_list_data += side_heading.format(section_header) side_list[section_header].append(fullpath) icon_name = icons.get(section_header, {}).get(filename, "") + if not icon_name: + # Some modules write reports under runtime names that differ from the + # artifact metadata name (e.g. chrome.py's "Chrome - Web History" vs + # "Web History", sms.py's "SMS & iMessage - ..." vs "SMS"). Fall back + # to the longest registered artifact name the report name starts or + # ends with, so those reports keep their artifact's icon. + matches = [(len(art_name), art_icon) + for art_name, art_icon in icons.get(section_header, {}).items() + if filename.endswith(art_name) or filename.startswith(art_name)] + if matches: + icon_name = max(matches)[1] if icon_name in tabler_icon_names: if icon_name in tabler_icon_correction: icon_name = tabler_icon_correction[icon_name] From 1de943e2cfe638373f648e3250a1590017b01155 Mon Sep 17 00:00:00 2001 From: Brigs Date: Thu, 2 Jul 2026 12:54:52 -0400 Subject: [PATCH 2/2] chrome.py: pass artifact_icon to per-browser LAVA tables The per-browser lava_process_artifact() calls omitted artifact_icon, so Chromium entries in the LAVA database had no icon and the viewer fell back to its default. Pass the module's metadata icon at all 17 call sites. --- scripts/artifacts/chrome.py | 51 ++++++++++++++++++++++++------------- 1 file changed, 34 insertions(+), 17 deletions(-) diff --git a/scripts/artifacts/chrome.py b/scripts/artifacts/chrome.py index c5d76076b..670f87196 100644 --- a/scripts/artifacts/chrome.py +++ b/scripts/artifacts/chrome.py @@ -359,7 +359,8 @@ def chromeWebHistory(files_found, report_folder, _seeker, wrap_text, _timezone_o category = "Chromium" module_name = "chromeWebHistory" table_name, object_columns, column_map = lava_process_artifact(category, module_name, report_name, - lava_data_headers, len(data_list)) + lava_data_headers, len(data_list), + artifact_icon=__artifacts_v2__[module_name].get("artifact_icon")) lava_insert_sqlite_data(table_name, data_list, object_columns, lava_data_headers, column_map) @@ -470,7 +471,8 @@ def chromeWebVisits(files_found, report_folder, _seeker, wrap_text, _timezone_of module_name = "chromeWebVisits" table_name, object_columns, column_map = lava_process_artifact(category, module_name, report_name, - lava_data_headers, len(data_list)) + lava_data_headers, len(data_list), + artifact_icon=__artifacts_v2__[module_name].get("artifact_icon")) lava_insert_sqlite_data(table_name, data_list, object_columns, lava_data_headers, column_map) @@ -555,7 +557,8 @@ def chromeWebSearch(files_found, report_folder, _seeker, wrap_text, _timezone_of module_name = "chromeWebSearch" table_name, object_columns, column_map = lava_process_artifact(category, module_name, report_name, - lava_data_headers, len(data_list)) + lava_data_headers, len(data_list), + artifact_icon=__artifacts_v2__[module_name].get("artifact_icon")) lava_insert_sqlite_data(table_name, data_list, object_columns, lava_data_headers, column_map) @@ -717,7 +720,8 @@ def chromeDownloads(files_found, report_folder, _seeker, _wrap_text, _timezone_o module_name = "chromeDownloads" table_name, object_columns, column_map = lava_process_artifact(category, module_name, report_name, - lava_data_headers, len(data_list)) + lava_data_headers, len(data_list), + artifact_icon=__artifacts_v2__[module_name].get("artifact_icon")) lava_insert_sqlite_data(table_name, data_list, object_columns, lava_data_headers, column_map) @@ -799,7 +803,8 @@ def chromeKeywordSearchTerms(files_found, report_folder, _seeker, wrap_text, _ti module_name = "chromeKeywordSearchTerms" table_name, object_columns, column_map = lava_process_artifact(category, module_name, report_name, - lava_data_headers, len(data_list)) + lava_data_headers, len(data_list), + artifact_icon=__artifacts_v2__[module_name].get("artifact_icon")) lava_insert_sqlite_data(table_name, data_list, object_columns, lava_data_headers, column_map) @@ -882,7 +887,8 @@ def chromeAutofillEntries(files_found, report_folder, _seeker, _wrap_text, _time # Generate LAVA output table_name, object_columns, column_map = lava_process_artifact(category, module_name, report_name, - lava_data_headers, len(data_list)) + lava_data_headers, len(data_list), + artifact_icon=__artifacts_v2__[module_name].get("artifact_icon")) lava_insert_sqlite_data(table_name, data_list, object_columns, lava_data_headers, column_map) @@ -926,7 +932,8 @@ def chromeAutofillEntries(files_found, report_folder, _seeker, _wrap_text, _time # Generate LAVA output table_name, object_columns, column_map = lava_process_artifact(category, module_name, report_name, - lava_data_headers, len(data_list)) + lava_data_headers, len(data_list), + artifact_icon=__artifacts_v2__[module_name].get("artifact_icon")) lava_insert_sqlite_data(table_name, data_list, object_columns, lava_data_headers, column_map) @@ -1024,7 +1031,8 @@ def chromeAutofillProfiles(files_found, report_folder, _seeker, _wrap_text, _tim module_name = "chromeAutofillProfiles" table_name, object_columns, column_map = lava_process_artifact(category, module_name, report_name, - lava_data_headers, len(data_list)) + lava_data_headers, len(data_list), + artifact_icon=__artifacts_v2__[module_name].get("artifact_icon")) lava_insert_sqlite_data(table_name, data_list, object_columns, lava_data_headers, column_map) @@ -1114,7 +1122,8 @@ def chromeBookmarks(files_found, report_folder, _seeker, _wrap_text, _timezone_o module_name = "chromeBookmarks" table_name, object_columns, column_map = lava_process_artifact(category, module_name, report_name, - lava_data_headers, len(data_list)) + lava_data_headers, len(data_list), + artifact_icon=__artifacts_v2__[module_name].get("artifact_icon")) lava_insert_sqlite_data(table_name, data_list, object_columns, lava_data_headers, column_map) @@ -1224,7 +1233,8 @@ def chromeCookies(files_found, report_folder, _seeker, wrap_text, _timezone_offs module_name = "chromeCookies" table_name, object_columns, column_map = lava_process_artifact(category, module_name, report_name, - lava_data_headers, len(data_list)) + lava_data_headers, len(data_list), + artifact_icon=__artifacts_v2__[module_name].get("artifact_icon")) lava_insert_sqlite_data(table_name, data_list, object_columns, lava_data_headers, column_map) @@ -1310,7 +1320,8 @@ def chromeLoginData(files_found, report_folder, _seeker, _wrap_text, _timezone_o module_name = "chromeLoginData" table_name, object_columns, column_map = lava_process_artifact(category, module_name, report_name, - lava_data_headers, len(data_list)) + lava_data_headers, len(data_list), + artifact_icon=__artifacts_v2__[module_name].get("artifact_icon")) lava_insert_sqlite_data(table_name, data_list, object_columns, lava_data_headers, column_map) @@ -1389,7 +1400,8 @@ def chromeTopSites(files_found, report_folder, _seeker, _wrap_text, _timezone_of module_name = "chromeTopSites" table_name, object_columns, column_map = lava_process_artifact(category, module_name, report_name, - lava_data_headers, len(data_list)) + lava_data_headers, len(data_list), + artifact_icon=__artifacts_v2__[module_name].get("artifact_icon")) lava_insert_sqlite_data(table_name, data_list, object_columns, lava_data_headers, column_map) @@ -1474,7 +1486,8 @@ def chromeOfflinePages(files_found, report_folder, _seeker, wrap_text, _timezone module_name = "chromeTopSites" table_name, object_columns, column_map = lava_process_artifact(category, module_name, report_name, - lava_data_headers, len(data_list)) + lava_data_headers, len(data_list), + artifact_icon=__artifacts_v2__[module_name].get("artifact_icon")) lava_insert_sqlite_data(table_name, data_list, object_columns, lava_data_headers, column_map) @@ -1557,7 +1570,8 @@ def chromeMediaHistorySessions(files_found, report_folder, _seeker, _wrap_text, module_name = "chromeMediaHistorySessions" table_name, object_columns, column_map = lava_process_artifact(category, module_name, report_name, - lava_data_headers, len(data_list)) + lava_data_headers, len(data_list), + artifact_icon=__artifacts_v2__[module_name].get("artifact_icon")) lava_insert_sqlite_data(table_name, data_list, object_columns, lava_data_headers, column_map) @@ -1643,7 +1657,8 @@ def chromeMediaHistoryPlaybacks(files_found, report_folder, _seeker, _wrap_text, module_name = "chromeMediaHistoryPlaybacks" table_name, object_columns, column_map = lava_process_artifact(category, module_name, report_name, - lava_data_headers, len(data_list)) + lava_data_headers, len(data_list), + artifact_icon=__artifacts_v2__[module_name].get("artifact_icon")) lava_insert_sqlite_data(table_name, data_list, object_columns, lava_data_headers, column_map) @@ -1719,7 +1734,8 @@ def chromeMediaHistoryOrigins(files_found, report_folder, _seeker, _wrap_text, _ module_name = "chromeMediaHistoryOrigins" table_name, object_columns, column_map = lava_process_artifact(category, module_name, report_name, - lava_data_headers, len(data_list)) + lava_data_headers, len(data_list), + artifact_icon=__artifacts_v2__[module_name].get("artifact_icon")) lava_insert_sqlite_data(table_name, data_list, object_columns, lava_data_headers, column_map) @@ -1796,7 +1812,8 @@ def chromeNetworkActionPredictor(files_found, report_folder, _seeker, _wrap_text module_name = "chromeNetworkActionPredictor" table_name, object_columns, column_map = lava_process_artifact(category, module_name, report_name, - lava_data_headers, len(data_list)) + lava_data_headers, len(data_list), + artifact_icon=__artifacts_v2__[module_name].get("artifact_icon")) lava_insert_sqlite_data(table_name, data_list, object_columns, lava_data_headers, column_map)