---
title: PayPal
description: Kết nối PayPal với NexCMP để nạp tiền ví — thông tin REST app, webhook, thử nghiệm sandbox và các tài khoản PayPal đã lưu.
url: https://nexcmp.com/vi/docs/billing/paypal/
applies_to: NexCMP 1.6.1
updated: 2026-11-02
---

# PayPal

> **Vị trí trong admin:** Finance › Payment channels › PayPal (`/payments/paypal`). Công tắc bật/tắt và phí nằm trong Finance › Payment channels › Fees & limits (`/payments/fees`).

## Chức năng {#what-it-does}

Cho phép khách hàng nạp tiền vào ví USD bằng số dư PayPal, tài khoản ngân hàng hoặc thẻ liên kết với PayPal. Khách hàng cũng có thể cho phép NexCMP lưu tài khoản PayPal để [nạp tiền tự động](https://nexcmp.com/vi/docs/billing/auto-top-up/). Sử dụng song song với [Stripe](https://nexcmp.com/vi/docs/billing/stripe/) cho những khách hàng thích dùng PayPal.

## Yêu cầu {#requirements}

| Hạng mục | Yêu cầu |
|---|---|
| Tài khoản PayPal | Tài khoản PayPal **Business** có thể nhận USD. |
| REST app | Một REST app trong PayPal Developer Dashboard (**Apps & Credentials**) cung cấp **Client ID** và **Client secret**. Sử dụng tab **Sandbox** để kiểm thử, **Live** cho môi trường production. |
| Mạng | HTTPS có thể truy cập được từ Internet (PayPal gọi webhook) và quyền truy cập chiều đi tới `api-m.paypal.com` (live) hoặc `api-m.sandbox.paypal.com` (sandbox), cổng 443. |
| Quyền hạn | REST app cần có các quyền refund và webhooks. Hộp thoại **Check** sẽ hiển thị xem cả hai scope này đã có hay chưa. |
| Thành phần phụ thuộc | Không có. |

## Chuẩn bị hạ tầng {#prepare-the-infrastructure}

1. Đăng nhập vào [developer.paypal.com](https://developer.paypal.com) bằng tài khoản Business của bạn và mở **Apps & Credentials**.
2. Chọn **Sandbox** (thử nghiệm) hoặc **Live**, sau đó nhấn **Create App**. Đặt tên cho ứng dụng, ví dụ "NexCMP".
3. Sao chép **Client ID** và **Secret** của ứng dụng.
4. Để thử nghiệm, hãy vào **Testing Tools › Sandbox Accounts** để tìm hoặc tạo một tài khoản sandbox *Personal* (người mua).
5. Bạn không cần tự tạo webhook; NexCMP sẽ tạo webhook bằng nút **Create webhook**.

## Kết nối trong NexCMP {#connect-in-nexcmp}

1. Mở **Finance › Payment channels › PayPal** (`/payments/paypal`).
2. Trong **API keys**, chọn **Mode**: `live` (tiền thật, `api-m.paypal.com`) hoặc `sandbox` (`api-m.sandbox.paypal.com`).
3. Dán **Client ID** (tối thiểu 20 ký tự) và **Client secret**.
4. Nhấp **Check**. Thao tác này sẽ kiểm tra thông tin xác thực bạn đã nhập (không bắt buộc phải lưu) và báo cáo kết nối, App ID, chế độ hoạt động, xem các scope refund và webhooks có hiện diện hay không cũng như thời hạn hiệu lực của token.
5. Nhấp **Save**.
6. Trong thẻ **Webhook**, hãy xác nhận URL là `https://<your-domain>/v1/billing/paypal/webhook` (phải là `https`), sau đó nhấp **Create webhook** và xác nhận. NexCMP sẽ yêu cầu PayPal tạo hoặc cập nhật webhook với 11 sự kiện và lưu **Webhook ID** trả về. Nút này sử dụng các khóa **đã lưu** — hãy lưu trước nếu bạn vừa chỉnh sửa chúng.
7. Nhấp **Check** lại: dòng **Webhook** sẽ hiển thị "exists, 11 events".
8. Mở **Fees & limits**, bật **PayPal**, đặt **PayPal fee %** (mặc định 4.4) và **PayPal fixed fee (cents)** (mặc định 30) theo biểu phí của bạn rồi nhấp **Save channels & fees**.

![Trang PayPal ở chế độ sandbox với thông tin xác thực mẫu đã nhập](https://nexcmp.com/vi/docs/images/billing/paypal-01-keys.webp)


### Sự kiện webhook {#webhook-events}

NexCMP đăng ký 11 sự kiện này: `CHECKOUT.ORDER.APPROVED`, `PAYMENT.CAPTURE.COMPLETED`, `PAYMENT.CAPTURE.PENDING`, `PAYMENT.CAPTURE.DECLINED`, `PAYMENT.CAPTURE.REFUNDED`, `PAYMENT.CAPTURE.REVERSED`, `CUSTOMER.DISPUTE.CREATED`, `CUSTOMER.DISPUTE.UPDATED`, `CUSTOMER.DISPUTE.RESOLVED`, `RISK.DISPUTE.CREATED`, `CHECKOUT.PAYMENT-APPROVAL.REVERSED`.

Mỗi webhook đều được xác minh bằng cách gọi API xác thực chữ ký của PayPal, được lưu một lần và xử lý theo cơ chế idempotent. NexCMP không bao giờ tin cậy số tiền trong nội dung webhook: trước khi ghi có một capture, hệ thống sẽ lấy dữ liệu capture từ PayPal.

## Kiểm tra {#verify}

1. Giữ **Mode** ở `sandbox`. Trong portal, mở **Billing › Deposit**, chọn **PayPal**, nhấp **Continue on PayPal** (hoặc nút PayPal) và đăng nhập bằng tài khoản người mua sandbox.
2. Phê duyệt thanh toán. Bạn sẽ quay lại portal, số dư tăng lên và khoản thanh toán xuất hiện dưới **Finance › Billing › Top-ups** với trạng thái *Completed*.
3. Mở **Payment channels › Gateway events › PayPal & USDT**: sự kiện `PAYMENT.CAPTURE.COMPLETED` sẽ được liệt kê.
4. Khi mọi thứ hoạt động bình thường, hãy chuyển **Mode** sang `live`, nhập thông tin xác thực live, nhấp **Save**, sau đó nhấp **Create webhook** lại (webhook sandbox và live tách biệt nhau).

## Hạn mức & lưu ý {#limits-notes}

- **Cách khoản thanh toán hoàn tất.** Đơn hàng được tạo bằng USD; sau khi khách hàng phê duyệt, **máy chủ** sẽ capture đơn hàng (với request ID theo cơ chế idempotent) và ghi có vào ví đúng một lần. Webhook cùng tác vụ đối soát chạy mỗi 10 phút là các lớp dự phòng an toàn nếu khách hàng đóng trình duyệt.
- **Đơn hàng chờ xử lý và đơn hàng bị bỏ dở.** Một đơn hàng có thể ở trạng thái mở trong 12 giờ. Khách hàng chỉ có thể có tối đa 5 đơn hàng đang chờ xử lý (máy chủ sẽ phản hồi `too_many_pending`, HTTP 429). Đơn hàng vẫn chưa được capture sau 24 giờ sẽ bị đánh dấu thất bại.
- **Chưa cấu hình webhook.** Bảng điều khiển sẽ trả về HTTP 503 cho mọi webhook của PayPal cho đến khi Webhook ID được lưu. Các khoản capture thực hiện qua portal và quá trình đối soát mỗi 10 phút vẫn ghi có vào ví, nhưng không có thông tin nào mà PayPal báo cáo qua webhook (tranh chấp, hoàn tiền, capture muộn) được áp dụng — hãy nhấp **Create webhook**.
- **Tài khoản PayPal đã lưu.** Khi khách hàng chọn lưu PayPal (hoặc hoàn tất lần nạp tiền đầu tiên, thao tác này sẽ bật [nạp tiền tự động](https://nexcmp.com/vi/docs/billing/auto-top-up/)), PayPal sẽ lưu payment token trong vault của họ. NexCMP chỉ lưu một mã định danh và e-mail PayPal. Xem [Phương thức thanh toán đã lưu](https://nexcmp.com/vi/docs/billing/saved-payment-methods/).
- **Hoàn tiền và tranh chấp** được xử lý tương tự Stripe: các yêu cầu hoàn tiền được phê duyệt tại **Finance › Payouts › Card refunds**; tranh chấp sẽ khóa tài khoản khách hàng và dừng các dịch vụ trả trước của họ cho đến khi bạn giải quyết xong.
- **Phí.** Phí của PayPal không được đọc ngược lại; tỷ lệ phần trăm và phí cố định bạn cấu hình sẽ quyết định số tiền khách hàng nhìn thấy và số tiền được ghi có. Mức phí thực tế tùy thuộc vào quốc gia của bạn (biểu mẫu gợi ý 4.4 % cho Việt Nam và 3.49 % cho Hoa Kỳ).

## Xử lý sự cố {#troubleshooting}

| Hiện tượng | Nguyên nhân | Cách khắc phục |
|---|---|---|
| "Client ID quá ngắn" | Đã dán ít hơn 20 ký tự | Sao chép toàn bộ Client ID. |
| "URL Webhook phải là https" | URL được nhập với `http://` | Sử dụng tên miền `https://` công khai của bạn. |
| Check báo lỗi kết nối | Sai chế độ (dùng live key trong sandbox hoặc ngược lại), sai secret, không có quyền truy cập outbound | Khớp **Mode** với loại key; kiểm tra `curl -I https://api-m.paypal.com` từ server. |
| Scope refund / webhooks hiển thị "no" | REST app thiếu các tính năng này | Bật các tính năng này trên app trong PayPal Developer Dashboard. |
| Banner "Đã thiết lập PayPal key, KHÔNG CÓ webhook" | Thiếu Webhook ID | Nhấp vào **Create webhook**. |
| "Không tìm thấy Webhook" trong Check | Webhook đã bị xóa trên PayPal hoặc thuộc về app khác | Nhấp vào **Create webhook** một lần nữa. |
| Khách hàng nhận được thông báo PayPal từ chối thanh toán | PayPal đã từ chối nguồn tiền đó | Yêu cầu khách hàng chọn nguồn thanh toán khác. |
| Khách hàng thấy "Too many pending requests" | Có 5 đơn hàng đang mở | Chờ các đơn hàng hết hạn hoặc hoàn tất chúng. |
| Thiếu nút PayPal | PayPal đang tắt trong **Fees & limits** hoặc chưa được cấu hình | Bật lên và lưu thông tin xác thực. |
