截图转举报表单,关键在人工纠错
项目使用 React、TypeScript、Supabase 和 Gemini,将诈骗截图转成结构化举报信息,降低用户填写复杂表单的门槛。文章强调模型出错后的人工审核,比演示效果更影响系统可靠性。
AI 深度解读
把一张可疑短信截图变成举报表单,难点不只是识别文字。Axon OSINT 团队用 React、TypeScript、Supabase 和 Gemini 搭建这套流程后发现,更关键的是:识别错了怎么办,谁来确认,哪些信息可以进入后续处理。
作者的核心主张是让 AI 整理材料,把判断和提交留给用户。这篇值得读的地方,是它把可编辑草稿、原始证据、人工复核和权限边界串成了一条产品流程;但它没有提供准确率或对照实验,不能据此判断方案效果有多好。
AI 读出了网址,不等于认定了诈骗
原文从一条要求支付 €2.95 重新配送的短信讲起。对担心被骗的人来说,填写事件类别、传播渠道、可疑域名和资金损失,可能比截个图困难得多。截图辅助的价值,就是先替用户整理这些材料。
但「截图里出现了 parcel-check.example」和「这个链接属于诈骗配送服务」,是两种不同的输出。前者描述可见内容,后者已经作出判断。模型可能正确读出网址,却误判发送者意图,也可能混淆号码、遗漏文字或选错分类。
作者因此把系统设计成:上传检查、Gemini 提取、结果归一化、生成可编辑草稿,随后由用户复核、补充、同意并提交。提交之后还有确认和受限处理环节。
AI 输出先成为草稿,用户确认之后才成为报告。
结构化输出方便映射到 React 表单,却不能证明内容正确。合法 JSON 只能说明格式符合预期,里面仍然可能装着错误号码。
下面是原文用于说明草稿转换规则的 TypeScript 示例,并非生产实现:
type Confidence = "high" | "medium" | "low";
type Extraction = {
confidence: Confidence;
message_text: string | null;
suggested_scenario: string;
entities: Array<{
type: string;
value: string;
}>;
};
function createEditableDraft(result: Extraction) {
return {
message: result.message_text,
scenario:
result.confidence === "low"
? "other_fraud_message"
: result.suggested_scenario,
identifiers: result.entities.map(({ type, value }) => ({
type,
value,
})),
requiresUserReview: true,
};
}
重点看 requiresUserReview: true:即使置信度为 high,也不取消复核。low 则会把分类降级为 other_fraud_message,避免把具体推断包装成可靠结论。
原文没有说明 high、medium、low 如何产生,也没有给出校准方法。因此,这些标签只能辅助呈现不确定性,不能当成正确率。
截图里的指令不能变成系统的指令
截图上传接口接受 JPEG、PNG、WebP,大小限制为 5 MB,并在分析前校验类型和体积。流程图还列了年龄检查,但没有解释具体规则。
文件通过检查,不代表图片内容可信。诈骗短信可能要求「立即访问网站验证身份」,分析系统应该提取这句话,而不是执行它。
作者在提取提示中要求 Gemini 只使用可见信息,不补造缺失值,不打开或检查链接。这里划出的边界很实用:读取一个可疑网址,与访问这个网址,应当是分别受控的能力。
不过,原文只交代了提示要求,没有展示工具权限配置或对抗测试,不能据此认定提示注入问题已经解决。
另一条边界是证据保真。界面和解释可以使用用户选择的德语、法语、乌克兰语或英语,原始消息与标识符则应保持原样。例如,原文中要求转账的 250 EUR、用户名 @payment_support_247,都不该在翻译时被改写。
原文用这两个域名说明自动纠错的风险:
trusted-service.example
trusted-servlce.example
要看的是第二行把字母 i 换成了 l。这种差异可能正是调查需要的信息。
作者提出,可以为比较生成归一化数据,但不能悄悄覆盖原始观察。对开发者而言,这要求展示解释、比较用途的数据和原始证据各有明确职责,不能拿一份「清洗后文本」包办所有用途。
用户能不能顺利提供材料,同样决定功能价值
系统提供手动填写、截图辅助、语音辅助三种入口,最终都通向草稿和报告。
截图与语音功能会在最终提交前,把选中的材料发送给 Google Gemini 提取草稿。界面需要在用户选择功能时说明这一点;不愿接受这类处理的人,可以走手动入口。
两种材料的留存方式也不同:提交的截图可以作为证据保存在受限存储中,语音录音用于生成草稿,在该流程里不作为证据录音存储。原文没有交代更完整的保存期限和删除机制,不能把这段说明扩展成全面的隐私保证。
跨设备上传则解决了一个很具体的阻力:用户在电脑填表,可疑短信却在手机里。
他们让电脑显示二维码,用户扫码后从手机上传,桌面接收分析结果并继续填报。上传使用有时限的会话,界面显示剩余时间,并跟踪 creating、qr_ready、waiting_for_upload、analyzing、analyzed、expired、failed 七种状态。
这些状态不是装饰。等待上传与正在分析需要不同提示;过期或失败则需要重试和其他入口。模型再准确,用户传不上材料,功能也无法发挥作用。
多份报告命中同一域名,也不能直接下结论
隐私边界延续到了提交之后。作者强调,报告不会成为公开动态或可搜索的个人陈述库;敏感信息使用受限存储和后端访问控制,注册账号也不等于获得访问权限。
公共查询可以返回历史报告中的有限匹配信息,但不开放底层陈述和证据。三个报告提到同一域名,能够形成待检查的信号,却不能自动证明犯罪,更不能据此确定责任人。
提交状态也要分层。系统允许用户不创建完整账号就提交报告,通过邮件确认流程,帮助确认报告使用了所填地址。后端还会校验必要声明、同意信息和报告详情。
AI 草稿、用户提交的报告、已确认报告,代表不同程度的用户操作和确认。原文记录的跨事件模式处理路径,要求具备适当同意和已确认状态。但邮件确认并不证明陈述真实,也没有解决重复或误导性举报的问题。作者把后者列为仍在研究的问题。
我的判断
我认可这套方案对操作边界的划分。相比提取后直接写入正式记录,多一步可编辑草稿,会增加确认成本,却给用户留下了纠错位置。对号码、域名和支付信息这类差一个字符就可能失去价值的数据,这个取舍有理由。
但「有人复核」也不是质量保证。用户可能直接接受预填内容,漂亮的表单还可能让模型猜测显得更可信。作者尚未解决如何突出需检查字段、如何向非技术用户表达不确定性,这恰好是人工复核能否有效的关键。
这是一份有价值的工程经验分享,还不是经过对照验证的效果报告。
原文没有提供提取准确率、用户纠错率、完成率,也没有比较 Gemini 与 OCR 加规则、其他模型或纯手动表单的效果。选用 React、TypeScript、Supabase 和 Gemini,并不能证明这套组合更优。
如果材料模板固定,OCR 加确定性解析同样值得比较;如果材料跨语言、版式变化大,模型辅助更有吸引力。具体选哪种,仍要看真实样本中的错误类型和复核成本。
能拿来做什么
- 在 React 表单中把 AI 提取结果先放入可编辑草稿,允许用户核对、修改和补充,再显式提交;不要用高置信度替用户完成确认。
- 在 Node 上传接口中落实文件类型和体积检查,并明确提取服务是否具备访问链接的能力;截图中的命令性文字只作为待处理内容。
- 为原始消息、网址、号码和用户名保留原值,翻译或归一化结果另存,避免为了展示整洁而损坏后续核对依据。
- 给上传、分析、过期和失败提供明确状态与恢复入口,同时在材料发送给第三方 AI 之前说明处理方式,让手动路径真正可用。