🎯

paypal-integration

🎯Skill

from rmyndharis/antigravity-skills

VibeIndex|
What it does

Enables seamless PayPal payment integration with support for express checkout, subscriptions, refunds, and international transactions.

πŸ“¦

Part of

rmyndharis/antigravity-skills(289 items)

paypal-integration

Installation

npm runRun npm script
npm run build:catalog
npxRun with npx
npx @rmyndharis/antigravity-skills search <query>
npxRun with npx
npx @rmyndharis/antigravity-skills search kubernetes
npxRun with npx
npx @rmyndharis/antigravity-skills list
npxRun with npx
npx @rmyndharis/antigravity-skills install <skill-name>

+ 15 more commands

πŸ“– Extracted from docs: rmyndharis/antigravity-skills
10Installs
-
AddedFeb 4, 2026

Skill Details

SKILL.md

Integrate PayPal payment processing with support for express checkout, subscriptions, and refund management. Use when implementing PayPal payments, processing online transactions, or building e-commerce checkout flows.

Overview

# PayPal Integration

Master PayPal payment integration including Express Checkout, IPN handling, recurring billing, and refund workflows.

Do not use this skill when

  • The task is unrelated to paypal integration
  • You need a different domain or tool outside this scope

Instructions

  • Clarify goals, constraints, and required inputs.
  • Apply relevant best practices and validate outcomes.
  • Provide actionable steps and verification.
  • If detailed examples are required, open resources/implementation-playbook.md.

Use this skill when

  • Integrating PayPal as a payment option
  • Implementing express checkout flows
  • Setting up recurring billing with PayPal
  • Processing refunds and payment disputes
  • Handling PayPal webhooks (IPN)
  • Supporting international payments
  • Implementing PayPal subscriptions

Core Concepts

1. Payment Products

PayPal Checkout

  • One-time payments
  • Express checkout experience
  • Guest and PayPal account payments

PayPal Subscriptions

  • Recurring billing
  • Subscription plans
  • Automatic renewals

PayPal Payouts

  • Send money to multiple recipients
  • Marketplace and platform payments

2. Integration Methods

Client-Side (JavaScript SDK)

  • Smart Payment Buttons
  • Hosted payment flow
  • Minimal backend code

Server-Side (REST API)

  • Full control over payment flow
  • Custom checkout UI
  • Advanced features

3. IPN (Instant Payment Notification)

  • Webhook-like payment notifications
  • Asynchronous payment updates
  • Verification required

Quick Start

```javascript

// Frontend - PayPal Smart Buttons

```

```python

# Backend - Verify and capture order

from paypalrestsdk import Payment

import paypalrestsdk

paypalrestsdk.configure({

"mode": "sandbox", # or "live"

"client_id": "YOUR_CLIENT_ID",

"client_secret": "YOUR_CLIENT_SECRET"

})

def capture_paypal_order(order_id):

"""Capture a PayPal order."""

payment = Payment.find(order_id)

if payment.execute({"payer_id": payment.payer.payer_info.payer_id}):

# Payment successful

return {

'status': 'success',

'transaction_id': payment.id,

'amount': payment.transactions[0].amount.total

}

else:

# Payment failed

return {

'status': 'failed',

'error': payment.error

}

```

Express Checkout Implementation

Server-Side Order Creation

```python

import requests

import json

class PayPalClient:

def __init__(self, client_id, client_secret, mode='sandbox'):

self.client_id = client_id

self.client_secret = client_secret

self.base_url = 'https://api-m.sandbox.paypal.com' if mode == 'sandbox' else 'https://api-m.paypal.com'

self.access_token = self.get_access_token()

def get_access_token(self):

"""Get OAuth access token."""

url = f"{self.base_url}/v1/oauth2/token"

headers = {"Accept": "application/json", "Accept-Language": "en_US"}

response = requests.post(

url,

headers=headers,

data={"grant_type": "client_credentials"},

auth=(self.client_id, self.client_secret)

)

return response.json()['access_token']

def create_order(self, amount, currency='USD'):

"""Create a PayPal order."""

url = f"{self.base_url}/v2/checkout/orders"

headers = {

"Content-Type": "application/json",

"Authorization": f"Bearer {self.access_token}"

}

payload = {

"intent": "CAPTURE",

"purchase_units": [{

"amount": {

"currency_code": currency,

"value": str(amount)

}

}]

}

response = requests.post(url, headers=headers, json=payload)

return response.json()

def capture_order(self, order_id):

"""Capture payment for an order."""

url = f"{self.base_url}/v2/checkout/orders/{order_id}/capture"

headers = {

"Content-Type": "application/json",

"Authorization": f"Bearer {self.access_token}"

}

response = requests.post(url, headers=headers)

return response.json()

def get_order_details(self, order_id):

"""Get order details."""

url = f"{self.base_url}/v2/checkout/orders/{order_id}"

headers = {

"Authorization": f"Bearer {self.access_token}"

}

response = requests.get(url, headers=headers)

return response.json()

```

