Sell Digital Products from AI Chatbots: No Fund Holding

2026-10-05 · AgentPay VN

ai agentsvietqr paymentspython sdkdigital productschatbot monetization

The Problem: Building Payment-Ready AI Without Becoming a Bank

You've built an AI chatbot that sells digital products—online courses, design templates, API access, or ebooks. Your users trust you. But here's the friction: to accept payments, you suddenly need a merchant account, PCI compliance, fraud detection, chargeback handling, and most intimidatingly, a bank-licensed system to hold and manage customer funds.

That's a liability minefield. Most indie developers and small AI teams aren't equipped for it. Traditional payment processors either take 3–5% in fees, require weeks of approval, or lock you into their ecosystem. And you end up holding money in escrow—turning your simple chatbot into an unintended financial institution.

What if your AI agent could collect payments directly into your bank account without ever touching the money?

That's exactly what AgentPay VN solves.

What Is AgentPay VN?

AgentPay VN is an open-source Python SDK (MIT license) plus an MCP (Model Context Protocol) server that lets AI agents generate and manage VietQR payment requests. Here's the critical difference: the QR code points directly at your merchant bank account. Settlement happens instantly through your bank's feed. No escrow. No holding period. No compliance nightmare.

Key facts: - Zero fund holding: Money goes straight to your bank - VietQR native: Works seamlessly with Vietnamese banking infrastructure - AI-native: Designed for LLM agents (Claude, GPT, etc.) via MCP - Production-ready: Open-source, MIT licensed, actively maintained - Simple 3-step flow: Create request → Send checkout URL → Await settlement

Install in one line:

pip install agentpay-vn

How It Works: The Three-Step Payment Flow

Step 1: Create a Payment Request

Your AI agent receives a customer intent ("I want to buy your Python course"). The agent calls create_payment_request() to generate a unique payment request with amount, description, and expiry.

Step 2: Send the Checkout URL

The agent sends the customer a VietQR checkout link (or embeds it in a QR image). The customer scans with any Vietnamese bank app and pays directly to your account.

Step 3: Await Settlement

Your agent polls the bank feed confirmation (via await_settlement()). Once confirmed, the agent delivers the digital product—course link, API key, file download, or access grant.

No middleware. No escrow. No waiting.

Building Your First Payment-Ready AI Agent

Let's build a concrete example: a Python course sales bot that sells a $19 course module.

Basic Setup

First, install the SDK:

pip install agentpay-vn

Then, initialize your merchant details:

from agentpay_vn import AgentPayClient

# Initialize with your merchant bank account
client = AgentPayClient(
    merchant_id="YOUR_MERCHANT_ID",
    merchant_name="Python Courses by AI",
    merchant_account="1234567890123",  # Your VietQR bank account
    bank_code="970436"  # Example: Techcombank
)

Create a Payment Request

Here's a real example where your chatbot receives a purchase request:

import json
from datetime import datetime, timedelta

# Customer wants to buy "Python Automation Mastery"
course_title = "Python Automation Mastery"
course_price = 19  # USD (or VND equivalent)
customer_email = "learner@example.com"

# Step 1: Create payment request
payment_request = client.create_payment_request(
    amount=course_price * 25000,  # Convert to VND (1 USD ≈ 25,000 VND)
    description=f"Course: {course_title}",
    order_id=f"course_{customer_email}_{datetime.now().timestamp()}",
    expires_at=(datetime.now() + timedelta(minutes=30)).isoformat()
)

# payment_request contains:
# {
#   "qr_code": "00020126...",  # Raw VietQR string
#   "qr_image_url": "https://...",  # PNG QR image
#   "checkout_url": "https://agentpay.vn/checkout/...",
#   "order_id": "course_learner@...",
#   "amount": 475000,
#   "expires_at": "2024-01-15T12:30:00"
# }

print(f"✓ Payment request created")
print(f"  QR Code: {payment_request['qr_image_url']}")
print(f"  Checkout: {payment_request['checkout_url']}")

