---
title: Return Abuse Detection
description: "The Return Abuse Detection module is the heart of TrustLens for most stores. Returns are the single largest source of preventable margin loss in WooCommerce — serial returners, wardrobing customers, and refund-fraud rings often hide in plain sight across hundreds…"
url: "https://webstepper.io/docs/trustlens/detection-modules/return-abuse-detection/"
updated: "2026-10-18"
category: Detection Modules
---

# Return Abuse Detection

The Return Abuse Detection module is the heart of TrustLens for most stores. Returns are the single largest source of preventable margin loss in WooCommerce — serial returners, wardrobing customers, and refund-fraud rings often hide in plain sight across hundreds of orders. The Returns module turns refund data your store already generates into a clear, sortable customer-level view of who's costing you money.

Module ID: `returns`. Default: enabled. Free tier (complete).

---

## What It Observes

Refunds are recorded by TrustLens's refund ledger, which counts every refund exactly once — full, partial, cumulative, edited and deleted refunds, whether they come from the WooCommerce admin or the REST API. When an order is refunded, the ledger:

1. Records the refund amount, the order total, the reason text and the order's delivery, coupon and item context
2. Rebuilds the customer's refund counters: `total_refunds` (distinct refunded orders), `full_refunds` / `partial_refunds`, `total_refund_value`, `coupon_then_refund` and `last_refund_date`
3. Refreshes `return_rate` as refunded orders ÷ counted orders (a refunded order always joins the counted set, so the rate can't exceed 100%)
4. Logs a `full_refund` or `partial_refund` event to the timeline
5. Queues an asynchronous score recalculation

An order counts as "fully refunded" when its cumulative refunds reach the order total (within a rounding allowance of a fraction of a cent). Anything less is "partial." This distinction matters for the wardrobing rule.

---

## What It Signals

The module emits **one** Returns signal. Since 1.3.16–1.3.18 it is built from a contextual return-risk profile rather than a single lifetime rate: rules add raw points, the total is multiplied by the product-risk multiplier (0.5×–2×, default 1.0× — see [Category-Aware Risk](/docs/trustlens/detection-modules/category-aware-risk/)) and by a sample-size confidence factor, and the result is capped at **-50**.

**Scoring window:** the last 90 days when the customer has counted orders in that window, otherwise their lifetime history. **Store baseline:** your store-wide return rate, so a customer is judged against what's normal for your store.

### Return Rate Tier (Primary)

Mutually exclusive — only one tier applies.

| Return Rate in the Scoring Window | Raw points |
| --- | --- |
| ≥ critical threshold (60%), or ≥ 50% and at least 3× the store baseline | 30 |
| ≥ high threshold (40%), or ≥ 30% and at least 2× the store baseline | 20 |
| ≥ 25% | 10 |
| Below 25% | 0 |

Reason shown on the profile: *"5 of 9 eligible orders were refunded in the scoring window (56%; store baseline 8.0%; confidence 83%)"*. The critical and high thresholds are configurable in **Settings → Refunds → Return Risk Thresholds**; the 25% tier and the baseline multiples are fixed in code. There is no positive "excellent return history" bonus — a low return rate simply adds nothing.

### Refund Value Ratio

Refund value as a share of the customer's completed purchase value, compared within the same currency — so it is relative to what the customer spent, not an absolute dollar amount.

| Refund Value ÷ Purchase Value | Raw points |
| --- | --- |
| ≥ 75% | 15 |
| ≥ 50% | 10 |
| ≥ 30% | 5 |

### Wardrobing and Other Return Patterns

These use delivery and item-return evidence captured by the ledger. The classic "buy, wear, return" cycle is caught by the first rule.

| Trigger | Raw points | Reason Shown on Profile |
| --- | --- | --- |
| 2 delivered orders fully refunded with item-level return evidence | 8 (12 at 3+) | "3 delivered orders with item-level return evidence were fully refunded" |
| 2+ delivered, evidenced partial refunds of at least 80% of the order value | 5 | "2 delivered, evidenced partial returns refunded at least 80% of their order value…" |
| 2+ evidenced returns refunded at 80%+ of the return window (day 24+ of the default 30 days) | 5 | "2 evidenced returns were requested near the end of the return window…" |
| The same refund reason on 3+ refunded orders | 5 | "The refund reason “too small” repeats across 3 refund records" |
| 3+ refunded orders used coupons or store credit, and the rate is at or above the high threshold | 4 | "3 refunded orders used coupons or store credit" |
| 2+ strongly linked accounts also have refunded orders, and the rate is at or above the high threshold | 5 | "2 strongly linked accounts also have refunded orders" |

Full refunds with no delivery evidence (cancelled before shipping) and shipping-only refunds are listed in the reason text but kept out of these post-delivery pattern rules, so a store's own pre-fulfillment cancellations don't read as abuse.

### Confidence and the Cap

The raw total is multiplied by a confidence factor based on how many counted orders are in the scoring window — about 18% at 1 order, 45% at 3, 63% at 5, 86% at 10 and 95% at 15 — then by the product-risk multiplier, and capped at -50. Example: a 65% rate (30) with refunds worth 80% of purchases (15) and 3 fully refunded delivered orders (12) is 57 raw points; at 10 orders and the default 1.0× multiplier that is 57 × 0.86 ≈ **-49**.

---

## Customers With Few Orders

The Returns module is the one module that keeps scoring below the Full-confidence Order Threshold (**Settings → General**, default 3 orders). Instead of a hard cut-off, the confidence factor keeps small samples small: a single refund on a single order is a 100% rate, but at 18% confidence the rate tier's 30 raw points become about -5 (about -8 once a full refund's value points are added). As the customer places more orders, the same pattern carries more weight.