IPN (Instant Payment Notification) Handling

IPN Verification and Processing

```python

from flask import Flask, request

import requests

from urllib.parse import parse_qs

app = Flask(__name__)

@app.route('/ipn', methods=['POST'])

def handle_ipn():

"""Handle PayPal IPN notifications."""

# Get IPN message

ipn_data = request.form.to_dict()

# Verify IPN with PayPal

if not verify_ipn(ipn_data):

return 'IPN verification failed', 400

# Process IPN based on transaction type

payment_status = ipn_data.get('payment_status')

txn_type = ipn_data.get('txn_type')

if payment_status == 'Completed':

handle_payment_completed(ipn_data)

elif payment_status == 'Refunded':

handle_refund(ipn_data)

elif payment_status == 'Reversed':

handle_chargeback(ipn_data)

return 'IPN processed', 200

def verify_ipn(ipn_data):

"""Verify IPN message authenticity."""

# Add 'cmd' parameter

verify_data = ipn_data.copy()

verify_data['cmd'] = '_notify-validate'

# Send back to PayPal for verification

paypal_url = 'https://ipnpb.sandbox.paypal.com/cgi-bin/webscr' # or production URL

response = requests.post(paypal_url, data=verify_data)

return response.text == 'VERIFIED'

def handle_payment_completed(ipn_data):

"""Process completed payment."""

txn_id = ipn_data.get('txn_id')

payer_email = ipn_data.get('payer_email')

mc_gross = ipn_data.get('mc_gross')

item_name = ipn_data.get('item_name')

# Check if already processed (prevent duplicates)

if is_transaction_processed(txn_id):

return

# Update database

# Send confirmation email

# Fulfill order

print(f"Payment completed: {txn_id}, Amount: ${mc_gross}")

def handle_refund(ipn_data):

"""Handle refund."""

parent_txn_id = ipn_data.get('parent_txn_id')

mc_gross = ipn_data.get('mc_gross')

# Process refund in your system

print(f"Refund processed: {parent_txn_id}, Amount: ${mc_gross}")

def handle_chargeback(ipn_data):

"""Handle payment reversal/chargeback."""

txn_id = ipn_data.get('txn_id')

reason_code = ipn_data.get('reason_code')

# Handle chargeback

print(f"Chargeback: {txn_id}, Reason: {reason_code}")

```

Subscription/Recurring Billing

Create Subscription Plan

```python

def create_subscription_plan(name, amount, interval='MONTH'):

"""Create a subscription plan."""

client = PayPalClient(CLIENT_ID, CLIENT_SECRET)

url = f"{client.base_url}/v1/billing/plans"

headers = {

"Content-Type": "application/json",

"Authorization": f"Bearer {client.access_token}"

}

payload = {

"product_id": "PRODUCT_ID", # Create product first

"name": name,

"billing_cycles": [{

"frequency": {

"interval_unit": interval,

"interval_count": 1

},

"tenure_type": "REGULAR",

"sequence": 1,

"total_cycles": 0, # Infinite

"pricing_scheme": {

"fixed_price": {

"value": str(amount),

"currency_code": "USD"

}

}

}],

"payment_preferences": {

"auto_bill_outstanding": True,

"setup_fee": {

"value": "0",

"currency_code": "USD"

},

"setup_fee_failure_action": "CONTINUE",

"payment_failure_threshold": 3

}

}

response = requests.post(url, headers=headers, json=payload)

return response.json()

def create_subscription(plan_id, subscriber_email):

"""Create a subscription for a customer."""

client = PayPalClient(CLIENT_ID, CLIENT_SECRET)

url = f"{client.base_url}/v1/billing/subscriptions"

headers = {

"Content-Type": "application/json",

"Authorization": f"Bearer {client.access_token}"

}

payload = {

"plan_id": plan_id,

"subscriber": {

"email_address": subscriber_email

},

"application_context": {

"return_url": "https://yourdomain.com/subscription/success",

"cancel_url": "https://yourdomain.com/subscription/cancel"

}

}

response = requests.post(url, headers=headers, json=payload)

subscription = response.json()

# Get approval URL

for link in subscription.get('links', []):

if link['rel'] == 'approve':

return {

'subscription_id': subscription['id'],

'approval_url': link['href']

}

```

