Chuyển đến nội dung chính

Yêu cầu gửi tới bạn

Thân yêu cầu luôn là JSON {"type","id","timestamp","data"}, nhỏ hơn 20 KB. id bằng webhook-id; timestamp là ISO 8601 có múi giờ; số tiền là số nguyên đồng.
id và các mã định danh (transaction_id, bank_account_id) là chuỗi số dài tới 19 chữ số. Lưu và so sánh chúng dưới dạng chuỗi: đổi sang kiểu số (JavaScript, Excel) sẽ bị làm tròn thành một mã khác.

Kiểm tra chữ ký

Luôn kiểm tra chữ ký trên nội dung gốc của yêu cầu (chưa qua phân tích JSON) trước khi xử lý. Dùng thư viện Standard Webhooks có sẵn cho nhiều ngôn ngữ; thư viện cũng từ chối tin có webhook-timestamp lệch quá 5 phút so với giờ máy bạn.
Nếu không dùng thư viện: chữ ký là HMAC-SHA256, mã hoá base64, trên chuỗi webhook-id + "." + webhook-timestamp + "." + thân yêu cầu, với khoá là phần base64 giải mã sau tiền tố whsec_. So sánh theo thời gian hằng (constant-time).

Phản hồi của bạn

Hãy trả 2xx nhanh (thời gian chờ tối đa 15 giây cho mỗi lượt) và xử lý nặng ở hàng đợi của bạn. Hệ thống không giữ kết nối để dùng lại và không hiển thị nội dung bạn trả về; nhật ký chỉ cho thấy mã HTTP và loại lỗi.

Gửi lại, trùng tin và thứ tự

  • Tin được giao ít nhất một lần. Cùng một sự kiện có thể đến nhiều lần (bạn trả lỗi, hết giờ chờ, hay mạng ngắt sau khi bạn đã xử lý). Hệ thống của bạn phải khử trùng theo id (webhook-id), và với giao dịch thì theo data.transaction_id. Hãy lưu các mã đã xử lý bền vững: tin có thể được gửi lại sau nhiều ngày.
  • Không bảo đảm thứ tự. Một sự kiện đến sau có thể xảy ra trước. Dùng timestamp trong thân hay data.transacted_at để sắp xếp nếu cần.
  • Hiếm khi một sự kiện không được ghi ngay lúc xảy ra; hệ thống tự ghi bù trong một lượt đối soát (thường dưới 15 phút, tối đa khoảng hai ngày). Tin bù có timestamp là lúc sự kiện xảy ra, không phải lúc gửi, và chỉ gửi tới webhook đã có từ trước lúc đó.
  • Lịch thử lại: lần đầu ngay lập tức, rồi sau 5 giây, 5 phút, 30 phút, 2 giờ, 5 giờ, 10 giờ, 14 giờ, 20 giờ và 24 giờ (từ 5 phút trở đi cộng trừ ngẫu nhiên tới 20%). Tổng cộng 10 lượt trong khoảng 3 ngày; sau lượt thứ 10, tin chuyển sang Thất bại.
  • Trong tab Nhật ký gửi, dưới trạng thái của tin chưa gửi được có kết quả lượt gửi cuối: mã HTTP kèm ý nghĩa (“429 · Quá nhiều yêu cầu”), hoặc lý do khi máy chủ không trả lời (“Quá thời gian chờ”, “Không phân giải được tên miền”).
  • Tin thất bại không mất. Ở tab Nhật ký gửi bạn xem được nội dung tin đã gửi và từng lượt gửi (thời gian, mã HTTP hoặc loại lỗi, thời lượng). Bấm Gửi lại cho riêng một tin, hoặc Gửi lại tin thất bại cho mọi tin “Thất bại” của một webhook đang bật (trong 30 ngày gần nhất, mỗi lần tối đa 1000 tin; tin “Đã huỷ” không được gửi lại). Tin gửi lại giữ nguyên webhook-id, có webhook-timestamp mới.
  • Mỗi lần gửi lại chỉ thử một lượt: nếu lượt đó lỗi, tin trở lại Thất bại, không vào lại lịch thử lại.
  • Gửi lại tin thất bại gửi lần lượt khoảng 1 tin mỗi giây, để sự kiện mới phát sinh trong lúc đó không phải chờ sau cả đợt. Bấm thêm khi đợt trước chưa xong thì đợt sau xếp tiếp phía sau.
  • Giới hạn mỗi webhook trong một giờ: 60 lần gửi lại từng tin (tính cả Gửi lại tới, vào webhook nhận) và 5 lần Gửi lại tin thất bại (lần bấm không có tin nào để gửi thì không tính). Vượt giới hạn thì hệ thống từ chối kèm lời nhắc thử lại sau.
  • Sự kiện chỉ được tạo cho webhook đã có lúc nó xảy ra: địa chỉ mới thêm không tự nhận lại lịch sử. Tin của một webhook đã xoá vẫn gửi được bằng tay: mở tin trong Nhật ký gửi, chọn ở Gửi lại tới một webhook đang bật có nhận loại sự kiện đó, rồi bấm Gửi lại (chỉ với sự kiện trong 30 ngày gần nhất). Tin giữ nguyên webhook-id và được ký bằng khoá bí mật của webhook nhận. Tin thử không gửi sang webhook khác được, và sự kiện xảy ra lúc cửa hàng chưa có webhook nào thì không được lưu nên không gửi lại được.
  • Thời hạn lưu: chi tiết từng lượt thử giữ 30 ngày; tin, trạng thái và kết quả lượt gửi cuối giữ 90 ngày kể từ khi tin gửi xong hoặc thất bại, sau đó bị xoá và không gửi lại được nữa. Tin còn đang chờ gửi không bị xoá.

Danh sách kiểm tra khi viết bộ nhận

  1. Chỉ đăng ký địa chỉ https có chứng chỉ TLS hợp lệ (chứng chỉ tự ký bị từ chối), cổng 443 hoặc 8443.
  2. Đọc thân gốc, kiểm tra chữ ký, rồi mới phân tích JSON.
  3. Trả 2xx nhanh, xử lý nặng ở nền.
  4. Khử trùng theo webhook-id hoặc data.transaction_id, lưu bền vững.
  5. Không giả định thứ tự tin.
  6. Không ghi khoá bí mật hay nội dung content vào log; giữ khoá trong kho bí mật.
  7. Theo dõi tỉ lệ lỗi 24 giờ trên trang Webhook; sửa lỗi trước khi webhook bị tắt tự động.