Mỗi khi community có chuyện — khách chốt đơn, member mới vào, ai đó hoàn thành challenge — focus.camp có thể gửi dữ liệu đó tới hệ thống của bạn: CRM, n8n/Zapier, Google Sheet, phần mềm kho… Khác với kênh Discord/Telegram (tin nhắn cho người đọc), webhook này gửi JSON cho máy đọc — đầy đủ mã đơn, email người mua, số tiền.
Chiều dữ liệu: focus.camp gửi đi. Nếu bạn cần chiều ngược lại (landing page của bạn tạo member trên focus.camp), xem Webhook tạo member.
Setup — 3 bước
- Vào
Settings → Tích hợp → Kênh thông báo→ mục 🔗 Custom webhooks → + Thêm webhook. - Dán URL nhận của hệ thống bạn (https), đặt signing secret (chuỗi bí mật bất kỳ — đưa cùng chuỗi này cho dev để verify chữ ký), chọn sự kiện muốn nghe (vd 💰 Đơn hàng).
- (Tuỳ chọn) Lọc: chỉ bắn đơn của challenge X / sản phẩm Y. Để trống = nhận tất cả. Bấm Lưu channels. Xong.
Câu hỏi thường gặp
Lọc theo challenge / sản phẩm hoạt động thế nào?
Đơn hàng trên focus.camp có 2 nguồn: đơn marketplace (mua sản phẩm) và phí tham gia challenge. Bộ lọc sản phẩm áp cho đơn marketplace; bộ lọc challenge áp cho phí tham gia challenge (và cả sự kiện check-in / hoàn thành). Hai bộ lọc độc lập, để trống bộ nào = không lọc theo chiều đó. Khoá học hiện chưa bán riêng nên chưa có loại đơn này.
Gửi trượt thì sao?
focus.camp tự gửi lại 2 lần (với lỗi mạng / lỗi 5xx phía bạn). Endpoint của bạn nên trả 200 nhanh (nhận rồi xử lý sau) để không bị tính timeout — quá 10 giây sẽ bị coi là trượt.
Ai thêm/sửa được webhook?
Owner và Admin. Mỗi webhook hiển thị nhãn 👤 người đã thêm — nên rõ trách nhiệm khi có nhiều người quản trị.
Phần kỹ thuật — đưa cho dev
Request bạn sẽ nhận
POST <URL của bạn>
Content-Type: application/json
X-Focuscamp-Event: purchase_completed
X-Focuscamp-Signature: sha256=<hex HMAC-SHA256 của raw body, key = signing secret>
{
"event": "purchase_completed",
"communityId": "cm...",
"timestamp": "2026-06-10T12:00:00.000Z",
"title": "💰 Đơn hàng mới: Khoá AI Agent",
"description": "Nguyễn Văn A · 500.000đ",
"data": {
"product": "Khoá AI Agent",
"buyer": "Nguyễn Văn A",
"buyerEmail": "a@example.com",
"amount": "500.000",
"orderId": "cm..."
},
"scope": { "productId": "cm..." }
}Với phí tham gia challenge, scope chứa challengeId thay vì productId. Các sự kiện khác (member mới, check-in, CỐT post, hoàn thành challenge) có cùng cấu trúc — khác event và data.
Verify chữ ký (Node.js)
import { createHmac, timingSafeEqual } from "crypto";
function verify(rawBody, signatureHeader, secret) {
// signatureHeader = "sha256=abc123..."
const expected = "sha256=" +
createHmac("sha256", secret).update(rawBody).digest("hex");
return timingSafeEqual(Buffer.from(expected), Buffer.from(signatureHeader));
}
// Lưu ý: tính HMAC trên RAW body (trước khi JSON.parse).Không đặt secret = không có header chữ ký — chỉ nên dùng khi endpoint của bạn đã có cách xác thực khác.
Sự kiện hiện có
purchase_completed— đơn marketplace hoặc phí tham gia challengenew_member— member mới join communitycheckin_submitted— check-in mới chờ duyệtchallenge_completed— member hoàn thành challengepost_cot— bài CỐT mới
Xem thêm: Webhook tạo member · MCP API · Hướng dẫn vận hành community