Refund Workflows

```python

def create_refund(capture_id, amount=None, note=None):

"""Create a refund for a captured payment."""

client = PayPalClient(CLIENT_ID, CLIENT_SECRET)

url = f"{client.base_url}/v2/payments/captures/{capture_id}/refund"

headers = {

"Content-Type": "application/json",

"Authorization": f"Bearer {client.access_token}"

}

payload = {}

if amount:

payload["amount"] = {

"value": str(amount),

"currency_code": "USD"

}

if note:

payload["note_to_payer"] = note

response = requests.post(url, headers=headers, json=payload)

return response.json()

def get_refund_details(refund_id):

"""Get refund details."""

client = PayPalClient(CLIENT_ID, CLIENT_SECRET)

url = f"{client.base_url}/v2/payments/refunds/{refund_id}"

headers = {

"Authorization": f"Bearer {client.access_token}"

}

response = requests.get(url, headers=headers)

return response.json()

```

Error Handling

```python

class PayPalError(Exception):

"""Custom PayPal error."""

pass

def handle_paypal_api_call(api_function):

"""Wrapper for PayPal API calls with error handling."""

try:

result = api_function()

return result

except requests.exceptions.RequestException as e:

# Network error

raise PayPalError(f"Network error: {str(e)}")

except Exception as e:

# Other errors

raise PayPalError(f"PayPal API error: {str(e)}")

# Usage

try:

order = handle_paypal_api_call(lambda: client.create_order(25.00))

except PayPalError as e:

# Handle error appropriately

log_error(e)

```

Testing

```python

# Use sandbox credentials

SANDBOX_CLIENT_ID = "..."

SANDBOX_SECRET = "..."

# Test accounts

# Create test buyer and seller accounts at developer.paypal.com

def test_payment_flow():

"""Test complete payment flow."""

client = PayPalClient(SANDBOX_CLIENT_ID, SANDBOX_SECRET, mode='sandbox')

# Create order

order = client.create_order(10.00)

assert 'id' in order

# Get approval URL

approval_url = next((link['href'] for link in order['links'] if link['rel'] == 'approve'), None)

assert approval_url is not None

# After approval (manual step with test account)

# Capture order

# captured = client.capture_order(order['id'])

# assert captured['status'] == 'COMPLETED'

```

Resources

  • references/express-checkout.md: Express Checkout implementation guide
  • references/ipn-handling.md: IPN verification and processing
  • references/refund-workflows.md: Refund handling patterns
  • references/billing-agreements.md: Recurring billing setup
  • assets/paypal-client.py: Production PayPal client
  • assets/ipn-processor.py: IPN webhook processor
  • assets/recurring-billing.py: Subscription management

Best Practices

  1. Always Verify IPN: Never trust IPN without verification
  2. Idempotent Processing: Handle duplicate IPN notifications
  3. Error Handling: Implement robust error handling
  4. Logging: Log all transactions and errors
  5. Test Thoroughly: Use sandbox extensively
  6. Webhook Backup: Don't rely solely on client-side callbacks
  7. Currency Handling: Always specify currency explicitly

Common Pitfalls

  • Not Verifying IPN: Accepting IPN without verification
  • Duplicate Processing: Not checking for duplicate transactions
  • Wrong Environment: Mixing sandbox and production URLs/credentials
  • Missing Webhooks: Not handling all payment states
  • Hardcoded Values: Not making configurable for different environments