Day 29 · W4 · 無障礙線 · 難度 ★★☆☆☆
本系列由 AI 協作撰寫。 本篇初稿與查證由作者和 Codex 協作,發布前由作者確認。完整系列協作模式見 Day 01。
Day 28 把送審的故事講到了核發。但另一份清單還在:Day 23 修完網站後,報告留下 0 個 fail、40 個 caveat。工具說「這些我判不了」,接下來呢?
今天拿其中一筆走到有答案。我沒有替那個圖示換顏色,也沒有關掉規則。補上背景之後,它已經符合這次檢查的門檻,而工具重跑,仍然留下同一句提醒。
一筆 caveat 處理完的標準,是留下足以支持結論的證據;還沒判完的,就把原因與下一步交代清楚。
9 月 13 日,0.6.0 掃自家站 30 頁,開瀏覽器渲染、不接模型:0 fail、176 info、40 caveat。這個結果與 9 月 7 日的報告相同。
我原本以為得逐項處理四十個不同的問題,拆開才發現:30 筆是每頁一次的「未設定模型」,8 筆是漸層文字對比量不到,2 筆是白色 SVG 圖示待確認。
模型那批先歸成同一件設定與覆核工作。漸層那批分布在 4 頁,每頁分別進 AA 和 AAA 規則,所以留下 8 筆;一筆又可能包住多處文字,不能把筆數當成元素數。最後兩筆,分別在方案頁和聯絡頁。
我先選方案頁。那條訊息寫著「SVG 全部 fill 為淺色(#ffffff),需人工確認與背景對比」。它已經把缺的東西講明白:白色知道了,白色背後是什麼,還不知道。
報告附了一小段 SVG。沿著它找到方案頁「需求訪談與診斷」那張卡片,是一個紫色方塊裡的白色對話圖示。旁邊有標題與說明文字,圖示本身沒有包在連結或按鈕裡。
這次只看淺色模式、1280 × 900 視窗下的預設狀態。瀏覽器讀到圖形的最終填色是白色,直接承載它的容器背景是紫色;相關元素與祖先沒有透明度折扣、濾鏡、遮罩或混色,圖示底下也沒有背景圖。那兩個顏色可以拿來算,不必猜祖先的漸層最後混成了什麼。背景也不能直接拿整張卡片的淺灰色:白色圖形的邊緣貼著的是紫色,紫色方塊才是這一次要比較的相鄰色。找錯那一層,計算公式完全正確,答案仍然會錯。

取的是瀏覽器計算後的填色與實際相鄰背景,沒有用截圖邊緣的反鋸齒像素取色。圖中數字四捨五入供閱讀,判定用完整精度。
算出來是 3.639971…,高於 3:1。這個門檻來自非文字對比:辨識元件或理解圖形所必要的視覺資訊,要和相鄰色達到足夠對比;適用範圍與取色原則見 W3C 的 1.4.11 說明。
這張卡片已經有文字把用途說清楚,圖示是否屬於必要資訊,可以另外判斷。我這次採取更直接的處理:即使以 3:1 檢查白色圖形和紫底,這個狀態也達標。因此這一筆的結論只寫「本次圖示對比已確認,無須因這條提醒改色」。沒有把它擴成整張卡片或整頁通過無障礙檢查。
接著拿同一頁渲染後的 HTML,單獨重跑那條圖示規則。結果仍然是 caveat,訊息一字沒變。
這次我知道為什麼。規則只檢查 SVG 裡寫出的填色,沒有讀進剛才那片紫底。我在旁邊完成了判斷,並不會讓原規則突然多出量背景的能力。
所以我留下兩份東西:原始掃描報告,以及一筆覆核紀錄。後者記錄網址、檢測碼、圖示位置、視窗與配色狀態、前背景色、完整對比值、判定理由、檢查日期和截圖。原始的 caveat 不改成 pass,人工補上的結論另存。
聯絡頁「輕量諮詢」那張卡片也有同一個圖形,尺寸不同。我沒有因為它長得一樣就順手勾掉,而是再開一次頁面,確認填色、背景和合成條件;這次兩邊相同,算出的對比也相同。第二筆同樣可以在這個檢查範圍內結案。
這次完成的是兩筆圖示對比覆核,不是修掉兩個網站缺陷。 網站沒有改動,兩筆原始提醒還在。若我只盯著 caveat 的總數,就會看不見剛才已經完成的工作。
圖示查完,還有兩批。我沒有把它們一起標成「已處理」。
| 這次的提醒 | 目前處理結果 | 下一步與接手工作 |
|---|---|---|
| SVG 對比 2 筆 | 預設淺色狀態的對比已確認 | 保留證據;配色或圖示改版時重驗 |
| 模型未設定 30 筆 | 未檢查,不能據此宣稱模型規則通過 | 工具維護工作:確認模型與輸入範圍,補跑後覆核輸出 |
| 漸層對比 8 筆 | 4 頁仍待量測,未給通過結論 | 網站維護工作:找齊訊息涵蓋的文字,依實際背景量測 AA/AAA |
這張表中的接手工作是分工建議,還沒有替任何人排日期或承諾已接受。要交給團隊執行時,必須填上實際負責人與重驗時機;填不出來,這份交接就還沒完成。
模型那批不能只是打開端點、看到提醒不見就結案。提醒消失,代表那個設定缺口不在了,模型判了什麼仍要看。漸層那批則要回到文字實際覆蓋的位置;報告只留下第一個片段當線索,不能只量那一處就替整頁打勾。
我也不把「目前只剩這三類」說成工具的全部邊界。這次重驗的 SVG 小測例裡,currentColor 和只有 CSS 類別的寫法仍會被直接略過。報告沒有列出來的部分,不能自動算進已確認。今天的清單處理的是這四十筆,範圍到這裡。
caveat 像一張交接單。只寫「請人工看」的時候,東西還停在櫃台;有人查過、把證據和結論補上,它才真的往前走。若查不到,就把缺哪份資料寫清楚,讓下一個人接得住。
要整理自己的報告,可以把下面存成 list_caveats.py,執行 python list_caveats.py report.json。輸入是 site --format json 的整站報告;它保留逐頁位置,供你另建覆核紀錄。
import json
import sys
with open(sys.argv[1], encoding="utf-8") as f:
report = json.load(f)
for page in report["pages"]:
for issue in page["issues"]:
if issue["status"] == "caveat":
print(json.dumps({
"url": page["url"],
"rule_id": issue["rule_id"],
"message": issue["message"],
"snippet": issue.get("snippet", ""),
}, ensure_ascii=False))
不要只用碼號去重。同一條規則在不同頁面、不同狀態,可能要不同的證據。這次兩個圖示最後得到同一答案,也是分別打開頁面以後才知道的。

原始報告有四十筆提醒,覆核紀錄有兩筆完成、三十八筆未完。兩份都保留,才能看見工具看不到的那段工作。
目前工具沒有人工結案指令,這份紀錄可以放在團隊的工作單裡。有人接手時,他應該能照記錄重做;條件改了,也能知道哪個結論已經不適用。結案只對寫明的範圍有效,不能替下一次改版預先保證。
Day 01 說自評的二十題都有可執行的規則,後面二十多天慢慢拆出那句話的範圍:規則存在、真的執行、取得足夠證據、最後判對,是四件事。把檔案寫出來,只完成了其中一件。
這三十天的案例可以收尾,網站的所有檢查卻不能因此被寫成完成。送審的結果、工具的輸出、這次補上的圖示覆核,以及還沒補齊的證據,各自都有自己的紀錄。我能交代哪些已經成立,也能指出哪些還沒有。
今天沒有把四十變成零。我把其中兩筆變成有證據的答案,把另外三十八筆留成說得清楚的未完事項。 剩下的工作不需要再開一篇心得才能成立,它需要接手者、量測與重驗。
這是這個案例最後要留下的做法:查到哪裡,就把結果交到哪裡。工具說不知道之後,故事可以結束,責任仍然有地方可查。
明天 Day 30:三十天前答應的四樣東西,今天逐項對帳。