it2023049/chat-screenshot-and-audio-to-csv-extractor

GitHub: it2023049/chat-screenshot-and-audio-to-csv-extractor

一个用于将聊天截图与音视频证据批量提取并转换为标准化 CSV 记录的数字取证工具。

Stars: 0 | Forks: 0

# KModelC-Griphia 聊天与音频转 CSV 提取器 一个 Python 工具包,用于从聊天截图、截图拼图、语音消息和通话录音中提取通讯证据,并将结果转换为标准化的 CSV 记录。 该流程支持: - Facebook Messenger 截图和截图拼图 - Viber 截图和截图拼图 - MOSS 转录后端支持的音频和视频文件 - 用于集成处理的 ZIP 压缩包输入 - 用于本地开发的文件夹输入 - 单张图片聊天提取 - 独立音频转录与说话人归属 - 截图的自动平台路由 - 递归证据发现 - 压缩包内的自动案件报告发现 - 跳过不支持、非聊天或未知图片 - 结合案件意识的发送者和接收者归属 - 按时间顺序合并聊天记录,随后追加音频行 - 每个压缩包或文件夹生成一份合并的 CSV 记录 最终的记录格式为: ``` "Time","Sender","Receiver","Message" "DD/MM/YYYY HH:MM:SS","Sender Name","Receiver Name","Message text" "","Audio Sender","Audio Receiver","Transcribed audio text" ``` ## 概述 该项目包含四个主要组件。 ### 1. 共享聊天提取工具 `chat/extractor_utils.py` 提供以下共享功能: - 案件报告解析 - 参与者提取 - 保守的参与者姓名验证 - 截图与拼图分割 - OCR 文本块解析 - 时间戳标准化 - 气泡侧边处理 - 消息清理 - 重复检测 - 发送者和接收者证据评分 - 对话级别的侧边映射验证 - CSV 生成与后处理 ### 2. 特定平台的聊天提取器 特定平台的聊天处理流程包括: - `chat/facebook_extract.py` - `chat/viber_extract.py` 每个提取器读取一张截图或拼图,生成匿名的 `LEFT`/`RIGHT` 消息行,确定固定的参与者映射,并写入最终的发送者/接收者 CSV。 ### 3. 音频转录与归属 音频处理流程包括: - `speech/audio_diarize.py` - `speech/audio_utils.py` MOSS 用于转录和匿名说话人分离。随后,受限的 Ollama 模型会利用案件报告、转录证据、文件名来源以及验证过的案件上下文,分配发送者和接收者身份。 ### 4. 批量编排 `chat/mass_extract.py` 提供集成的压缩包和文件夹处理功能。 它会: - 发现案件报告 - 安全地解压 ZIP 压缩包 - 递归扫描支持的证据 - 将聊天截图分类为 Facebook Messenger 或 Viber - 跳过不支持和非聊天的图片 - 运行匹配的聊天提取器 - 在存在音频证据时运行音频处理流程 - 按时间顺序合并带日期的聊天行 - 追加无日期的音频行 - 可选择写入 JSON 运行清单 ## 归属策略 发送者和接收者归属是在对话级别执行的,而不是为每一行独立猜测姓名。 ### 聊天归属 对于聊天截图,处理流程首先使用以下内容推导出临时的固定 `LEFT`/`RIGHT` 映射: - 平台布局 - 气泡几何形状 - 气泡颜色(如果可用) - 标题文本 - 联系人或电话证据 - 报告参与者 - 从提取的对话中获取的证据 然后,根据案件报告和从图片或拼图中提取的完整消息集,对该临时映射进行验证。 在接受 LLM 辅助的映射修正之前,会先评估确定性证据。 强证据的示例包括: - 前导说话人标签,例如 `Casey Advisor: ...` - 自我身份识别,例如 `This is Casey Advisor` - 直接称呼,例如 `Hello Jordan`、`Jordan, ...` 或 `Oh Alex` - 确切的联系人或标题证据 - 多条消息间一致的对话结构 第三方措辞将单独处理。例如: ``` I spoke with Alex. Jordan told me about the payment. ``` 这种措辞不会自动使 Alex 或 Jordan 成为当前消息的发送者或接收者。 参与者姓名只能从经过验证的人类姓名候选者中选出,这些候选者来自: - 结构化的案件报告字段 - 基于报告的保守姓名提取 - 临时侧边映射 - 消息内明确的姓名自我识别 一旦接受,该参与者配对将在该图片或拼图中保持固定。发送者和接收者通常遵循已接受的 `LEFT`/`RIGHT` 映射。 仅当存在强确定性线索(如准确的前导说话人标签或明确的自我身份识别)证明该指定参与者是发送者时,单行记录的方向才可能被反转。此修正仅限于同一已接受的两人配对。 Ollama 模型被限制在预先排序的候选映射中。不允许其捏造组织作为参与者,将多个身份合并为一个值,或逐行随意选择不相关的参与者。 当证据不足时,将保留临时的几何形状和标题映射。 ### 音频归属 对于音频证据,处理流程结合了: - MOSS 生成的匿名说话人标签 - 明确的自我身份识别 - 直接称呼 - 案件报告中的确切参与者姓名 - 文件名来源 - 验证过的案件交互图谱 - 相关的时间线和通讯阶段上下文 - 受限的 LLM 归属 - 确定性后验证 对于单人语音消息,可以通过自我身份识别或文件名来源识别出发声者。未发声的接收者则根据直接称呼、交互证据和匹配的案件阶段保守推断。 仅仅作为第三方被提及的人,不会自动被选为接收者。 在写入 CSV 之前,最终身份会被规范化。完整的或被截断的尾部括号别名将被移除。例如: ``` Alex Example (A. Example ``` 将被写入为: ``` Alex Example ``` ## 前置条件 - Python 3.10 或更高版本 - 已安装 Ollama 并在 `PATH` 中可用 - Ollama 模型,例如 `gemma3:12b` - 与所选 CPU 或 GPU 环境兼容的 PyTorch - 用于聊天提取的 EasyOCR 和 OpenCV - 用于本地音频处理的 MOSS Transcribe-Diarize 包 - 为了实现实用的视觉模型和本地 MOSS 推理,推荐使用 GPU ## 安装说明 克隆仓库并进入其根目录: ``` git clone https://github.com/it2023049/chat-screenshot-and-audio-to-csv-extractor.git cd chat-screenshot-and-audio-to-csv-extractor ``` 创建并激活虚拟环境: ``` python3 -m venv .venv source .venv/bin/activate ``` 对于 CUDA 环境,请安装与可用 CUDA 运行时兼容的 PyTorch 版本。 然后安装声明的项目依赖项: ``` python3 -m pip install --upgrade pip python3 -m pip install -r requirements.txt ``` 典型的聊天依赖项包括: ``` opencv-python-headless easyocr numpy ollama PyPDF2 ``` 典型的音频依赖项包括: ``` torch transformers accelerate soundfile requests ``` MOSS Transcribe-Diarize 包直接从其 GitHub 仓库通过 `requirements.txt` 安装。 如果由于特定环境的 PyTorch 或 CUDA 要求导致安装失败,请先安装兼容的 PyTorch 版本,然后重新运行: ``` python3 -m pip install -r requirements.txt ``` 有关确切支持的包版本和模型要求,请遵循 MOSS 项目说明。 ## Ollama 设置 拉取默认的 Ollama 模型: ``` ollama pull gemma3:12b ``` 检查模型是否可用: ``` ollama list ``` 启动 Ollama 服务器: ``` ollama serve ``` 也可以通过以下方式提供 Ollama 主机: ``` export OLLAMA_HOST=http://127.0.0.1:11434 ``` ## 依赖检查 检查主要的聊天依赖项: ``` python3 -c "import cv2, easyocr, ollama, PyPDF2, numpy; print('chat dependencies ok')" ``` 在不启动真实转录的情况下检查音频后端: ``` python3 speech/audio_diarize.py placeholder.wav \ --case-report placeholder.txt \ --check-deps ``` 依赖项检查不会处理占位符输入。 ## 项目结构 ``` chat-screenshot-and-audio-to-csv-extractor/ ├── README.md ├── LICENSE ├── requirements.txt ├── chat/ │ ├── mass_extract.py # Batch package/folder orchestrator │ ├── facebook_extract.py # Facebook Messenger extraction pipeline │ ├── viber_extract.py # Viber extraction pipeline │ └── extractor_utils.py # Shared chat helper functions └── speech/ ├── audio_diarize.py # MOSS transcription and LLM attribution pipeline └── audio_utils.py # Shared audio and identity utilities ``` 以下文件必须保持在 `chat/` 目录内: ``` mass_extract.py facebook_extract.py viber_extract.py extractor_utils.py ``` 以下文件必须保持在 `speech/` 目录内: ``` audio_diarize.py audio_utils.py ``` 使用此仓库结构,`chat/mass_extract.py` 会自动解析: ``` chat/facebook_extract.py chat/viber_extract.py chat/extractor_utils.py speech/audio_diarize.py speech/audio_utils.py ``` 因此,对于标准布局,不需要 `--facebook-script`、`--viber-script` 和 `--audio-script`。 仅当脚本存储在自定义位置时才需要使用它们。 ## 输入数据 主要的集成输入是一个 ZIP 压缩包或文件夹,包含: - PDF 或 TXT 格式的案件报告或案件概述 - 一张或多张 Facebook Messenger 或 Viber 截图 - 可选的音频或视频证据文件 ### 支持的图片扩展名 ``` .png .jpg .jpeg .webp .bmp .tif .tiff ``` ### 支持的音频和视频扩展名 ``` .mp3 .wav .m4a .aac .flac .ogg .opus .wma .mp4 .mkv .mov ``` ### 支持的案件报告扩展名 ``` .pdf .txt ``` 案件报告用于: - 识别有效的人类参与者 - 恢复别名和联系方式 - 了解角色和通讯关系 - 约束发送者和接收者归属 - 提供时间线和案件阶段背景 - 生成转录热词 - 区分积极参与者和仅被提及的第三方 ## 输出格式 所有最终合并的 CSV 记录均使用此表头: ``` "Time","Sender","Receiver","Message" ``` ### 聊天时间戳 聊天时间戳格式: ``` DD/MM/YYYY HH:MM:SS ``` 时间戳行为: - Viber 记录保留可见的单条消息时间,并添加 `:00` 作为秒数。 - Facebook Messenger 记录使用可见的截图时间作为第一行的时间。 - 当 Messenger 不显示具体的秒数时,随后的记录将获得确定性递增的秒数,以保留可见的消息顺序。 示例: ``` "Time","Sender","Receiver","Message" "12/03/2026 10:15:00","Alice Example","Bob Example","Hello Bob." "12/03/2026 10:15:01","Bob Example","Alice Example","Hi Alice." ``` ### 音频时间戳 音频行在最终合并的 CSV 中目前使用空的 `Time` 字段: ``` "","Alice Example","Bob Example","Transcribed voice-message text." ``` 独立音频输出可能会保留时间、匿名说话人标签和详细的归属元数据。 ## 快速开始 以下所有命令均假定当前工作目录为仓库根目录: ``` kmodelc-griphia-extractor/ ``` ### 推荐的压缩包模式 处理包含报告和证据的单个 ZIP 压缩包: ``` python3 chat/mass_extract.py case_name.zip ``` 编排器将: 1. 在结果目录下安全地解压 ZIP 2. 搜索最可能的 PDF 或 TXT 案件报告 3. 发现支持的截图和音频文件 4. 按平台对截图进行分类 5. 运行相应的提取器 6. 处理音频证据 7. 写入一个合并的 CSV 默认输出布局: ``` results/ ├── extracted/ └── _merged.csv ``` 除非启用了保留或调试标志,否则每个图像和音频的中间文件都是临时的。 ### 带有明确案件报告的压缩包模式 当压缩包包含多个报告候选项或报告单独存储时,请使用此模式: ``` python3 chat/mass_extract.py \ case_name.zip \ --case-report case_reports/case_report.pdf ``` ### 文件夹模式 处理已解压的压缩包或包含可发现报告的证据文件夹: ``` python3 chat/mass_extract.py case_name/ ``` ### 明确报告模式 处理已知报告以及一个或多个证据文件、文件夹、通配符路径或 ZIP 压缩包: ``` python3 chat/mass_extract.py \ case_reports/case_report.pdf \ evidence/ \ --results-dir results \ --model gemma3:12b \ --langs en \ --classify-mode auto \ --emoji-mode omit \ --audio-device cuda ``` 可以提供多个证据路径: ``` python3 chat/mass_extract.py \ case_reports/case_report.pdf \ evidence/facebook/ \ evidence/viber/ \ evidence/audio/ ``` 也可以通过 `--case-report` 提供明确的报告: ``` python3 chat/mass_extract.py \ evidence_package.zip \ --case-report case_reports/case_report.pdf ``` ## 单张图片聊天提取 ### Facebook Messenger ``` python3 chat/facebook_extract.py \ images/facebook/example_messenger_chat.png \ case_reports/case_report.pdf \ --model gemma3:12b \ --langs en \ --emoji-mode omit \ --output results/per_image/example_messenger_chat_extracted.csv \ --debug-dir results/per_image/example_messenger_chat_debug ``` ### Viber ``` python3 chat/viber_extract.py \ images/viber/example_viber_chat.png \ case_reports/case_report.pdf \ --model gemma3:12b \ --langs en \ --emoji-mode omit \ --output results/per_image/example_viber_chat_extracted.csv \ --debug-dir results/per_image/example_viber_chat_debug ``` ### 仅 OCR 聊天提取 禁用视觉模型图像输入,同时保留基于 OCR 的处理: ``` python3 chat/facebook_extract.py \ images/facebook/example_messenger_chat.png \ case_reports/case_report.pdf \ --no-vision ``` 仅 OCR 模式可能会减少 GPU 使用,但可能会降低文本和气泡边界的准确性。 ## 独立音频提取 ### 处理单个音频文件 ``` python3 speech/audio_diarize.py \ evidence/audio/example_voice_message.mp3 \ --case-report case_reports/case_report.pdf \ --output-dir results/per_audio/example_voice_message \ --backend moss-local \ --language en \ --device cuda \ --dtype bfloat16 \ --llm-backend ollama \ --ollama-model gemma3:12b ``` ### 处理音频文件夹 ``` python3 speech/audio_diarize.py \ evidence/audio/ \ --case-report case_reports/case_report.pdf \ --output-dir results/per_audio \ --backend moss-local \ --device cuda \ --llm-backend ollama \ --ollama-model gemma3:12b ``` ### 处理音频 ZIP 压缩包 ``` python3 speech/audio_diarize.py \ evidence/audio_package.zip \ --case-report case_reports/case_report.pdf \ --output-dir results/per_audio \ --backend moss-local \ --device cuda \ --llm-backend ollama \ --ollama-model gemma3:12b ``` ### 仅生成匿名说话人轮次 禁用 LLM 身份归属: ``` python3 speech/audio_diarize.py \ evidence/audio/example_call.wav \ --case-report case_reports/case_report.pdf \ --output-dir results/per_audio/example_call \ --llm-backend none ``` ### 手动说话人映射 提供一个 JSON 映射: ``` { "S01": "Alice Example", "S02": "Bob Example" } ``` 然后运行: ``` python3 speech/audio_diarize.py \ evidence/audio/example_call.wav \ --case-report case_reports/case_report.pdf \ --output-dir results/per_audio/example_call \ --speaker-map speaker_map.json ``` 有用的独立音频输出包括: ``` .moss.raw.txt .speaker_turns.txt .llm_attribution.json .diarized.csv .diarized.txt .speaker_map_template.json diarization_manifest.json ``` 使用 `--debug-json` 以保留额外的转录、prompt、案件上下文和归属产物。 ## 平台分类 `chat/mass_extract.py` 支持自动路由到正确的聊天提取器。 | 模式 | 行为 | | ---------- | ------------------------------------------------------------------------------------ | | `auto` | 首先使用文件名和路径提示,然后在需要时回退到视觉模型。 | | `filename` | 仅使用文件名和路径关键字,如 `facebook`、`messenger` 或 `viber`。 | | `vision` | 首先使用视觉模型,然后回退到文件名和路径提示。 | ### 仅文件名分类 ``` python3 chat/mass_extract.py \ case_name.zip \ --classify-mode filename ``` ### 强制 Facebook Messenger 提取 ``` python3 chat/mass_extract.py \ case_reports/case_report.pdf \ images/facebook/ \ --force-platform facebook ``` ### 强制 Viber 提取 ``` python3 chat/mass_extract.py \ case_reports/case_report.pdf \ images/viber/ \ --force-platform viber ``` 仅当所有提供的候选图片均属于所选平台时,才应使用强制分类。 ## 实用的批量标志 | 标志 | 用途 | | ---------------------------------------- | --------------------------------------------------------------------------- | | `--case-report PATH` | 覆盖自动报告发现功能。 | | `--output PATH` | 设置合并后的 CSV 路径。相对路径在 `--results-dir` 下解析。 | | `--results-dir PATH` | 设置根输出目录。 | | `--manifest PATH` | 将 JSON 运行清单写入提供的路径。 | | `--classify-mode {auto,filename,vision}` | 选择截图平台分类策略。 | | `--force-platform {auto,facebook,viber}` | 强制候选图片使用选定的平台。 | | `--model MODEL` | 设置用于聊天提取和图像分类的 Ollama 模型。 | | `--langs LANGS` | 设置 EasyOCR 语言列表。 | | `--cpu` | 强制 EasyOCR 使用 CPU 模式。 | | `--no-vision` | 禁用聊天视觉模型的图像输入,仅使用 OCR 支持。 | | `--emoji-mode omit` | 从最终聊天文本中省略表情符号。为提高可重复性推荐使用。 | | `--emoji-mode vision` | 仅保留视觉模型判断为清晰可见的表情符号。实验性功能。 | | `--debug` | 保留每个图像的调试目录。 | | `--keep-per-image` | 保留每个图像的中间 CSV 文件。 | | `--dump-ocr` | 保存 OCR 文本和定位的 OCR 文本块。 | | `--dump-draft` | 保存中间模型生成的聊天 CSV 草稿。 | | `--dump-side-map` | 保存临时和已验证的侧边映射。 | | `--keep-audio-output` | 在 `results/per_audio` 下保留独立的音频产物。 | | `--keep-duplicates` | 禁用确切的最终行去重。 | | `--facebook-script PATH` | 覆盖 `facebook_extract.py` 的路径。 | | `--viber-script PATH` | 覆盖 `viber_extract.py` 的路径。 | | `--audio-script PATH` | 覆盖 `audio_diarize.py` 的路径。 | | `--extra-extractor-arg VALUE` | 向两个聊天提取器传递附加参数。可以重复使用。 | | `--extra-audio-arg VALUE` | 向 `audio_diarize.py` 传递附加参数。可以重复使用。 | ## 实用的集成音频标志 这些标志由 `chat/mass_extract.py` 接受并转发给音频处理流程。 | 标志 | 用途 | | ----------------------------------------------- | ---------------------------------------------------------------- | | `--audio-backend {moss-local,moss-api}` | 选择本地 MOSS 模型或 HTTP 转录 endpoint。 | | `--audio-model-id MODEL` | 设置 MOSS 模型 ID 或本地模型路径。 | | `--audio-language LANG` | 设置转录语言提示。 | | `--audio-device {auto,cuda,cpu}` | 选择 MOSS 推理设备。 | | `--audio-dtype {auto,bfloat16,float16,float32}` | 选择本地 MOSS 推理 dtype。 | | `--audio-max-new-tokens N` | 设置最大 MOSS 生成长度。 | | `--audio-hotwords VALUES` | 添加逗号分隔的转录热词。 | | `--audio-max-hotwords N` | 限制生成的案件报告热词。 | | `--audio-prompt TEXT` | 覆盖基础的 MOSS 转录 prompt。 | | `--audio-api-url URL` | 使用 `moss-api` 时设置 MOSS API endpoint。 | | `--audio-api-timeout SECONDS` | 设置 MOSS API 请求超时时间。 | | `--audio-llm-backend {ollama,none}` | 启用或禁用发送者/接收者归属。 | | `--audio-ollama-model MODEL` | 覆盖用于音频归属的 Ollama 模型。 | | `--audio-ollama-host URL` | 覆盖用于音频归属的 Ollama 主机。 | | `--audio-llm-timeout SECONDS` | 设置音频归属请求超时时间。 | | `--audio-speaker-map PATH` | 提供手动说话人映射 JSON 文件。 | | `--audio-participants VALUES` | 提供可选的逗号分隔参与者约束。 | | `--audio-map-speakers-by-order` | 按首次出现顺序将说话人映射到提供的参与者。 | | `--audio-no-merge-turns` | 保持连续的匿名说话人片段独立。 | | `--audio-debug-json` | 保留原始和诊断音频 JSON 输出。 | | `--keep-audio-output` | 保留每个音频的中间文件。 | ## 拼图处理 首先尝试自动拼图分割。 当自动分割不可靠时,对于独立的聊天提取,可以使用手动布局标志。 ### 固定网格 ``` --grid 2x1 ``` 示例: ``` python3 chat/facebook_extract.py \ images/facebook/collage.png \ case_reports/case_report.pdf \ --grid 2x1 \ --output results/per_image/collage_extracted.csv \ --debug-dir results/per_image/collage_debug ``` ### 不均匀行布局 ``` --layout 2,3 ``` 示例: ``` python3 chat/facebook_extract.py \ images/facebook/collage.png \ case_reports/case_report.pdf \ --layout 2,3 \ --output results/per_image/collage_extracted.csv \ --debug-dir results/per_image/collage_debug ``` 使用 `--grid` 或 `--layout`,但不能同时使用两者。 ## 内部运行缓存 集成的批量处理流程可能会在一次运行期间创建临时的内部缓存。 ### 聊天对话状态缓存 聊天处理流程为每个平台和证据文件夹对话键存储最后接受的 `LEFT`/`RIGHT` 映射。 此映射仅用作后续看起来属于同一对话的截图的软连续性先验。 当前图像中的证据仍然具有权威性。示例包括: - 不同的可见联系人 - 明确的自我身份识别 - 精确的前导说话人标签 - 强直接称呼证据 - 与缓存映射不兼容的参与者配对 编排器传递内部参数: ``` --conversation-state-cache --conversation-key ``` 用户通常不需要手动提供这些参数。 ### 音频案件上下文缓存 音频处理流程可能会创建一个经过验证的案件上下文 JSON 图谱,包含: - 参与者 - 角色 - 别名 - 联系信息 - 交互对 - 通讯渠道 - 时间线事件 - 简明的案件摘要 该图谱在同一次批处理运行期间处理的所有音频文件中重复使用,避免重复分析案件报告。 编排器传递内部音频参数: ``` --case-context-cache ``` 这两个缓存都是内部的、运行本地的产物,不应提交到仓库中。 ## 输出保留 默认情况下,集成流程优先考虑最终合并的 CSV,并删除临时的每个项目的工作空间。 在需要详细检查时,请使用以下标志: ``` --keep-per-image --keep-audio-output --debug --dump-ocr --dump-draft --dump-side-map --audio-debug-json ``` 保留的典型输出树可能如下所示: ``` results/ ├── extracted/ ├── per_image/ │ ├── _extracted.csv │ └── _debug/ ├── per_audio/ │ ├──
标签:AI风险缓解, OCR, Python, 凭据扫描, 数字取证, 数据提取, 无后门, 系统调用监控, 自动化脚本, 语音转写, 逆向工具