API Status Support Dashboard

Voids

Cancel transactions before they settle.


Overview

Voiding cancels a transaction before it's been settled (batched). Unlike refunds, voids prevent the transaction from ever appearing on the customer's statement.

Key Differences: Void vs Refund

Feature Void Refund
Timing Before settlement After settlement
Statement Never appears Appears as separate credit
Fees None (transaction cancelled) Processing fees may apply
Speed Instant cancellation 3-10 business days
Use When Same day, before batch After settlement

API Route Options

Auth Type Endpoint Use Case
API Key (x-api-key) POST /api/v1/public/void ERP / server integration
JWT Bearer POST /api/v1/transactions/:id/void Dashboard / admin

For ERP and server-to-server integrations, see Void — Public API.


Void Transaction (Admin API)

Endpoint

POST /api/v1/transactions/:transactionId/void
curl -X POST https://dev.auxcore.net/api/v1/transactions/txn_abc123/void \
  -H "Authorization: Bearer YOUR_TOKEN" \
  -H "X-Tenant-ID: your-tenant-id" \
  -H "Content-Type: application/json" \
  -d '{
    "reason": "Customer cancellation"
  }'

Response:

{
  "success": true,
  "data": {
    "transactionId": "txn_abc123",
    "status": "voided",
    "voidedAmount": 150.00,
    "currency": "USD",
    "voidedAt": "2026-01-28T13:00:00Z",
    "reason": "Customer cancellation"
  }
}

Request Parameters

Parameter Type Required Description
reason string No Reason for voiding

Response Fields

Field Type Description
transactionId string Original transaction ID
status string New status (voided)
voidedAmount decimal Amount voided
currency string Currency code
voidedAt timestamp When void occurred
reason string Void reason (if provided)

When to Use Voids

✅ Use Void For:

  1. Customer cancellations (same day)

    # Customer calls minutes after purchase to cancel
    curl -X POST /api/v1/transactions/txn_abc123/void \
      -d '{"reason": "Customer cancelled order"}'
    
  2. Duplicate charges

    # Accidentally charged customer twice
    curl -X POST /api/v1/transactions/txn_duplicate_456/void \
      -d '{"reason": "Duplicate transaction"}'
    
  3. Order errors

    # Wrong product or price charged
    curl -X POST /api/v1/transactions/txn_wrong_789/void \
      -d '{"reason": "Incorrect item charged"}'
    
  4. Suspected fraud

    # Fraudulent transaction detected before settlement
    curl -X POST /api/v1/transactions/txn_fraud_101/void \
      -d '{"reason": "Suspected fraud"}'
    

❌ Don't Use Void For:

  1. Settled transactions → Use refund instead
  2. Partial cancellations → Void is all-or-nothing
  3. After batch close → Too late, use refund

Settlement Windows

Transactions can typically be voided until the settlement batch closes:

Merchant Type Settlement Time Void Window
Most merchants Midnight (local time) Same day until midnight
Restaurants 3 AM next day Extended window for tips
Hotels Custom schedule Varies by merchant

⚠️ Important: Once batched, you must use refund instead of void.


Validation Rules

Cannot Void If:

  1. Already voided

    {
      "success": false,
      "error": {
        "code": "ALREADY_VOIDED",
        "message": "Transaction already voided"
      }
    }
    
  2. Already settled

    {
      "success": false,
      "error": {
        "code": "ALREADY_SETTLED",
        "message": "Cannot void settled transaction, use refund"
      }
    }
    
  3. Already refunded

    {
      "success": false,
      "error": {
        "code": "ALREADY_REFUNDED",
        "message": "Transaction already refunded"
      }
    }
    
  4. Transaction declined

    {
      "success": false,
      "error": {
        "code": "NOT_VOIDABLE",
        "message": "Only approved transactions can be voided"
      }
    }
    
  5. Authorization (not captured)

    {
      "success": false,
      "error": {
        "code": "NOT_VOIDABLE",
        "message": "Uncaptured authorizations expire automatically"
      }
    }
    