---

## Settings

| Setting | Default | Description |
| --- | --- | --- |
| **Critical risk** (return rate) | 60% | Return rate at or above this earns the 30-point tier (20–100; never lower than High risk) |
| **High risk** (return rate) | 40% | Return rate at or above this earns the 20-point tier (10–90) |
| **Module enabled** | On | Master toggle for Return Abuse Detection scoring (Settings → Detection) |

To adjust the thresholds, go to **TrustLens → Settings → Refunds → Return Risk Thresholds**. Category multipliers live on the same screen under **Product Risk by Category**.

---

## Tuning for Your Industry

Default thresholds are sensible for general retail. Industries with naturally higher return rates need adjustment:

| Industry | Typical Baseline Return Rate | Suggested Thresholds |
| --- | --- | --- |
| General retail | 5–12% | Defaults: 60 / 40 |
| Electronics | 3–8% | Tighter: 50 / 30 |
| Apparel (general) | 15–25% | Looser: 70 / 50 |
| Apparel (fashion / fit-critical) | 20–40% | Much looser: 80 / 60 |
| Shoes | 20–35% | Looser: 75 / 55 |
| Beauty / cosmetics | 3–8% | Tighter: 50 / 30 |
| Home goods | 8–15% | Defaults work; consider 65 / 45 |
| Digital / subscription | 1–5% | Tighter: 40 / 20 |

The principle: thresholds should be set so that the worst 5–10% of your customers (by return rate) reach the high tier, not the median customer. The store-baseline route adapts on its own — in a store where 20% of orders are refunded, reaching the high tier through the baseline takes a 40% rate (2× the baseline). If you're seeing 30% of your customer base in Caution or Risk, your thresholds are too tight.

---

## Common Patterns

### The Serial Returner

**Signature:** 30+ orders, 50%+ return rate, refunds spread across many small orders.

**Signals:** Critical (30 raw) or high (20 raw) rate tier, usually plus refund-value points. With 30+ orders the confidence factor is close to 100%.

**Profile:** Lands in Risk or Critical, typical Returns penalty -30 to -50.

### The Wardrobing Customer

