Redemption Codes
Redemption codes let merchants distribute single-use or limited-use alphanumeric codes that customers can redeem to add a fixed or percentage-based credit directly to their wallet balance. Use them for promotions, gift campaigns, loyalty rewards, or refund alternatives.
Overview
Redemption codes are distinct from coupon codes applied at checkout. Instead of discounting an order, a redemption code deposits credit into the customer's wallet balance, which they can then spend across future orders. This makes them well-suited for:
- Welcome bonuses for new account holders
- Influencer or affiliate campaign codes
- Refund-as-credit offers (instead of reversing a payment)
- Gift cards distributed offline or via email
- Event or seasonal promotional campaigns
Each code tracks its own usage count, per-customer usage limit, expiry date, and redemption history. Codes that exceed their usage cap or expiry date are automatically rejected at the point of redemption.
How It Works
- A merchant creates one or more codes in WooCommerce > WalletPro > Redemption Codes, specifying the credit value, usage limits, and optional expiry.
- The merchant distributes the code via email, social media, printed materials, or any other channel.
- The customer navigates to My Account > Wallet > Redeem a Code and enters the code.
- WalletPro validates the code (active status, usage cap, expiry, per-customer limit, KYC gate if configured) and, on success, credits the wallet balance immediately.
- A transaction record appears on the customer's wallet statement and in the merchant's audit ledger.
Redemption codes credit the wallet balance, not an order discount. The credited amount becomes spendable on any future order where wallet payment is accepted, subject to any spending limits configured for the customer's role.
Creating Redemption Codes
Navigate to WooCommerce > WalletPro > Redemption Codes > Add New Code.
| Field | Description | Notes |
|---|---|---|
| Code | The alphanumeric string customers will enter. Case-insensitive at redemption. | Click Generate to auto-create a random 12-character code, or enter a custom value. Spaces are not permitted. |
| Credit Type | Fixed amount or percentage of the customer's last completed order total. | Percentage codes require the customer to have at least one completed order. |
| Credit Amount / Percentage | The value to credit. For fixed: amount in the store's base currency. For percentage: 1 to 100. | For percentage codes, optionally set a Maximum Credit Cap to limit the payout. |
| Currency | Which wallet currency to credit (visible only on multi-currency installations). | Defaults to the store's primary currency. |
| Total Usage Limit | Maximum number of times this code can be redeemed across all customers. Leave blank for unlimited. | |
| Per Customer Usage Limit | Maximum times a single customer account can redeem this code. | Defaults to 1. Set to blank to allow unlimited redemptions per customer. |
| Expiry Date | Date after which the code is no longer accepted. Stored in UTC. | Leave blank for a non-expiring code. |
| Status | Active or Inactive. Inactive codes are rejected at redemption without revealing whether the code exists. | |
| Require KYC Verification | When enabled, the customer must pass the configured KYC check before redeeming. | Depends on KYC gating being enabled in WalletPro > Settings > Compliance. |
| Restrict to Role | Limit redemption to customers with a specific WordPress user role. | Optional. Leave blank to allow any authenticated user. |
| Internal Note | Admin-only memo field for campaign tracking. Not visible to customers. |
Click Save Code. The code appears in the codes list with its current redemption count and status.
Bulk Code Generation
To generate many unique codes at once (for example, to distribute individually in a mailer), use the Bulk Generate button on the Redemption Codes list screen. A modal appears with the following options:
- Number of Codes, how many unique codes to create (max 10,000 per batch)
- Code Prefix, optional string prepended to each generated code (e.g.,
SUMMER25-) - Code Length, total character length of the random portion (8 to 24 characters)
- All other fields (credit type, limits, expiry) are shared across the batch
After generation, click Export CSV on the confirmation screen to download a spreadsheet of all generated codes.
Managing Existing Codes
The Redemption Codes list at WooCommerce > WalletPro > Redemption Codes shows:
- Code string
- Credit value
- Redeemed / Total Usage Limit counts
- Expiry date
- Status (Active / Inactive / Expired / Exhausted)
Use the Bulk Actions dropdown to activate, deactivate, or delete multiple codes at once. Use the Search field or status filter tabs to locate specific codes.
Clicking a code opens its edit screen, where you can adjust limits and expiry but cannot change the code string itself once it has been redeemed at least once.
Redemption History
Within each code's edit screen, a Redemption History table lists every redemption event:
| Column | Description |
|---|---|
| Customer | Linked display name and email of the redeeming user |
| Date & Time | UTC timestamp of the redemption |
| Credit Applied | Actual amount credited (relevant for percentage codes where the value varies per customer) |
| Transaction ID | Links to the wallet ledger entry for this credit |
To export the history for a single code, click Export History (CSV) in the Redemption History section header.
Rate Limiting
WalletPro applies rate limiting to the redemption endpoint to prevent brute-force code discovery. Configure the limits at WooCommerce > WalletPro > Settings > Redemption Codes:
| Setting | Default | Description |
|---|---|---|
| Max Attempts Per Hour (per user) | 10 | Failed attempts from a single logged-in user that trigger a temporary block. |
| Max Attempts Per Hour (per IP) | 20 | Failed attempts from a single IP address across all accounts. |
| Lockout Duration (minutes) | 60 | How long a user or IP is blocked from redemption attempts after exceeding the cap. |
Generic error messages are returned on failed redemptions regardless of whether the failure is due to an invalid code, an exhausted code, an expired code, or a rate-limit lockout. This prevents enumeration attacks where an attacker could determine which codes exist.
Customer Experience
Redeeming a Code
- Log in to the store and navigate to My Account > Wallet.
- Locate the Redeem a Code section (displayed as a card below the balance summary).
- Enter the code in the text field. The field is case-insensitive and ignores leading/trailing whitespace.
- Click Apply Code.
- On success, a confirmation message displays the credited amount and the updated wallet balance. The transaction appears immediately in the wallet statement.
If the code is invalid, expired, exhausted, or the customer has already reached their per-customer limit, a generic error message is shown: "This code could not be applied. Please check the code and try again."
Transaction Statement Entry
A successfully redeemed code creates a wallet transaction visible in the customer's statement with:
- Type: Redemption Code
- Description: Code redeemed: [CODE] (the code string is shown to the customer who redeemed it)
- Amount: credited value
- Running balance after credit
Settings Reference
All redemption code settings are at WooCommerce > WalletPro > Settings > Redemption Codes.
| Setting | Default | Description |
|---|---|---|
| Enable Redemption Codes | On | Master switch. When off, the Redeem a Code section is hidden from My Account and the redemption endpoint returns 404. |
| Show Code Field on Checkout | Off | When on, a code redemption field also appears at checkout. Credit is applied to the wallet before the order total is recalculated. |
| Maximum Credit Cap (percentage codes) | N/A | Store-wide ceiling on credits from percentage-type codes. Overrides any individual code cap if lower. |
| Credit Expiry (days) | N/A | If set, credits from redemption codes expire this many days after being applied. Leave blank for credits that never expire. |
| Require Login | On | When off, guest users can redeem codes. Credit is held in a session and applied if they register or log in before the session expires. |
| Email Notification on Redemption | Off | Sends the customer a confirmation email when a code is successfully redeemed. |
| Admin Alert on Code Exhaustion | Off | Sends an email to the WooCommerce admin address when a code reaches its total usage limit. |
Developer Reference
REST API
Redemption code resources are available under the walletpro/v1 namespace. All endpoints require authentication via WooCommerce API keys or a logged-in nonce.
List Codes
# List all redemption codes (admin only)
GET /wp-json/walletpro/v1/redemption-codes
# Query parameters
# ?status=active|inactive|expired|exhausted
# ?per_page=25&page=1
# ?search=SUMMER
Create a Code
POST /wp-json/walletpro/v1/redemption-codes
Content-Type: application/json
{
"code": "SUMMER25",
"credit_type": "fixed",
"credit_amount": "15.00",
"currency": "USD",
"usage_limit": 500,
"usage_limit_per_user": 1,
"expiry_date": "2026-08-31",
"status": "active"
}
Response (201 Created):
{
"id": 42,
"code": "SUMMER25",
"credit_type": "fixed",
"credit_amount": "15.00",
"currency": "USD",
"usage_limit": 500,
"usage_count": 0,
"usage_limit_per_user": 1,
"expiry_date": "2026-08-31T23:59:59+00:00",
"status": "active",
"created_at": "2026-06-20T10:00:00+00:00"
}
Redeem a Code (Customer)
POST /wp-json/walletpro/v1/redemption-codes/redeem
Content-Type: application/json
X-WP-Nonce: {nonce}
{
"code": "SUMMER25"
}
Success response (200 OK):
{
"success": true,
"credit_applied": "15.00",
"currency": "USD",
"new_balance": "65.00",
"transaction_id": 1087
}
Error response (422 Unprocessable Entity):
{
"code": "walletpro_redemption_failed",
"message": "This code could not be applied. Please check the code and try again.",
"data": { "status": 422 }
}
Get Redemption History for a Code
GET /wp-json/walletpro/v1/redemption-codes/42/history?per_page=25&page=1
WP-CLI
# Create a redemption code
wp wallet code create --code=LAUNCH50 --type=fixed --amount=10.00 --limit=200 --expiry="2026-12-31"
# Generate 1000 unique codes in bulk
wp wallet code generate --count=1000 --prefix=GIFT- --type=fixed --amount=5.00 --export=./codes.csv
# Deactivate a code
wp wallet code update SUMMER25 --status=inactive
# Get usage stats for a code
wp wallet code get SUMMER25
# List all active codes with usage counts
wp wallet code list --status=active --format=table
# Manually redeem a code on behalf of a customer
wp wallet code redeem SUMMER25 --user=42
Hooks and Filters
Filter: Validate a code before redemption
/**
* Add custom validation logic before a redemption code is applied.
*
* @param WP_Error|true $result Pass WP_Error to reject, or true to allow.
* @param array $code_data The code record from the database.
* @param int $user_id The redeeming customer's user ID.
*/
add_filter( 'walletpro_validate_redemption_code', function( $result, $code_data, $user_id ) {
// Example: require customer to have placed at least one order.
$order_count = wc_get_customer_order_count( $user_id );
if ( $order_count === 0 ) {
return new WP_Error(
'walletpro_no_prior_orders',
'You must have placed at least one order to redeem this code.'
);
}
return $result;
}, 10, 3 );
Action: After a code is successfully redeemed
/**
* Fires after a redemption code is applied and wallet balance updated.
*
* @param int $user_id The customer who redeemed the code.
* @param array $code_data The full code record.
* @param string $credit_applied The amount actually credited.
* @param int $transaction_id The wallet transaction ID.
*/
add_action( 'walletpro_redemption_code_applied', function( $user_id, $code_data, $credit_applied, $transaction_id ) {
// Example: tag the user in your CRM.
my_crm_tag_user( $user_id, 'redeemed_code_' . $code_data['code'] );
}, 10, 4 );
Filter: Modify the credit amount before it is applied
/**
* Adjust the credit amount for a redemption code.
*
* @param string $credit_amount The calculated credit as a numeric string.
* @param array $code_data The code record.
* @param int $user_id The redeeming customer.
* @return string Modified credit amount.
*/
add_filter( 'walletpro_redemption_credit_amount', function( $credit_amount, $code_data, $user_id ) {
// Example: double the credit for VIP customers.
if ( in_array( 'vip_customer', (array) wp_get_current_user()->roles ) ) {
$credit_amount = (string) ( (float) $credit_amount * 2 );
}
return $credit_amount;
}, 10, 3 );
The walletpro_validate_redemption_code filter runs before the rate-limit counter is incremented. Return a WP_Error from this filter for business-logic rejections that should not count against the customer's failed-attempt tally. Rate limiting is enforced independently by the endpoint layer before this filter is called.
Exporting Code Data
To export all codes and their redemption counts to CSV, go to WooCommerce > WalletPro > Redemption Codes, apply any filters you need (status, date range), then click Export Filtered Codes (CSV) in the screen toolbar.
The export includes: code string, credit type, credit amount, currency, usage limit, usage count, per-customer limit, expiry date, status, created date, and total credit value distributed to date.
Individual code redemption histories can also be exported from each code's edit screen (see Redemption History above). For a combined transaction-level export across all codes, use the GL-friendly CSV export at WooCommerce > WalletPro > Reports > Export Transactions and filter by transaction type Redemption Code.
```