Một quy trình thanh toán phía máy chủ có cơ chế thử lại và chống trùng lặp.
1. Chuẩn bị ID và quyền truy cập
Bắt đầu với cửa hàng đã bật và phương thức thanh toán đã thử. Trong Cài đặt → Truy cập API, tạo thông tin xác thực đọc/ghi giới hạn trong dự án cần dùng. Giữ token ở backend, không bao giờ đưa vào mã trình duyệt hoặc kho mã công khai.
Sao chép API ID của dự án và API ID của cửa hàng từ ô Cơ bản → API ID của cửa hàng. Đây là UUID, không phải mã định danh dự án dễ đọc hay số đơn hàng của bạn. Dùng tên máy chủ API của riêng bạn.
Trong Cửa hàng → IPN, tạo bí mật ký trước khi cung cấp ipn_url. Bộ nhận HTTPS của bạn phải truy cập được từ VPS nhà bán hàng.
2. Tạo hóa đơn
Thay các phần giữ chỗ và gửi yêu cầu này từ backend. Số tiền là chuỗi thập phân, không phải phép tính số thực dấu phẩy động.
curl --fail-with-body --request POST \
'https://api.example.com/v1/projects/YOUR_PROJECT_ID/stores/YOUR_STORE_ID/invoices' \
--header 'Authorization: Bearer YOUR_MERCHANT_API_TOKEN' \
--header 'Content-Type: application/json' \
--header 'Idempotency-Key: order-1042-attempt-1' \
--data '{
"amount": "10.00",
"currency": "EUR",
"order_id": "order-1042",
"description": "Example order",
"ipn_url": "https://shop.example.com/payments/wholly-ipn",
"metadata": {
"cart_id": "cart-1042"
}
}'Lưu data.invoice_id cùng đơn hàng, rồi chuyển hướng khách hàng đến links.checkout. Dùng khóa idempotency duy nhất cho lần thử thanh toán mới. Khi hết thời gian chờ, thử lại với cùng thông tin xác thực, khóa và chính xác các byte nội dung.
Bỏ qua payment_methods sẽ dùng các phương thức cửa hàng chấp nhận. Bạn có thể giới hạn chúng cho từng hóa đơn bằng slug chuỗi và mã tài sản; điều này không bao giờ bật tài sản chưa được chấp nhận. Tất cả trường yêu cầu và ví dụ phản hồi →
3. Chọn IPN, webhook hoặc cả hai
IPN theo vòng đời hóa đơn. Đặt URL IPN mặc định của cửa hàng hoặc ghi đè bằng ipn_url cho một hóa đơn. Webhook đăng ký một endpoint nhận các sự kiện được chọn, ví dụ invoice.settled.
Chúng dùng cùng định dạng chữ ký, nhưng bí mật khác nhau: IPN dùng bí mật IPN của cửa hàng; mỗi endpoint webhook có bí mật riêng. Không loại nào dùng bearer token API để ký.
Nếu cả hai gửi đến ứng dụng của bạn, sẽ có thông báo chồng lặp. Đừng ghi có đơn hàng hai lần.
4. Xác minh và lưu thông báo
- Đọc chính xác nội dung yêu cầu thô trước khi phân tích JSON. Xác minh
Wholly-Signaturevới bí mật tương ứng và kiểm tra dấu thời gian/chống phát lại. SDK chính thức có bộ xác minh. - Xác thực danh tính dự án, cửa hàng, hóa đơn và sự kiện trong nội dung đã ký. Các header gửi thông báo không được ký không phải nguồn xác thực.
- Lưu bền vững sự kiện với một
event_idduy nhất, rồi nhanh chóng trả HTTP 2xx. Xử lý đơn hàng bằng worker chạy nền. - Lấy hóa đơn hiện tại từ máy chủ API bạn đã cấu hình, không phải máy chủ tùy ý được cung cấp trong yêu cầu. So sánh dự án, cửa hàng, số tiền, đơn vị tiền và tham chiếu đơn hàng đã lưu.
PHP · Python · JavaScript / TypeScript · Đặc tả chữ ký và ví dụ bộ nhận
5. Thực hiện đơn hàng một lần, khi quyết toán
Với bộ nhận dựa trên sự kiện , xử lý event_type = invoice.settled, rồi xác minh status = settled hiện tại và chính sách ngoại lệ của bạn. Thực hiện đơn hàng một lần trong giao dịch cơ sở dữ liệu/ràng buộc duy nhất cho đơn hàng.
Một chuỗi hoàn tất nhanh có thể gửi cả hai payment.received và invoice.settled với status = settled. Trên chuỗi khác, payment.received vẫn có thể ghi processing. Cả hai luồng đều không phải lỗi.
Loại bỏ sự kiện trùng bằng event_id, không chỉ số thứ tự: các loại sự kiện khác nhau có thể dùng cùng số thứ tự. Thay vào đó, bộ xử lý SDK dựa trên trạng thái gộp các phiên bản hóa đơn và kiểm tra trạng thái bất kể loại sự kiện. Đừng kết hợp cách gộp đó với bộ lọc loại sự kiện. Cả hai cách vẫn cần chống trùng lặp ở cấp đơn hàng.
Kiểm tra requires_review và các xử lý thủ công trước khi thực hiện đơn hàng. amount_status = paid riêng lẻ không chứng minh đã được xác nhận. Các trường tài sản đã thanh toán ở cấp cao nhất tóm tắt quyết toán; payment_info chứa chi tiết khoản nhận và dữ liệu báo giá. Tất cả trạng thái, sự kiện và quy tắc ngoại lệ →
6. Thử việc gửi lại và khôi phục
Thử khoản thanh toán nhỏ, gửi thông báo trùng, hóa đơn hết hạn và bộ nhận tạm thời không hoạt động. Phát lại sự kiện không được ghi có đơn hàng lần thứ hai. Xử lý sự kiện sai thứ tự mà không ghi đè trạng thái mới hơn.
Kiểm tra Cửa hàng → IPN / Webhook → Lịch sử → Chi tiết, hoặc các mục gửi thông báo trong Chi tiết hóa đơn. Gửi lại dùng sự kiện đã ghi, không phải lần quyết toán mới.
Tín dụng xử lý thấp làm tạm dừng IPN/webhook trong khi thanh toán vẫn tiếp tục. Đối soát đơn hàng chưa xử lý qua API và xử lý thông báo được giữ lại sau khi phục hồi. Không bao giờ thực hiện đơn hàng chỉ dựa vào chuyển hướng trình duyệt hoặc ảnh chụp màn hình của khách.