Line-by-line explanation: - amount: Convert customer's chosen price to VND (typically 1 USD = ~25,000 VND in Vietnam) - description: What appears on the customer's bank statement - order_id: Unique identifier linking payment to customer; use email/timestamp to ensure uniqueness - expires_at: Set a 30-minute window; prevents old QR codes from being used - Returns: A dict with both raw QR code string and a checkout URL for non-scanning scenarios

Await Settlement Confirmation

Once the customer pays, your agent needs to confirm:

import time
from typing import Optional

async def deliver_course(order_id: str, customer_email: str) -> bool:
    """
    Wait for bank settlement, then deliver digital product.
    Polls every 3 seconds for up to 5 minutes.
    """
    max_wait_seconds = 300
    poll_interval = 3
    elapsed = 0

    while elapsed < max_wait_seconds:
        # Check if payment settled
        settlement = client.await_settlement(
            order_id=order_id,
            timeout=poll_interval
        )

        if settlement and settlement.get('status') == 'confirmed':
            # Payment confirmed! Deliver the product
            print(f"✓ Payment settled: {settlement['amount']} VND")
            print(f"  Transaction ID: {settlement['transaction_id']}")

            # Generate access token/link for the course
            access_link = generate_course_access_token(
                course_id="python-automation-mastery",
                customer_email=customer_email,
                expires_days=365
            )

            # Send to customer
            send_email(
                to=customer_email,
                subject="Welcome to Python Automation Mastery!",
                body=f"Your course link: {access_link}"
            )

            return True

        elapsed += poll_interval
        time.sleep(poll_interval)

    print(f"✗ Payment timeout after {max_wait_seconds}s")
    return False

# Usage in your AI agent
await deliver_course(
    order_id=payment_request['order_id'],
    customer_email="learner@example.com"
)

Key points: - await_settlement() returns None if not yet paid, or a dict with status='confirmed' and transaction details - Set reasonable timeouts (30 seconds to 5 minutes); Vietnam's bank network is fast - Once confirmed, generate access tokens and send immediately—the customer has already paid

Integrating with Your LLM (MCP Server Setup)

If you're using Claude, GPT, or another LLM agent framework, use the MCP server to give your AI native payment capabilities:

pip install agentpay-vn
agentpay-mcp --merchant-id YOUR_ID --account 1234567890123 --bank 970436

Then configure Claude or your LLM client:

{
  "mcpServers": {
    "agentpay": {
      "command": "agentpay-mcp",
      "args": [
        "--merchant-id", "YOUR_MERCHANT_ID",
        "--merchant-name", "Your Business Name",
        "--account", "1234567890123",
        "--bank", "970436"
      ],
      "env": {
        "AGENTPAY_LOG_LEVEL": "info"
      }
    }
  }
}

Once configured, your AI agent can call AgentPay tools directly:

User: "I want to buy your advanced Python course."
Agent (thinking): The user wants to purchase. I'll use the agentpay tool to create a payment request.
Agent (action): create_payment_request(amount=19, description="Advanced Python Course")
Agent (result): {"checkout_url": "https://agentpay.vn/checkout/abc123", ...}
Agent (response): "Here's your checkout link: [link]. You can pay with any Vietnamese bank app."

Real-World Example: A Digital Product Marketplace Bot

Imagine TechVNMarket, a Discord bot selling Vietnamese-created digital products (design templates, code libraries, tutorials):

User journey: 1. User: !buy template-figma-ui-kit 2. Bot checks inventory and pricing from database 3. Bot: "Figma UI Kit - 150,000 VND. Scanning your QR code..." 4. Bot creates payment request: Order ID: cmd_user123_1705000000 Amount: 150,000 VND Expires: 5 minutes 5. Bot displays QR image and checkout link 6. User scans with Vietcombank/Techcombank/OCB app → pays immediately 7. Bot's backend detects settlement within 2 seconds (VietQR is instant) 8. Bot sends DM: "✓ Payment received! Here's your download link: [secure token]" 9. User downloads template, bot logs sale

