如何在 Next.js 中使用草稿模式預覽內容
在頁面文件與資料獲取文件中,我們討論了如何使用 getStaticProps
和 getStaticPaths
在建置時預渲染頁面(靜態生成)。
當您的頁面從無頭 CMS 獲取資料時,靜態生成非常有用。但當您在無頭 CMS 上撰寫草稿並希望立即在頁面上預覽時,這就不是理想方案。您會希望 Next.js 在請求時而非建置時渲染這些頁面,並獲取草稿內容而非已發布內容。您會希望 Next.js 僅在此特定情況下繞過靜態生成。
Next.js 的草稿模式 (Draft Mode) 功能可解決此問題。以下是使用說明。
步驟 1:建立並存取 API 路由
如果您不熟悉 Next.js API 路由,請先查看 API 路由文件。
首先建立 API 路由,可任意命名,例如 pages/api/draft.ts
在此 API 路由中,您需在回應物件上呼叫 setDraftMode
。
這將設定一個 cookie 來啟用草稿模式。後續包含此 cookie 的請求將觸發草稿模式,改變靜態生成頁面的行為(詳見後續說明)。
您可以手動測試,建立如下 API 路由並從瀏覽器手動存取:
若開啟瀏覽器開發者工具並訪問 /api/draft
,您會注意到一個 Set-Cookie
回應標頭,其中包含名為 __prerender_bypass
的 cookie。
從無頭 CMS 安全存取
實務上,您會希望從無頭 CMS 安全地 呼叫此 API 路由。具體步驟會因使用的無頭 CMS 而異,但以下是常見做法。
這些步驟假設您使用的無頭 CMS 支援設定自訂草稿網址。若不支援,您仍可使用此方法保護草稿網址,但需手動建構並存取草稿網址。
首先,您應使用您選擇的令牌生成器建立一個密鑰令牌字串。此密鑰僅您的 Next.js 應用和無頭 CMS 知曉,可防止無權存取 CMS 的人訪問草稿網址。
其次,若無頭 CMS 支援設定自訂草稿網址,請指定以下為草稿網址。此處假設您的草稿 API 路由位於 pages/api/draft.ts
。
<your-site>
應為您的部署網域<token>
應替換為您生成的密鑰令牌<path>
應為您想預覽的頁面路徑。若想預覽/posts/foo
,則應使用&slug=/posts/foo
您的無頭 CMS 可能允許在草稿網址中包含變數,使 <path>
能根據 CMS 資料動態設定,例如:&slug=/posts/{entry.fields.slug}
最後,在草稿 API 路由中:
- 檢查密鑰是否匹配及
slug
參數是否存在(若否,請求應失敗) - 呼叫
res.setDraftMode
- 然後將瀏覽器重新導向至
slug
指定的路徑(以下範例使用 307 重新導向)
若成功,瀏覽器將被重新導向至您想預覽的路徑,並帶有草稿模式 cookie。
步驟 2:更新 getStaticProps
下一步是更新 getStaticProps
以支援草稿模式。
若您請求的頁面具有 getStaticProps
且設定了 cookie(透過 res.setDraftMode
),則 getStaticProps
將在請求時(而非建置時)被呼叫。
此外,它將被呼叫並帶有一個 context
物件,其中 context.draftMode
為 true
。
我們已在草稿 API 路由中使用 res.setDraftMode
,因此 context.draftMode
將為 true
。
若您同時使用 getStaticPaths
,則 context.params
也將可用。
獲取草稿資料
您可以根據 context.draftMode
更新 getStaticProps
以獲取不同資料。
例如,您的無頭 CMS 可能有專用的草稿文章 API 端點。若是如此,您可以如下修改 API 端點網址:
就是這樣!若您從無頭 CMS 或手動存取草稿 API 路由(帶有 secret
和 slug
),現在應能看到草稿內容。若您在未發布的情況下更新草稿,也能預覽草稿。
將此設為無頭 CMS 上的草稿網址或手動存取,您應能看到草稿。
更多細節
清除草稿模式 cookie
預設情況下,草稿模式工作階段會在瀏覽器關閉時結束。
若要手動清除草稿模式 cookie,請建立一個呼叫 setDraftMode({ enable: false })
的 API 路由:
然後發送請求至 /api/disable-draft
以呼叫該 API 路由。若使用 next/link
呼叫此路由,必須傳遞 prefetch={false}
以避免在預取時意外刪除 cookie。
與 getServerSideProps
協作
草稿模式可與 getServerSideProps
協作,並作為 draftMode
鍵存在於 context
物件中。
須知:使用草稿模式時不應設定
Cache-Control
標頭,因其無法被繞過。建議改用 ISR。
與 API 路由協作
API 路由可透過請求物件存取 draftMode
。例如:
每次 next build
生成唯一值
每次執行 next build
時都會生成新的繞過 cookie 值。
這確保繞過 cookie 無法被猜測。
須知:若要在 HTTP 環境下本地測試草稿模式,您的瀏覽器需允許第三方 cookie 和本地儲存存取。