開發紀錄
建置通過不等於網站完成:每個驗證只能證明自己的範圍
把 Astro 筆記網站的型別、lint、build、靜態輸出、內容輸出、瀏覽器操作與主觀驗收拆開,避免用一個綠色結果代表整個網站已經完成。
- 驗證
- Astro
- 靜態網站
- 開發流程
「build 過了」是一個必要的回報,但它不是「網站完成了」的同義句。
建置只能回答目前的程式能不能產生輸出。它不能替你檢查每一個公開網址是否正確、草稿是否洩漏、按鈕是否符合用途、手機閱讀順序是否舒服,也不能替站主決定這一版的視覺方向。主要判斷是:交付時要把完成拆成多層證據,每個工具只拿來支持它實際檢查到的事情。
先把「完成」拆成不同問題
一個內容網站至少同時有幾種不同的完成條件:
| 問題 | 需要什麼證據 |
|---|---|
| 程式能不能被 Astro 理解? | type check、Astro diagnostics |
| 程式風格和規則有沒有違反? | lint |
| 網站能不能產生靜態輸出? | build |
| 產出的固定頁和 metadata 是否正確? | 靜態輸出檢查 |
| 草稿、日期和文章路由是否遵守內容契約? | notes test、notes output verification |
| 使用者真的能不能操作? | 瀏覽器操作、鍵盤與錯誤路徑檢查 |
| 這一版是否符合想要的閱讀感受? | 站主的視覺和內容驗收 |
| 是否可以公開? | 明確的發布授權與 frontmatter 狀態 |
這些問題彼此有關,但沒有一個命令可以替其他問題回答。把它們全部縮成「npm run build 成功」,只是把未知藏起來。
check 先確認型別和 Astro 檔案
npm run check 使用 Astro 的檢查流程,會讀取 Content Collection、產生型別,並檢查 Astro 檔案中的診斷。
它適合回答:
- 元件 props 是否符合目前型別。
- Content Collection 的 frontmatter 是否通過 schema。
- Astro template 和 TypeScript 是否有可診斷的錯誤。
- 路由、layout 和資料讀取之間的型別是否接得起來。
它不會回答:
- 讀者是否看得懂這篇文章。
- 一個連結是否應該出現在主導覽。
- 使用者是否喜歡手機版的段落寬度。
- 一個通過型別的元件是否真的有被頁面使用。
型別檢查是內容和程式能不能對接的門檻,不是內容品質或產品方向的替代品。
lint 檢查規則,不檢查意圖
npm run lint 會執行 ESLint。它可以抓到目前設定涵蓋的程式規則,例如未使用的變數、某些語法問題或專案明確禁止的寫法。
lint 通過代表程式符合那組規則,不代表這個規則本身已經涵蓋所有可用性問題。例如一個按鈕可以完全通過 lint,卻可能放錯位置;一段文案也可能語法正確,卻把草稿描述成已完成的功能。
因此 lint 的結果應該照實回報為「規則檢查通過」,不要延伸成「功能正確」或「使用體驗完成」。
build 檢查能不能產生網站
Astro build 會依目前的 routes、Content Collection 和元件產生靜態檔案。它能確認建置流程走得完,也能在路由或內容資料不合法時讓錯誤浮出來。
但 build 的範圍仍然有限:
- 它不會替沒有被引用的元件建立使用證據。
- 它不會替站主檢查動畫節奏。
- 它不會自動判斷 sitemap 是否列了不該公開的網址。
- 它不會證明所有互動都在鍵盤和錯誤狀態下可用。
- 它不會證明正式部署主機的 rewrite、404 或快取行為。
所以 build 是輸出管線的必要門檻,不是整個網站的驗收章。
靜態輸出檢查要讀回真正的 HTML
目前的靜態輸出檢查不是只看 build 的 exit code,而是讀取 dist/ 裡的檔案,逐一檢查固定頁、相容路由和 404。
它會確認像這些條件:
- 每個固定頁有正確的
lang。 - 頁面有且只有一個
h1。 - canonical、description、Open Graph metadata 和 hreflang 存在於預期頁面。
- 正式頁不是空的 SPA shell,也沒有意外的 hydrated framework 標記。
- 舊
/work路由保留可讀入口,但 canonical 指向/about/work。 - 404 是 noindex,沒有把自己宣告成首頁。
- HTML 和 CSS 引用的本地資源真的存在。
這些檢查把「原始元件看起來合理」提升成「建置後文件符合契約」。它仍然不是瀏覽器驗收,但至少檢查的是讀者真正收到的檔案。
筆記輸出檢查要看公開集合
文章系統還有另一組問題:哪些文章可以進入正式輸出,哪些只能留在預覽。
目前的筆記輸出檢查會讀取所有 Markdown,依 schema 解析 frontmatter,再計算正式文章集合。它會確認:
- 已發布文章有自己的正式頁面。
- 已發布文章的 canonical 和 sitemap 連結存在。
- 草稿、沒有發布日期或尚未到日期的文章,不會出現在正式 HTML、sitemap 或首頁卡片。
- 英文和日文沒有文章時,列表和首頁維持真實空狀態。
- 首頁顯示的文章和正式列表使用同一組發布資料。
這組檢查和一般 build 不同。build 可能成功產生網站,但只有讀回文章資料和 dist/,才能確認內容狀態沒有穿過正式邊界。
瀏覽器和主觀驗收仍然要保留
靜態檔案正確,不代表瀏覽器裡每一個操作都完成。還要實際檢查:
- 語言切換是否真的連到對應頁面。
- 文章目錄和頁內錨點是否能使用。
- 頭像 dialog 能否用 Escape 關閉,焦點是否回到觸發按鈕。
- 背景動畫在隱藏分頁、reduced-motion 和離頁時是否依規則停止或清理。
- JavaScript 失效時,文章、作品和主要連結是否仍然可讀。
- 手機版的閱讀順序、按鈕換行、表格和長標題是否需要調整。
其中一部分可以用瀏覽器工具協助檢查,另一部分仍然需要站主親自看。尤其是「這個順序對不對」、「這個留白舒服嗎」、「這個視覺焦點是否搶錯位置」,不是 build 能代替的判斷。
發布又是另一個決定
即使內容已經通過工程檢查,也不等於文章獲准公開。草稿仍然要保留:
publishedAt: ''
draft: true
只有在文章內容、公開範圍和視覺閱讀都確認後,才把它改成真實的發布日期並設為正式狀態。這裡的「已經寫完」、「已經接進網站」、「已經通過工程檢查」和「可以發布」是四個不同事件。
如果交付說明只寫「全部完成」,讀者和合作夥伴就無法知道還有哪些事情需要人判斷。比較可靠的回報方式是把下面幾層分開:
已修改:哪些內容和程式真的變了
已驗證:哪些命令和產物檢查通過
待驗收:哪些視覺、互動或內容判斷還需要人看
未發布:目前是否仍是草稿,是否尚未授權公開
每種結果都要使用正確的語氣
可以說:
- 「
npm run check沒有診斷錯誤。」 - 「靜態輸出檢查確認固定頁有 canonical 和實際 HTML。」
- 「筆記輸出檢查確認草稿沒有洩漏到正式輸出。」
- 「文章仍保留草稿狀態,尚未取得發布授權。」
不能從這些結果直接說:
- 「所以使用者一定會喜歡。」
- 「所以所有裝置都沒有問題。」
- 「所以 SEO 一定會變好。」
- 「所以正式部署一定和本機一樣。」
這不是刻意保守,而是讓結論的強度和證據的範圍相等。工具已經做了很多事,但沒有做的事也要留在報告裡。
建立自己的完成清單
如果一個任務同時改到頁面、內容和互動,可以用下面的順序整理:
- 先確認資料和需求邊界。
- 跑 type check 和 lint,處理程式層問題。
- 跑 build,確認能產生輸出。
- 讀回正式 HTML、sitemap 和內容集合,確認公開邊界。
- 用瀏覽器操作真實連結、鍵盤和錯誤路徑。
- 由站主確認視覺、閱讀順序和公開範圍。
- 最後才決定是否把草稿改成正式發布。
這套順序不會讓每次修改都變成很大的流程。它只是把不同風險放在適合的檢查裡,避免一次 build 通過就把所有未知一起蓋掉。
紀錄範圍
本文整理目前 Astro 靜態網站的命令、輸出檢查和內容發布邊界。它說明各層驗證能支持的結論,不宣稱效能、搜尋排名、商業成果、使用者研究或正式主機行為已經由這些命令證明。