ドキュメント
始め方
登録から、
1. 登録
https://app.webhookadmin.com/signup で、
最初の
2. プロジェクト
送る
| 環境 | API キー | 送信数 |
|---|---|---|
| 本番 | sk_live_… | 月の |
| テスト | sk_test_… | 数えない |
3. API キー
管理画面の
| 権限 | できる |
|---|---|
messages:send | メッセージの |
messages:retry | 送信の |
logs:read | 配信記録・顧客・送信先の |
endpoints:write | 送信先の |
consumers:write | 顧客の |
有効期限は
このWEBHOOK_ADMIN_API_KEY に
export WEBHOOK_ADMIN_API_KEY=sk_test_…4. 顧客と送信先
顧客はexternal_id には、
curl https://api.webhookadmin.com/v1/consumers \
-H "Authorization: Bearer $WEBHOOK_ADMIN_API_KEY" \
-H "Content-Type: application/json" \
-d '{ "external_id": "cus_1024", "name": "株式会社サンプル" }'const res = await fetch('https://api.webhookadmin.com/v1/consumers', {
method: 'POST',
headers: {
Authorization: `Bearer ${process.env.WEBHOOK_ADMIN_API_KEY}`,
'Content-Type': 'application/json',
},
body: JSON.stringify({ external_id: 'cus_1024', name: '株式会社サンプル' }),
});
const consumer = await res.json(); // { id: 'con_…', external_id: 'cus_1024', … }顧客のid をsecretwhsec_ で
curl https://api.webhookadmin.com/v1/endpoints \
-H "Authorization: Bearer $WEBHOOK_ADMIN_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"consumer_id": "con_…",
"url": "https://example.com/webhooks",
"event_types": ["invoice.paid"]
}'const res = await fetch('https://api.webhookadmin.com/v1/endpoints', {
method: 'POST',
headers: {
Authorization: `Bearer ${process.env.WEBHOOK_ADMIN_API_KEY}`,
'Content-Type': 'application/json',
},
body: JSON.stringify({
consumer_id: consumer.id,
url: 'https://example.com/webhooks',
event_types: ['invoice.paid'],
}),
});
const endpoint = await res.json(); // { id: 'ep_…', secret: 'whsec_…', … }- URL は
https、 ポートは 443 か 8443。 IP アドレスを 直接書いた URL・社内アドレスを 指す名前は 登録できません。 event_typesを省くと、 すべての イベントを 送ります。 fixed_ip: trueにすると、 固定の 送信元 IP 209.71.107.233から送ります。 受け取る 側で この IP を 許可して もらいます。
5. 送信
POST /v1/messages に、external_id・イベントの
curl https://api.webhookadmin.com/v1/messages \
-H "Authorization: Bearer $WEBHOOK_ADMIN_API_KEY" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: inv_88-paid" \
-d '{
"consumer": "cus_1024",
"event_type": "invoice.paid",
"payload": { "invoice_id": "inv_88", "amount": 128000 }
}'const res = await fetch('https://api.webhookadmin.com/v1/messages', {
method: 'POST',
headers: {
Authorization: `Bearer ${process.env.WEBHOOK_ADMIN_API_KEY}`,
'Content-Type': 'application/json',
'Idempotency-Key': 'inv_88-paid',
},
body: JSON.stringify({
consumer: 'cus_1024',
event_type: 'invoice.paid',
payload: { invoice_id: 'inv_88', amount: 128000 },
}),
});
const message = await res.json(); // { id: 'msg_…', deliveries: 1 }HTTP/1.1 202 Accepted
{ "id": "msg_…", "deliveries": 1 }Idempotency-Keyが同じ 送信は、 24 時間の あいだ 最初の idを返し、 2 通目は 作りません。 external_idの顧客が 無いときは、 その 場で 顧客を 作ります (送信先が 無いので deliveriesは0) 。 - 届いたか
どうかは、 管理画面の 「配信記録」 か GET /v1/messages/{id}で見られます。
6. 受け側で署名を検証
送信先には
npm install standardwebhooks expressimport express from 'express';
import { Webhook } from 'standardwebhooks';
const wh = new Webhook(process.env.WEBHOOK_SECRET); // whsec_…
const app = express();
// 署名は届いた本文そのもので検証するので、JSON に変換する前の本文を受け取る
app.post('/webhooks', express.raw({ type: 'application/json' }), (req, res) => {
try {
const event = wh.verify(req.body, req.headers);
console.log(event.type, event.data);
res.sendStatus(200);
} catch {
res.sendStatus(400);
}
});
app.listen(3000);WEBHOOK_SECRET には、whsec_… を