為了讓自己能隨時隨地發布文章,我決定在工房裡加一個簡易的管理後臺 /admin。
需求很明確:
- 不需要資料庫:所有的文章最終都要變成 GitHub 上的 Markdown 檔案。
- 安全性:只有我能發布,需要一個簡單的密碼驗證。
- 無縫整合:提交後,自動觸發 Cloudflare Pages 的重新建置。
我使用了 Cloudflare Pages Functions。這是一個非常輕量級的 Serverless 方案,完全免費,而且和 Pages 整合得非常好。
核心邏輯其實就是呼叫 GitHub 的 API:
// 取得最新的 commit SHA
const refRes = await fetch(`https://api.github.com/repos/${owner}/${repo}/git/refs/heads/main`);
// 建立新的 Blob (檔案內容)
const blobRes = await fetch(`https://api.github.com/repos/${owner}/${repo}/git/blobs`);
// 建立新的 Tree
const treeRes = await fetch(`https://api.github.com/repos/${owner}/${repo}/git/trees`);
// 建立新的 Commit
const commitRes = await fetch(`https://api.github.com/repos/${owner}/${repo}/git/commits`);
// 更新 Ref
const updateRes = await fetch(`https://api.github.com/repos/${owner}/${repo}/git/refs/heads/main`);
聽起來有點繁瑣,但寫成一個封裝好的 API 後,前端只需要傳送一個 POST 請求,帶上標題、分類和內容就可以了。
介面設計上,我保持了全站的「家床感」。沒有花俏的編輯器,就是一個純文字的 Textarea,支援 Markdown 語法。提交成功時,按鈕會短暫變成綠色,顯示「✓ 已發布」。
這種自己掌控每一個畫素和邏輯的感覺,真的很不錯。
So I could publish posts anytime, anywhere, I decided to add a simple admin backend /admin to the workshop.
The requirements were clear:
- No database needed: all posts should ultimately become Markdown files on GitHub.
- Security: only I can publish, so a simple password authentication is required.
- Seamless integration: after submission, automatically trigger a rebuild of Cloudflare Pages.
I used Cloudflare Pages Functions. It's a very lightweight Serverless solution, completely free, and integrates very well with Pages.
The core logic is basically calling the GitHub API:
// 取得最新的 commit SHA
const refRes = await fetch(`https://api.github.com/repos/${owner}/${repo}/git/refs/heads/main`);
// 建立新的 Blob (檔案內容)
const blobRes = await fetch(`https://api.github.com/repos/${owner}/${repo}/git/blobs`);
// 建立新的 Tree
const treeRes = await fetch(`https://api.github.com/repos/${owner}/${repo}/git/trees`);
// 建立新的 Commit
const commitRes = await fetch(`https://api.github.com/repos/${owner}/${repo}/git/commits`);
// 更新 Ref
const updateRes = await fetch(`https://api.github.com/repos/${owner}/${repo}/git/refs/heads/main`);
It sounds a bit tedious, but once packaged into a simple API, the frontend only needs to send a POST request with the title, category, and content.
For the interface design, I kept the site's "homely" feel. No fancy editor — just a plain text Textarea that supports Markdown. When a submission succeeds, the button briefly turns green and shows "✓ Published".
That feeling of controlling every pixel and piece of logic myself is really nice.