Void vs Refund Decision Tree

Transaction needs to be cancelled
    ↓
Has it settled yet?
    ↓                    ↓
   YES                  NO
    ↓                    ↓
Use REFUND          Use VOID
(appears on         (never appears
statement)          on statement)

How to check if settled:

curl https://dev.auxcore.net/api/v1/transactions/txn_abc123 \
  -H "Authorization: Bearer YOUR_TOKEN" \
  -H "X-Tenant-ID: your-tenant-id"

Response:

{
  "success": true,
  "data": {
    "transactionId": "txn_abc123",
    "status": "approved",
    "settled": false,  ← Check this field
    "settledAt": null
  }
}

Common Scenarios

Scenario 1: Customer Changes Mind

Timeline: 30 minutes after purchase
Action: Void

curl -X POST /api/v1/transactions/txn_abc123/void \
  -d '{"reason": "Customer cancelled order within 30 minutes"}'

Result: Transaction cancelled, never appears on statement

Scenario 2: Duplicate Click

Timeline: Seconds after original charge
Action: Void the duplicate

curl -X POST /api/v1/transactions/txn_duplicate_456/void \
  -d '{"reason": "Duplicate transaction from double-click"}'

Result: One charge processes, duplicate cancelled

Scenario 3: Next-Day Cancellation

Timeline: 24 hours after purchase
Action: Check if settled, then decide

# Check settlement status
curl /api/v1/transactions/txn_abc123

# If not settled:
curl -X POST /api/v1/transactions/txn_abc123/void

# If settled:
curl -X POST /api/v1/transactions/txn_abc123/refund

Webhooks

transaction.voided

{
  "type": "transaction.voided",
  "data": {
    "transactionId": "txn_abc123",
    "amount": 150.00,
    "voidedAt": "2026-01-28T13:00:00Z",
    "voidedBy": "user_123",
    "reason": "Customer cancellation"
  }
}

Best Practices

✅ DO:

❌ DON'T:


Testing

Test Voids in Sandbox

# 1. Create test transaction
TXNID=$(curl -X POST https://dev.auxcore.net/api/v1/transactions \
  -d '{
    "type": "sale",
    "amount": 100.00,
    "card": {
      "number": "4111111111111111",
      "expiryMonth": "12",
      "expiryYear": "2027",
      "cvv": "123"
    },
    ...
  }' | jq -r '.data.transactionId')

# 2. Void the transaction
curl -X POST https://dev.auxcore.net/api/v1/transactions/$TXNID/void \
  -d '{"reason": "Test void"}'

# 3. Verify voided
curl https://dev.auxcore.net/api/v1/transactions/$TXNID
# Should show status: "voided"

# 4. Try to void again (should fail)
curl -X POST https://dev.auxcore.net/api/v1/transactions/$TXNID/void
# Should return ALREADY_VOIDED error

Error Handling

Void Failed, Use Refund

async function cancelTransaction(transactionId) {
  try {
    // Try void first
    const voidResponse = await voidTransaction(transactionId);
    return voidResponse;
  } catch (error) {
    if (error.code === 'ALREADY_SETTLED') {
      // Void failed because settled, use refund instead
      const refundResponse = await refundTransaction(transactionId);
      return refundResponse;
    }
    throw error;
  }
}

Impact on Merchant Fees

Void = No Fees

Original transaction: $100.00
Processing fee: $3.00
  ↓
Transaction voided
  ↓
Customer charged: $0.00
Merchant pays: $0.00 (fee refunded)

Refund = Fees Apply (usually)

Original transaction: $100.00
Processing fee: $3.00
  ↓
Transaction refunded next day
  ↓
Customer refunded: $100.00
Merchant still pays: $3.00 (fee not refunded)

💡 Tip: Void quickly to save on processing fees!


Next Steps


Need help? Contact support@auxvault.com