Physical Address
304 North Cardinal St.
Dorchester Center, MA 02124
在解決問題之道上不斷前行
實作了一個放在Vercel的爬蟲,然後定期去執行,這篇記錄一下在Vercel上實作排程(cron-job)的過程。
原本Vercel就有提供排程的作法,官方說明提到如果是低度頻率排程(例如每天),可以使用GitHub Actions,範例如下:
name: daily-cron
on:
schedule:
- cron: '0 1 * * *'
jobs:
cron:
runs-on: ubuntu-latest
steps:
- name: Call our API route
run: |
curl --request POST \
--url 'https://yoursite.com/api/cron' \
--header 'Authorization: Bearer ${{ secrets.API_SECRET_KEY }}'
GitHub Actions的作法在這邊就不提了。
其實實作概念很簡單,就是多開一個需要驗證的api,然後排時間去觸發api,進而去執行要做的事情。
但我實作完後發現怎樣排程都不會觸發,查了一下找到有個討論說明GitHub Actions的排程其實不穩定,常常會延時或不觸發,連結。因此我改用了另外的免費cron服務,這類服務其實滿多的。
補充:幾天後發現GitHub Actions的排程還是有成功運作,可能是初次觸發會需要一點時間(?,總之相較主打排程的服務,在GitHub Actions使用排程可能會有那麼一點不穩,請注意唷。
官方提供的範例如下,需注意要做驗證所以必須準備API_SECRET_KEY,這個可以寫在Vercel的環境變數(Environment Variables)裡面
export default async function handler(req, res) {
if (req.method === 'POST') {
try {
const { authorization } = req.headers;
if (authorization === `Bearer ${process.env.API_SECRET_KEY}`) {
//執行需要的事情
res.status(200).json({ success: true });
} else {
res.status(401).json({ success: false });
}
} catch (err) {
res.status(500).json({ statusCode: 500, message: err.message });
}
} else {
res.setHeader('Allow', 'POST');
res.status(405).end('Method Not Allowed');
}
}
像我使用express建置,最後用一個route接這隻api就可以。
app.post('/api/cron', async (req, res) => {
handler();
});
剛剛有提到這是低度頻率排程的作法,若是高度頻率官方建議用Upstash QStash 函式庫來實作,這部分就要再研究了XD