戰(zhàn):從零搭建文檔問答系統(tǒng)的完整路徑)
不開源的話光“怎么把模型塞進(jìn)自己的服務(wù)里”就是一個(gè)大坑開了源部署、微調(diào)、數(shù)據(jù)管線的活又是一套完全不同的技能樹。我身邊不少人是在這一步被勸退的要么被“AI”兩個(gè)字嚇住要么被鋪天蓋地的教程帶偏跑了個(gè)demo就以為懂工程了真上線才發(fā)現(xiàn)連日志都不知道怎么查。所以這次我干脆以自己最近從零搭建的一套文檔問答系統(tǒng)為線索把AI工程化的完整路徑拆開揉碎講一遍——從數(shù)據(jù)準(zhǔn)備、模型選型、微調(diào)決策到部署監(jiān)控、成本優(yōu)化、故障排查。這套流程不依賴某一家云廠商也不綁定某個(gè)特定的模型你在自己的電腦上、自己的服務(wù)器上都能照著走一遍。1. 決定做AI工程化之前先想清楚“工程化”和“寫腳本”的分界線在哪里1.1 我接到的第一個(gè)AI項(xiàng)目的真實(shí)起點(diǎn)事情要從一個(gè)很普通的業(yè)務(wù)需求說起公司內(nèi)部有大量產(chǎn)品文檔、技術(shù)手冊(cè)和客服問答記錄散落在不同的wiki和共享盤里每次找答案都要翻半天。老板的想法很簡單——“搞個(gè)AI問答機(jī)器人唄把文檔喂進(jìn)去讓它自己回答?!甭犉饋硐袷莻€(gè)周末就能搞定的小項(xiàng)目但真正開始動(dòng)手我才發(fā)現(xiàn)這壓根不是一個(gè)“訓(xùn)練模型”的問題而是一個(gè)系統(tǒng)性的工程問題。最直接的沖擊來自數(shù)據(jù)幾千篇文檔格式五花八門有PDF、有Word、有Markdown還有不少掃描件。每份文檔的排版、層級(jí)、術(shù)語都不同有的甚至帶頁眉頁腳和表格。我原以為“喂給AI”是個(gè)簡單動(dòng)作實(shí)際上你要先解決“怎么把文檔變成模型能理解的干凈文本”這件事。等到數(shù)據(jù)清洗完又一個(gè)問題冒出來了模型到底該用哪個(gè)用商用API還是開源模型要不要微調(diào)向量檢索該怎么做回答質(zhì)量怎么評(píng)估上線后用戶多了怎么辦這些問題沒有一個(gè)能在寫腳本的階段想到但它們恰恰是“工程化”的真正含義。1.2 工程化的核心元器件拆解數(shù)據(jù)層、訓(xùn)練層、部署層、監(jiān)控層如果讓我用一個(gè)類比來說明AI工程化和普通腳本的區(qū)別我會(huì)說寫腳本像是做一個(gè)手工零件雖然能用但只能解決當(dāng)下的一個(gè)問題工程化則是搭一條流水線要考慮原料供應(yīng)、加工流程、質(zhì)檢標(biāo)準(zhǔn)、故障檢修還要算生產(chǎn)效率。對(duì)AI系統(tǒng)來說這條流水線至少包含四個(gè)核心層缺一不可。第一層是數(shù)據(jù)層負(fù)責(zé)原料的采集、清洗、切分和版本管理。沒有這一層后面的一切都是空中樓閣。第二層是訓(xùn)練層或者更廣義地說模型層包含模型選型、微調(diào)、評(píng)測(cè)你要搞清楚“現(xiàn)成的模型夠不夠用”“要不要為特定領(lǐng)域再訓(xùn)練一步”。第三層是部署層涉及推理服務(wù)、接口封裝、資源調(diào)度和并發(fā)控制它決定系統(tǒng)能不能在真實(shí)流量下穩(wěn)定跑起來。第四層是監(jiān)控層做的是日志收集、質(zhì)量評(píng)估、效果回歸和告警沒有它你就像一個(gè)蒙著眼睛開車的人。我當(dāng)時(shí)犯的一個(gè)典型錯(cuò)誤就是一開始把注意力全放在第二層天天琢磨“該用哪個(gè)模型”結(jié)果數(shù)據(jù)沒整理、評(píng)測(cè)沒設(shè)計(jì)等到模型接進(jìn)來才發(fā)現(xiàn)連個(gè)客觀標(biāo)準(zhǔn)來判斷好壞都沒有。這是新手最容易踩的坑——你以為是模型不夠強(qiáng)其實(shí)是工程鏈路上的其他環(huán)節(jié)在拖后腿。2. 從零搭建的第一關(guān)數(shù)據(jù)收集、清洗與驗(yàn)證遠(yuǎn)比模型選型更耗時(shí)2.1 數(shù)據(jù)從哪來冷啟動(dòng)階段的三種來源和取舍對(duì)于一套從零開始的AI系統(tǒng)數(shù)據(jù)收集永遠(yuǎn)是最先要面臨的現(xiàn)實(shí)問題。我當(dāng)時(shí)面對(duì)的是三種典型來源第一是企業(yè)內(nèi)部的wiki和知識(shí)庫導(dǎo)出后是HTML或者M(jìn)arkdown格式結(jié)構(gòu)相對(duì)清晰但噪聲大夾帶著導(dǎo)航欄、廣告位和大量無關(guān)鏈接第二是歷史客服對(duì)話記錄以Excel和CSV為主口語化嚴(yán)重錯(cuò)別字多還有各種脫敏不徹底的風(fēng)險(xiǎn)第三是產(chǎn)品PDF手冊(cè)最頭疼因?yàn)樗鼈兝锎罅績?nèi)容是表格和圖片PDF解析器稍微不給力內(nèi)容就亂成一團(tuán)。面對(duì)這三種來源我的處理策略是分優(yōu)先級(jí)先處理wiki和Markdown類數(shù)據(jù)因?yàn)樗鼈冑|(zhì)量相對(duì)高能快速構(gòu)建一個(gè)可用的初始語料庫其次處理PDF手冊(cè)但OCR和版面解析要額外投入精力最后才處理客服對(duì)話記錄因?yàn)樗鼈冃枰罅康那逑春兔撁?。如果你反過來一上來就跟最臟的數(shù)據(jù)較勁大概率第一周就被干趴下了。我建議冷啟動(dòng)階段的原則是“先讓系統(tǒng)跑起來再逐步喂更多數(shù)據(jù)”別指望一次就把所有數(shù)據(jù)完美入庫。2.2 清洗腳本里的那些細(xì)節(jié)去重、去噪、格式歸一化數(shù)據(jù)清洗是這個(gè)階段最無聊但又最不能跳過的工作。我給你看幾個(gè)我實(shí)際遇到的細(xì)節(jié)你就明白它有多瑣碎文檔去重同一個(gè)文檔在不同目錄下有多個(gè)版本內(nèi)容相似但又不完全相同。我用的是MinHash近似去重先把文本分片成n-gram集合再算Jaccard相似度相似度超過0.85的文檔標(biāo)記為重復(fù)人工確認(rèn)后丟棄舊版本。這個(gè)方案對(duì)長文檔很有效但對(duì)短文本容易誤傷所以閾值要調(diào)。格式歸一化編碼統(tǒng)一轉(zhuǎn)成UTF-8換行符統(tǒng)一成\n全角半角符號(hào)統(tǒng)一標(biāo)題層級(jí)統(tǒng)一成#式Markdown。這些看似無關(guān)緊要的差異到了文本切分和向量化階段都會(huì)變成隱患。比如全角逗號(hào)和半角逗號(hào)混在一起切出來的文本塊就可能帶上莫名其妙的空字符。頁眉頁腳和導(dǎo)航噪聲從wiki導(dǎo)出的HTML里要專門寫規(guī)則去掉“相關(guān)文章”“目錄導(dǎo)航”這些區(qū)塊從PDF解析出來的內(nèi)容要去掉頁眉、頁碼和頁腳的重復(fù)文本。我一開始偷懶沒做這一步結(jié)果向量檢索時(shí)經(jīng)常命中的是“第3頁共20頁”這種垃圾片段氣得我半夜爬起來加正則。這一步給我的最大體會(huì)是清洗腳本本身不復(fù)雜復(fù)雜的是你必須對(duì)數(shù)據(jù)內(nèi)容有足夠敏感度。別急著寫自動(dòng)化先抽樣看50條原始數(shù)據(jù)摸清噪聲規(guī)律再動(dòng)手設(shè)計(jì)規(guī)則。2.3 驗(yàn)證集怎么構(gòu)建標(biāo)注一致性比想象中更關(guān)鍵清洗完數(shù)據(jù)下一步不是急著灌進(jìn)向量庫而是先構(gòu)建一套可以用來評(píng)估后續(xù)模型效果的“金標(biāo)準(zhǔn)”數(shù)據(jù)。我當(dāng)時(shí)的方法是從各個(gè)業(yè)務(wù)部門收集了200個(gè)真實(shí)問題每個(gè)問題由兩個(gè)人分別標(biāo)注標(biāo)準(zhǔn)答案和對(duì)應(yīng)的參考文檔片段然后比對(duì)標(biāo)注一致性。標(biāo)注不一致的地方去和業(yè)務(wù)方確認(rèn)最終形成一份帶標(biāo)準(zhǔn)答案的驗(yàn)證集。這個(gè)過程比想象中耗時(shí)但價(jià)值巨大。因?yàn)楹竺娌还苣闶钦{(diào)prompt、切文本塊還是換模型、做微調(diào)都要靠這套驗(yàn)證集來量化“變好了還是變壞了”。沒有驗(yàn)證集你的所有優(yōu)化都是憑感覺很容易被幾個(gè)典型案例誤導(dǎo)。我后來還做了一步擴(kuò)展把驗(yàn)證集里的每個(gè)問題按類型打標(biāo)事實(shí)型、操作型、對(duì)比型、主觀型這樣評(píng)測(cè)時(shí)能看清系統(tǒng)在哪類問題上表現(xiàn)差從而倒推優(yōu)化方向。3. 模型選型與微調(diào)的真實(shí)決策過程跑通demo只是萬里長征第一步3.1 選型背后要算的三筆賬性能、成本、可控性數(shù)據(jù)備好了終于到了選模型環(huán)節(jié)。但請(qǐng)注意選模型絕不是一個(gè)單純比“誰聰明”的過程而是要算三筆賬性能、成本、可控性。性能包括理解能力、生成質(zhì)量和檢索能力成本包括訓(xùn)練成本、推理成本和人力成本可控性則包括數(shù)據(jù)隱私、本地部署可行性、以及你是否能對(duì)模型行為進(jìn)行干預(yù)。我當(dāng)時(shí)對(duì)比了商用API和開源模型兩大路線。商用API的優(yōu)勢(shì)是開箱即用、效果優(yōu)秀尤其在國內(nèi)服務(wù)方對(duì)中文理解做得相當(dāng)好劣勢(shì)是按量計(jì)費(fèi)高頻調(diào)用時(shí)成本飆升而且數(shù)據(jù)要出內(nèi)網(wǎng)過不了信息安全這關(guān)。開源模型如Qwen系列、ChatGLM系列等優(yōu)勢(shì)是部署在自己服務(wù)器上數(shù)據(jù)不出內(nèi)網(wǎng)沒有按量計(jì)費(fèi)的壓力劣勢(shì)是對(duì)硬件資源和工程能力要求高。綜合下來我最終選了開源模型作為底座因?yàn)楹弦?guī)和成本這兩項(xiàng)權(quán)重在我們場(chǎng)景里遠(yuǎn)高于那點(diǎn)性能差距。如果你面臨同樣的選擇我建議你把決策表拉出來按每個(gè)維度的權(quán)重打分而不是被單點(diǎn)性能吸引。表1是我當(dāng)時(shí)用的簡化版比較表決策維度商用API開源模型本地部署中文理解效果優(yōu)良好取決于具體型號(hào)單次調(diào)用成本按量計(jì)費(fèi)長期偏高主要是硬件折舊和電費(fèi)數(shù)據(jù)隱私合規(guī)依賴服務(wù)商承諾數(shù)據(jù)完全本地可控二次開發(fā)自由度低只能調(diào)接口高可微調(diào)、可定制工程復(fù)雜度低高需自建服務(wù)上線速度快較慢3.2 微調(diào)的判斷標(biāo)準(zhǔn)什么時(shí)候該微調(diào)什么時(shí)候不該很多教程一上來就教你微調(diào)模型但微調(diào)絕不是默認(rèn)選項(xiàng)。我在這個(gè)項(xiàng)目里一度陷入“不微調(diào)等于不專業(yè)”的焦慮中后來做了幾輪對(duì)比實(shí)驗(yàn)才冷靜下來。判斷要不要微調(diào)我總結(jié)出三條標(biāo)準(zhǔn)模型是否在目標(biāo)領(lǐng)域頻繁出錯(cuò)、領(lǐng)域知識(shí)是否需要內(nèi)化到參數(shù)里、以及是否有足夠的高質(zhì)量標(biāo)注數(shù)據(jù)。以我的文檔問答場(chǎng)景為例我先用未微調(diào)的模型配合全文檢索測(cè)試發(fā)現(xiàn)它應(yīng)對(duì)“標(biāo)準(zhǔn)操作流程”“故障排查”這類問題效果不錯(cuò)但在“產(chǎn)品版本差異”“專有名詞解釋”上頻繁出錯(cuò)。這說明通用能力夠用缺的是特定領(lǐng)域知識(shí)。此時(shí)有兩個(gè)選擇一是基于檢索增強(qiáng)RAG把知識(shí)塞進(jìn)上下文二是微調(diào)把知識(shí)內(nèi)化進(jìn)參數(shù)。RAG的優(yōu)點(diǎn)是靈活、無需訓(xùn)練缺點(diǎn)是回答質(zhì)量依賴檢索質(zhì)量且上下文長度有限微調(diào)的優(yōu)點(diǎn)是一勞永逸缺點(diǎn)是成本高、有災(zāi)難性遺忘風(fēng)險(xiǎn)。我最終的策略是“先RAG后微調(diào)”先用檢索增強(qiáng)把絕大多數(shù)問題解決掉再針對(duì)檢索也解決不了的極小部分疑難case做微調(diào)。這種分層策略的好處是省資源、見效快、風(fēng)險(xiǎn)可控。3.3 實(shí)測(cè)對(duì)比base模型、RAG方案、微調(diào)模型的效果差異這里把實(shí)測(cè)數(shù)據(jù)放出來供參考。我用前面說過的200道驗(yàn)證題做了三類方案的對(duì)比純base模型直接問不檢索。準(zhǔn)確率只有63%而且很多回答“一本正經(jīng)地胡說八道”因?yàn)樗鼪]有外部知識(shí)來源。base模型RAG先檢索再生成。準(zhǔn)確率提升到86%尤其在事實(shí)型問題上進(jìn)步明顯。微調(diào)模型RAG在檢索基礎(chǔ)上進(jìn)一步微調(diào)準(zhǔn)確率到了91%。提升主要集中在專有名詞解釋和復(fù)雜指令跟隨上但V100級(jí)別的單卡訓(xùn)練花了兩天數(shù)據(jù)標(biāo)注花了三個(gè)星期。這個(gè)結(jié)果告訴我們對(duì)多數(shù)業(yè)務(wù)場(chǎng)景RAG帶來的收益遠(yuǎn)超微調(diào)微調(diào)更像是錦上添花。我見過不少團(tuán)隊(duì)一上來就微調(diào)結(jié)果訓(xùn)練數(shù)據(jù)質(zhì)量不行微調(diào)后的模型反而變笨了。所以我的建議是先用最輕量的方案把系統(tǒng)跑起來用數(shù)據(jù)說話再?zèng)Q定是否投入更大的訓(xùn)練成本。4. 部署上線的工程細(xì)節(jié)推理服務(wù)、評(píng)估回放與模型版本管理4.1 推理服務(wù)三個(gè)容易忽略的細(xì)節(jié)顯存管理、動(dòng)態(tài)批處理、超時(shí)重試模型選好、效果驗(yàn)證通過之后真正的工程挑戰(zhàn)才剛開始。部署推理服務(wù)時(shí)有三個(gè)細(xì)節(jié)最容易被忽略我一個(gè)個(gè)說。第一個(gè)是顯存管理。很多人以為只要模型能加載進(jìn)顯存就算完實(shí)際上還要考慮推理時(shí)的KV Cache和臨時(shí)張量。以ChatGLM3-6B為例FP16全精度加載權(quán)重約12GB推理時(shí)KV Cache可能再占2-4GB所以你至少需要24GB顯存的顯卡如3090/4090才能舒服地跑并發(fā)。我一開始用T4的16GB顯存硬扛結(jié)果一上并發(fā)就OOM才明白要預(yù)留buffer。實(shí)踐上我建議把單卡并發(fā)數(shù)控制在8左右不要為了省成本硬壓并發(fā)顯存溢出導(dǎo)致的服務(wù)抖動(dòng)代價(jià)更大。第二個(gè)是動(dòng)態(tài)批處理。推理框架如vLLM支持把多個(gè)請(qǐng)求拼成一個(gè)batch并行計(jì)算吞吐量能提升好幾倍。但動(dòng)態(tài)批處理不是免費(fèi)午餐它會(huì)犧牲單請(qǐng)求延遲。我在實(shí)際壓測(cè)中發(fā)現(xiàn)batch size從1升到16總吞吐能提升6倍但單次響應(yīng)時(shí)間會(huì)從800ms上升到2000ms。所以你要根據(jù)業(yè)務(wù)的延遲要求反推并發(fā)上限而不是一味追求吞吐。第三個(gè)是超時(shí)與重試。LLM推理天然存在不確定性同一個(gè)問題有時(shí)2秒返回有時(shí)要20秒。所以接口超時(shí)不能設(shè)太短我設(shè)為30秒同時(shí)要做客戶端重試機(jī)制但要加退避策略不然模型卡住的時(shí)候所有請(qǐng)求都重試直接把服務(wù)打掛。這些細(xì)節(jié)不在生產(chǎn)環(huán)境被虐幾次很難提前想到。4.2 沒有評(píng)估回放機(jī)制你根本不知道新模型是變好還是變壞這是我認(rèn)為整個(gè)AI工程化里最重要、但最容易被忽視的環(huán)節(jié)。所謂“評(píng)估回放”就是把歷史線上請(qǐng)求存下來當(dāng)模型更新或參數(shù)調(diào)整時(shí)用同一批歷史請(qǐng)求重新跑一遍自動(dòng)對(duì)比新舊版本的輸出質(zhì)量。沒有這個(gè)機(jī)制你換模型只能靠肉眼抽查換了也不知道是變好了還是變壞了。我實(shí)現(xiàn)評(píng)估回放的方式很樸素線上每次請(qǐng)求的輸入、輸出、檢索的文檔片段、用戶反饋都存日志每周抽一批代表性請(qǐng)求組成回歸集模型版本更新時(shí)自動(dòng)跑一遍回歸集按規(guī)則評(píng)分。評(píng)分有兩層一層是機(jī)器評(píng)分用規(guī)則檢查和內(nèi)置評(píng)判模型打分另一層是人工抽驗(yàn)挑出分?jǐn)?shù)波動(dòng)最大的case來看。這套機(jī)制上線后我們避開了一次嚴(yán)重的“升級(jí)事故”——新模型在基準(zhǔn)測(cè)試上分?jǐn)?shù)更高但實(shí)際在特定類型問題上全面退化靠回放及時(shí)發(fā)現(xiàn)并回滾了版本。從此我堅(jiān)信沒有評(píng)估回放的模型迭代就是耍流氓。4.3 模型版本管理和回滾比代碼回滾更需要設(shè)計(jì)傳統(tǒng)軟件都有版本管理但模型版本管理更麻煩因?yàn)槟P臀募?dòng)輒幾個(gè)GB而且一個(gè)線上服務(wù)可能在同時(shí)服務(wù)多個(gè)版本。我的做法是把模型服務(wù)分為“預(yù)發(fā)”和“生產(chǎn)”兩套模型文件放在對(duì)象存儲(chǔ)里通過帶版本的路徑引用。更新流程是新模型先在預(yù)發(fā)跑評(píng)估回放通過后再切生產(chǎn)切的時(shí)候用負(fù)載均衡按10%灰度引流觀察幾個(gè)小時(shí)后全量。一旦線上發(fā)現(xiàn)問題回滾操作就是改一個(gè)配置指針把流量切回到上一個(gè)版本整個(gè)操作一分鐘之內(nèi)完成。這個(gè)設(shè)計(jì)讓我在后續(xù)幾次模型迭代中都能大膽試錯(cuò)因?yàn)槲抑雷畈钜材芸焖倩赝恕H绻麤]有這套機(jī)制你一定會(huì)在“要不要升級(jí)”這件事上變得畏手畏腳最后反而讓系統(tǒng)停滯在舊版本上。5. 成本、延遲與穩(wěn)定性的三角博弈我的實(shí)測(cè)數(shù)據(jù)與調(diào)優(yōu)記錄5.1 成本拆解訓(xùn)練、推理、存儲(chǔ)分別花在哪AI系統(tǒng)的成本和傳統(tǒng)服務(wù)完全不同它不是均勻分布在每臺(tái)服務(wù)器上而是集中在三個(gè)大頭訓(xùn)練成本、推理成本、存儲(chǔ)成本。訓(xùn)練成本是一次性的包括GPU租用或折舊、數(shù)據(jù)標(biāo)注人力、實(shí)驗(yàn)試錯(cuò)消耗推理成本是長期的跟著線上流量走模型越大、并發(fā)越高這一項(xiàng)越驚人存儲(chǔ)成本則來自向量庫、日志和模型版本增長雖然慢但容易被忽視。我這套文檔問答系統(tǒng)的成本結(jié)構(gòu)大致是這樣訓(xùn)練階段用了一張V100租用加上標(biāo)注人力約一周時(shí)間折算下來約2000元推理階段部署了一臺(tái)雙卡服務(wù)器電費(fèi)加折舊每月約1500元存儲(chǔ)方面向量庫和日志每月幾百元。整體算下來比商用API在中等規(guī)模調(diào)用下每月約5000元略低但如果流量翻十倍本地推理的成本優(yōu)勢(shì)會(huì)更明顯。這也解釋了為什么很多AI應(yīng)用在驗(yàn)證階段用API規(guī)?;蠓炊D(zhuǎn)向自部署。5.2 延遲優(yōu)化三板斧量化、緩存、路由策略用戶對(duì)問答系統(tǒng)的延遲感知是很敏感的超過3秒就會(huì)覺得“卡”。我把延遲優(yōu)化歸納成三板斧親測(cè)都有效。第一板斧是量化。FP16轉(zhuǎn)INT8能讓模型體積縮小一半推理速度提升30%-50%而效果損失在可接受范圍內(nèi)我實(shí)測(cè)準(zhǔn)確率下降不到2%。如果你用的是支持AWQ或GPTQ的模型建議直接跑量化版本性價(jià)比極高。第二板斧是緩存。高頻問題如“密碼忘了怎么辦”“如何申請(qǐng)權(quán)限”命中緩存后可以直接返回這一招能把有效QPS需求砍掉40%以上。但要注意緩存必須設(shè)置過期時(shí)間和基于語義的相似度匹配不然用戶換了種問法就命中不了。第三板斧是路由策略。簡單問題走小模型或規(guī)則引擎復(fù)雜問題才走大模型在大模型之前加一個(gè)意圖分類器能明顯降低平均響應(yīng)時(shí)間。我實(shí)測(cè)三類請(qǐng)求全走大模型時(shí)平均延遲2600ms路由分流后降到1100ms體驗(yàn)提升非常明顯。5.3 穩(wěn)定性建設(shè)限流、熔斷與降級(jí)方案穩(wěn)定性的重要程度是在你第一次線上事故后才真正理解的。我遇到的是典型的“熱點(diǎn)問題雪崩”一個(gè)內(nèi)部公告引發(fā)大量員工同時(shí)提問同一個(gè)問題結(jié)果模型服務(wù)被打滿請(qǐng)求排隊(duì)時(shí)間飆升最后整個(gè)系統(tǒng)陷入死鎖。事后我補(bǔ)了三道防線這也是我認(rèn)為AI服務(wù)必備的穩(wěn)定性組合拳。第一道是限流在網(wǎng)關(guān)層按用戶維度設(shè)置單機(jī)QPS上限超出部分直接返回排隊(duì)提示而不是讓請(qǐng)求繼續(xù)往后打。第二道是熔斷當(dāng)模型服務(wù)的錯(cuò)誤率超過閾值我設(shè)的10%或平均延遲超過5秒時(shí)熔斷器自動(dòng)打開后續(xù)請(qǐng)求快速失敗不再打到模型上給它時(shí)間恢復(fù)。第三道是降級(jí)熔斷期間自動(dòng)切換到規(guī)則引擎版本比如從向量庫直接返回相關(guān)性最高的文檔摘要保證用戶至少能拿到部分信息而不是完全不可用。這三道防線讓系統(tǒng)在最壞情況下也能“優(yōu)雅失敗”而不是全線崩潰。6. 一次pipeline偶發(fā)返回離譜答案的根因定位排查鏈路與方法6.1 現(xiàn)象特定類型問題開始頻繁“答非所問”在某次模型版本升級(jí)后系統(tǒng)整體準(zhǔn)確率沒有明顯變化但“版本對(duì)比類”問題開始頻繁出現(xiàn)離譜答案——比如用戶問“V2.1和V2.0有什么區(qū)別”系統(tǒng)卻回答“V2.1沒有這個(gè)功能”。這類case在驗(yàn)證集上也有但比例不大一開始我沒太在意直到業(yè)務(wù)方專門來投訴才意識(shí)到問題嚴(yán)重了。我起初懷疑是模型變了因?yàn)閯偤檬悄P蜕?jí)后出現(xiàn)的。于是先做了評(píng)估回放把新舊模型在同樣輸入下的輸出拉出來對(duì)比結(jié)果發(fā)現(xiàn)同一個(gè)問題的檢索結(jié)果變了舊模型能檢索到正確的文檔片段新模型卻檢索到另一篇完全不相關(guān)的文檔。這立刻把矛頭指向了檢索環(huán)節(jié)而不是生成環(huán)節(jié)。6.2 順著數(shù)據(jù)鏈路排查檢索源變更、切塊策略、向量偏差定位到檢索環(huán)節(jié)后我開始逐步排查。第一個(gè)懷疑點(diǎn)是索引數(shù)據(jù)源是不是索引更新任務(wù)出了問題導(dǎo)致部分新文檔沒被寫入向量庫查了任務(wù)日志發(fā)現(xiàn)索引更新正常但文檔庫里的確有部分文檔的內(nèi)容和源文件對(duì)不上——原來是清洗腳本在處理某種特定表格格式時(shí)把表格的行列順序打亂了導(dǎo)致語義變化。第二個(gè)懷疑點(diǎn)是文本切塊策略。版本對(duì)比類文檔通常用表格描述差異而我的切塊策略是按Markdown標(biāo)題切分一個(gè)表格被硬切成多塊單塊語義不完整檢索時(shí)就失去了關(guān)鍵信息。這是很多RAG系統(tǒng)的通病切塊不是按“語義完整”來切而是按“結(jié)構(gòu)整齊”來切。第三個(gè)懷疑點(diǎn)是向量檢索的相似度閾值。我檢查后發(fā)現(xiàn)由于切塊不完整相關(guān)文檔片段的向量相似度被拉低部分相關(guān)片段被閾值過濾掉了剩下的不相關(guān)片段反而被召回。6.3 根因確認(rèn)與修復(fù)一個(gè)清洗規(guī)則引發(fā)的連鎖反應(yīng)順藤摸瓜最終確認(rèn)了根因鏈條清洗腳本里我沒料到一個(gè)“表格識(shí)別”函數(shù)在特定目錄下的PDF中會(huì)把兩列內(nèi)容的順序顛倒導(dǎo)致生成的產(chǎn)品對(duì)比信息文本里“新版本”和“舊版本”的指代被互換。這種語義翻轉(zhuǎn)在單看文本時(shí)幾乎察覺不出來但一旦和檢索、生成聯(lián)動(dòng)系統(tǒng)就會(huì)一本正經(jīng)地給出完全相反的答案。修復(fù)分兩步。第一步是修正清洗腳本針對(duì)這類表格增加行列校驗(yàn)邏輯同時(shí)加入一條“自檢規(guī)則”凡是解析出的文本中包含“V2.0”“V2.1”這類版本號(hào)且同時(shí)出現(xiàn)在同一段自動(dòng)標(biāo)記為人工復(fù)核候選。第二步是調(diào)整切塊邏輯改用滑動(dòng)窗口加標(biāo)題分割的混合策略讓表格內(nèi)容盡可能完整保留在同一個(gè)塊內(nèi)避免語義被切斷。修復(fù)后版本對(duì)比類問題的檢索準(zhǔn)確率從71%回升到94%。6.4 這次故障給我留下的排查方法論先數(shù)據(jù)后模型先鏈路后節(jié)點(diǎn)回頭復(fù)盤這次故障之所以難查是因?yàn)楸硐笤凇吧伞备磪s在“數(shù)據(jù)清洗”跨越了整條流水線的好幾個(gè)環(huán)節(jié)。我事后總結(jié)出一套排查順序之后遇到類似問題基本都按這個(gè)思路走先查數(shù)據(jù)層清洗、切塊、索引有沒有問題再查檢索層召回質(zhì)量、排序閾值最后才查模型層生成有沒有跑偏。這個(gè)順序和大多數(shù)人的直覺相反但在我接觸的案例里絕大多數(shù)“模型變笨了”的問題根因都在數(shù)據(jù)鏈路。具體做法上我會(huì)在排查一開始就同時(shí)拉三份日志——輸入日志、檢索結(jié)果日志、模型輸出日志——先看檢索結(jié)果是否靠譜。如果檢索結(jié)果是對(duì)的但輸出錯(cuò)的那是生成問題。如果檢索結(jié)果就是錯(cuò)的那就繼續(xù)往前查索引和切塊。用這種“從中間切開、向兩邊定位”的方式能極大縮小排查范圍而不是一頭扎進(jìn)模型參數(shù)里瞎調(diào)。寫在最后的一點(diǎn)經(jīng)驗(yàn)一路從零走下來最大的感受是做AI工程化真正考驗(yàn)人的不是那點(diǎn)模型調(diào)參的手藝而是你能不能把數(shù)據(jù)、模型、部署、監(jiān)控、成本這些環(huán)節(jié)捏合成一個(gè)整體系統(tǒng)。如果你現(xiàn)在正準(zhǔn)備開一個(gè)類似的項(xiàng)目我建議你從第一天起就按工程化的思路來先搭好數(shù)據(jù)管道和評(píng)估機(jī)制再談模型選型和效果優(yōu)化——因?yàn)樾Ч麊栴}可以迭代解決但骨架沒搭好后面每一步都會(huì)給你埋雷。最后分享一個(gè)小技巧每次對(duì)系統(tǒng)做任何改動(dòng)無論改prompt、換模型、調(diào)切塊還是改清洗規(guī)則都把修改前后的驗(yàn)證集分?jǐn)?shù)記錄在一個(gè)表格里附帶修改說明。這個(gè)習(xí)慣幫我避免了很多“改著改著變回去了”的尷尬局面也讓我在向團(tuán)隊(duì)解釋決策時(shí)有了客觀依據(jù)。AI工程化沒有銀彈但記錄和回放就是最好的防護(hù)網(wǎng)。