我原本以為這次 Trackly 記帳提示詞優化已經接近收尾。

前面用 Qwen3.5-122B-A10B-5bit 跑完一輪圖片記帳驗收後,主要工作看起來只是清理錯例:哪些是真的 prompt/model failure,哪些是測試資料庫裡的 gold 本身錯。後面確實整理出了幾筆有價值的 case,但真正值得寫下來的不是某一張很糟糕的 UI,而是更早暴露的一個基礎問題:VLM 收到圖片,不代表它會主動把圖片當作主要證據。

問題:圖片有送進去,但模型仍像只看 OCR

這次任務的輸入其實很明確:資料庫裡有 OCR text,也有原始圖片 blob;測試腳本會把圖片轉成 JPEG,用 OpenAI-compatible 的 image_url 形式送給本地 oMLX server。從 log 看,request 裡有 request_image_count=1,也有 JPEG hash。也就是說,這不是 OCR-only 任務。

但 Qwen3.5 的第一輪行為仍然非常像只看 OCR。典型例子是 54347F52-1913-4D75-847E-1A447922E3C5:模型首輪判成 pending,理由是缺少最終實際支付金額。可是當我在後續單筆對話裡追問「你看不到圖片嗎?」同一張圖、同一段資料,它又能重新判斷出正確金額 33.7。

問題不是圖片沒有傳到,而是模型沒有把圖片當作主要判斷來源。

第一個重要觀察:VLM 不必然 visual-first

我以前對 VLM 任務有一個隱含假設:只要 messages 裡同時有 text 和 image,模型就會自然使用視覺能力。這次被打破了。

對 Qwen3.5 這類中等規模 VLM 來說,圖片更像是一個可用但不一定主動使用的證據源。如果 prompt 沒有明確建立證據優先級,它會退回最容易解析的 OCR 文字,然後沿著 OCR 的缺口做決策。OCR 裡沒有看到明確的「實付」或「合計」,它就傾向 pending;OCR 裡有一個醒目的「合計」,它就傾向停在那個文字上。

這也是為什麼單筆追問能改變答案:模型不是完全不能看圖,而是第一輪任務沒有被迫把圖像結構放到判斷流程的最前面。

錯誤方向:把 image_url 當成足夠的證據

一開始我檢查的是工程鏈路:是不是沒有把圖片送出去?是不是 oMLX server 沒收到 image_url?是不是 JPEG 轉換失敗?這些方向都必須查,因為沒有先排除 transport 問題,就不能談 prompt 問題。

但 log 反而把問題縮小了:圖片確實送了,request metadata 也有 image count、JPEG bytes、hash。真正的未知變成:模型為什麼在有圖的情況下,仍然按 OCR 文字的缺口做 pending 判斷?

這一步讓我意識到,VLM prompt 不能只描述輸入類型,還要描述證據使用順序。

有效方向:把視覺證據優先級寫清楚

後來有效的修改不是告訴模型某張圖的答案,也不是加入某家店或某個外賣平台的特化規則。真正有效的是把視覺證據的優先級寫清楚:

必須先讀圖片視覺內容,再用 OCR 輔助校對。
只有圖片和 OCR 都無法支持金額或對象時才 pending。
OCR 破碎或缺少「實付/合計」字樣時,不能直接 pending。

這幾句改變的是模型的工作順序:先看圖,再用 OCR 校對;不是先讀 OCR,再把圖片當成可選補充。對圖片記帳這種任務來說,這個順序差很多。

後續特例:UI reasoning 是第二層問題

後面又出現一筆高價值 case:879AD927-9F8A-4AA7-A595-C6608A629887。那張圖的 UI 本身非常糟糕,同一張訂單裡有主商品結算區,也有隨單購買區。正確金額是 3 + 14.9 = 17.9,但這對人類也有誤導性。