Zero complexity. Zero fund holding. Zero PCI scope.

AgentPay vs. Traditional Payment Solutions

Feature AgentPay VN Stripe/PayPal Local Banks
Fund Holding ✗ Direct to bank ✓ Escrow (1-3 days) Varies
Setup Time 5 minutes 1-2 weeks 1-4 weeks
VietQR Native ✓ Yes ✗ No ✓ Yes
Fees Bank standard 2.9% + $0.30 0.1-0.5%
AI Agent Ready ✓ MCP built-in ✗ API only ✗ Legacy
Compliance Burden Low High (PCI DSS) Medium
Open Source ✓ MIT ✗ Proprietary N/A

Pro Tips & Common Patterns

Tip 1: Use Idempotency Keys

When creating payment requests, include a hash of customer + product + timestamp to avoid duplicate requests:

import hashlib

idempotency_key = hashlib.sha256(
    f"{customer_email}_{product_id}_{int(time.time())}".encode()
).hexdigest()

payment_request = client.create_payment_request(
    amount=amount,
    description=description,
    order_id=idempotency_key
)

Tip 2: Implement Webhook Confirmations

Don't just poll. If AgentPay supports webhooks, register a callback endpoint:

# Your webhook receiver
@app.post("/webhooks/agentpay/settlement")
async def on_settlement(payload: dict):
    order_id = payload['order_id']
    status = payload['status']

    if status == 'confirmed':
        # Immediately deliver product
        deliver_digital_product(order_id)

Tip 3: Retry Logic

Network hiccups happen. Wrap settlement checks in exponential backoff:

import asyncio
from tenacity import retry, stop_after_attempt, wait_exponential

@retry(
    stop=stop_after_attempt(5),
    wait=wait_exponential(multiplier=1, min=2, max=10)
)
async def safe_await_settlement(order_id):
    return client.await_settlement(order_id)

Frequently Asked Questions

Q: What if the customer doesn't pay within the QR expiry time? A: The QR code expires (default 30 minutes). Your agent should prompt the customer to create a new payment request. No funds are at risk—nothing was transferred.

Q: Can I use this for subscription billing? A: AgentPay VN currently handles one-time payments. For subscriptions, you'd create a new request at each billing cycle (monthly, yearly). Automate this with cron jobs in your agent framework.

Q: Is this PCI DSS compliant? A: Yes. Because you never touch the payment data (VietQR/bank handles it), you're out of PCI scope entirely. Your agent only handles order IDs and settlement confirmations.

Q: What if I'm selling to international customers? A: VietQR works for Vietnamese bank accounts. For international customers, you'd need a separate payment processor (Stripe, etc.) or ask them to use a Vietnamese banking partner.

FAQ: Do's and Don'ts

✅ Do: - Store order IDs in your database linking to customer emails - Set reasonable expiry times (15–30 minutes for digital products) - Log all transactions for accounting - Deliver products only after settlement confirmation - Test with small amounts first

❌ Don't: - Assume payment without confirmation - Expose merchant account numbers in frontend code - Poll forever without timeout - Deliver before settlement completes - Skip proper error logging

Key Takeaways

Getting Started Now

You can have a payment-ready chatbot running in under 30 minutes:

  1. Install the SDK: bash pip install agentpay-vn

  2. Read the full docs: https://agentpay.servicesai.vn/v1/docs

  3. Clone examples: https://github.com/phuocdu/agentpay-vn

  4. Set up your merchant account with your Vietnamese bank (if you don't have one, this step takes 1–2 business days)

  5. Deploy your agent with payment flows using the code examples above

The barrier to monetizing AI has just dropped dramatically. Your chatbot can sell digital products, subscriptions, or services without any of the traditional payment infrastructure headaches. That's the AgentPay VN promise.

Start building today. The next generation of AI commerce doesn't hold funds—it flows directly to your bank. 🚀

Get started →

← All posts