我們常常被要求在 HTML 的 meta description 還有 Open Graph 之類的 metadata 填入一個頁面的描述,常見達成的方法大概有這三個:
- 直接沿用網站的描述
- 在 frontmatter 加一個
description
欄位,自己寫描述 - 從內文中取前幾十字的摘要做描述
方法 1 是最簡單的,不過網站描述通常與文章內容沒什麼關係,所以不太能做為頁面的描述,但如果只是要湊字數的話是可行的。
方法 2 在程式上很簡單,但是要為每個頁面寫出一段話做為描述,真的是有點麻煩的事情。
方法 3 是很多網站的做法,有些 CMS 或 SSG 都有內建這個功能。
要如何在 Astro 實作這個功能呢?
在 Astro 獲得 Markdown 檔案的 excerpt
在 Gatsbyjs,gatsby-plugin-mdx
會產出 excerpt
,就直接用這個做為描述就好。
但是如果是 Astro 的話要自己把程式寫出來,幸好有好心人已經寫出來了:銀河渡舟的 rehype-post-excerpt.ts
。
這個程式很簡單,存取 rehype 產生的 hast(表示 HTML 的抽象語法樹),取得文件的前幾十字放到 frontmatter 中。
放到 frontmatter 中的方法在 Astro 文件中有記載,只要在 file.data.astro.frontmatter
加入自己的 property 即可:
用這種方式放進去 frontmatter 的 property 有個限制。如果 markdown 檔案是放在 content collection 的話,需要經過 render()
才能得到這個 property:
因為需要 render()
才能得到 property,所以會造成 markdown 檔案 render 的次數增加,從而造成建置時間增加,所以這種動態加入的 frontmatter property 最好謹慎使用。
其實 Gatsbyjs 的 gatsby-plugin-mdx
也是使用類似的方法。它產生 excerpt 的方式是做一次 MDX compile,用在選項加入的 rehype-infer-description-meta
plugin 產生 excerpt 再回傳。
不過為什麼在用 Gatsbyjs 的時候沒有感覺到建置時間有被拖長呢?真奇怪呢。