**Signature:** Moderate order count, 40–60% return rate, delivered orders refunded in full with items returned. Buys expensive items, returns them late in the return window.

**Signals:** High rate tier (20) + 3+ delivered full refunds (12) + refund value (10–15) + late returns (5) raw points — roughly -35 to -45 from Returns once the customer has 8–10 orders.

**Profile:** Lands in Risk. Particularly common in apparel and electronics.

### The Defective-Item Cluster

**Signature:** Multiple customers with elevated return rates concentrated in a specific product or category.

**Signals:** Per-customer Returns signals, raised by the product-risk multiplier once the SKU's own return rate is high (Category-Aware Risk never adds a separate penalty).

**Profile:** Look for the "high SKU return rate" driver in the Returns reason text and check your WooCommerce returns by product — if a product or category shows store-wide elevated returns, the issue is the product, not the customers. *Don't* punish customers for legitimate defective-item returns; investigate the SKU.

### The Refund-Fraud Ring

**Signature:** Multiple linked accounts (same address/phone/payment method), each with high return rates, coordinated refund timing.

**Signals:** Returns signals per account (plus 5 raw points when 2+ linked accounts also have refunds), Linked Accounts -5 to -15 plus 5 per linked account already in Risk/Critical, Coupons signals often present too.

**Profile:** Multiple Critical-tier accounts linked together. Investigate as a ring, not individuals.

---

## False-Positive Watch List

The Returns module is generally high-signal, but certain patterns can produce misleading scores. Watch for:

- **Customers with one large refund and few orders.** A single $5,000 refund on 4 orders shows a 25% rate. Check whether this is a legitimate large transaction (B2B order, custom build) before flagging.
- **Customers buying in bulk to choose-and-return.** Apparel customers ordering 5 sizes intending to keep one is a sales channel choice, not abuse. If your store allows this explicitly, raise the thresholds.
- **Recently-recovered customers.** For customers with orders in the last 90 days the rate uses that window, so an old spike fades out. A customer with no recent orders is scored on lifetime history and may still be carrying an old spike. Consider manual review for borderline cases.
- **Customers stuck just above 25%.** The boundary is sharp. A 25.1% return rate earns the 10-point tier (up to -10 after confidence); 24.9% earns nothing. If borderline customers feel unfair, soften the Returns signal via the `trustlens/score_signals` filter.

---

## Disabling the Module

Disabling Returns is almost never recommended — it's the highest-signal module. The only realistic use case is: you've completely rebuilt scoring around external data (CRM, dedicated fraud platform) and Returns signals are interfering with your custom logic. Even then, consider softening the Returns signal in your custom code via `trustlens/score_signals` rather than turning off the module.

---

## What Happens When You Disable It

Since 1.3.20, turning Return Abuse Detection off silences *scoring* only:

- No Returns signals contribute to scores
- The refund ledger keeps recording every refund — `total_refunds`, `return_rate`, refund value and the timeline events keep updating, so dashboards, reporting and Refund Defense are unaffected
- The return-risk thresholds stay available under Settings → Refunds

Because the history is never interrupted, re-enabling scores customers on their full refund history, including refunds made while the module was off.

---

## Reading the Returns Section of a Profile

On the Customer Detail page, the Returns module's contribution shows up in two places:

1. **The signal breakdown** — one row tagged with the `returns` module ID, with its score and every reason that contributed
2. **The order-cohort return rate chart** — a 12-week view of how the customer's return rate has moved

The stat tiles above them show orders, return rate and refund value, and the reason text includes the counts, store baseline and confidence used, so you can follow the calculation by hand.

---

## API Access

The Returns module's data is part of the customer record and is accessible via REST:

```
GET /wp-json/trustlens/v1/customers/{email_hash}
```

Response includes `total_refunds` / `refunded_orders` (distinct refunded orders), `return_rate`, `total_order_value`, `total_refund_value` and a `refund_amounts` summary. See [REST API Reference](/docs/trustlens/developer-documentation/rest-api-reference/).
