> For the complete documentation index, see [llms.txt](https://docs.xandtech.fr/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.xandtech.fr/home/xplayercurrencies/features/fraud-detection.md).

# Fraud Detection

An anti-dupe/exploit safety net that watches every **income** balance change (shop sells, kill coins, bank interest, cheque redeems, Vault deposits, etc.) for patterns a legitimate player could never produce, and can automatically block them.

{% hint style="info" %}
This is a global, `config.yml`-level system (`fraud-detection`), not per-currency - it applies to every currency at once, scaling its size-based rules to each currency's own `max-balance`.
{% endhint %}

## How it works

It hooks into the exact same event every balance mutation already passes through (`CurrencyBalanceChangeEvent`, see [API & Events](/home/xplayercurrencies/developer/api.md)), tracking a rolling window of recent gains per player, per currency. Two kinds of rules can trip:

1. **Frequency** - more separate income transactions than allowed within the time window. Works for every currency regardless of scale - the main defense against a sell/kill-coin macro or packet exploit.
2. **Size** - a single gain, or the cumulative total within the window, bigger than a percentage of that currency's own `max-balance`. Skipped entirely for a currency with no `max-balance` set (unlimited).

Admin-issued reasons (give/take/set/reset, bank admin actions, one-time imports) are always trusted and never checked.

## Configuration

```yaml
fraud-detection:
  enabled: true
  exempt-reasons:
    - GIVE
    - TAKE
    - SET
    - RESET
    - BANK_ADMIN_GIVE
    - BANK_ADMIN_TAKE
    - BANK_ADMIN_SET
    - BANK_ADMIN_RESET
    - BANK_ADMIN_SET_TIER
    - MIGRATION_IMPORT
  window-seconds: 10
  max-transactions-per-window: 20
  max-single-gain-percent: 20
  max-cumulative-gain-percent: 50
  action: CANCEL_AND_FREEZE
  freeze-duration-seconds: 300
  kick-on-freeze: false
  notify-permission: xplayercurrencies.admin.fraud.alerts
```

| Key                           | Description                                                                                                                                         |
| ----------------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------- |
| `exempt-reasons`              | Balance-change reasons never checked.                                                                                                               |
| `window-seconds`              | The sliding time window the two rules below look back over.                                                                                         |
| `max-transactions-per-window` | More than this many separate income transactions within the window = flagged. Set `-1` to disable.                                                  |
| `max-single-gain-percent`     | A single gain bigger than this % of a currency's `max-balance` is flagged instantly. `-1` to disable.                                               |
| `max-cumulative-gain-percent` | Total gains within the window bigger than this % of `max-balance` is flagged, even if no single gain alone tripped the rule above. `-1` to disable. |
| `action`                      | What happens once a rule trips - see below.                                                                                                         |
| `freeze-duration-seconds`     | How long a `CANCEL_AND_FREEZE` freeze lasts.                                                                                                        |
| `kick-on-freeze`              | Also kick the player the instant they get frozen, on top of everything else. Off by default - a freeze alone already stops further gain.            |
| `notify-permission`           | Who receives the live in-game alert (see below).                                                                                                    |

### Actions

| `action`            | Effect                                                                                                                                                                                       |
| ------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `NOTIFY_ONLY`       | Lets the gain through, just alerts/logs it.                                                                                                                                                  |
| `CANCEL`            | Blocks that one gain, alerts/logs it, nothing else.                                                                                                                                          |
| `CANCEL_AND_FREEZE` | Blocks it **and** stops that player earning that currency at all for `freeze-duration-seconds` - spending and admin actions are never affected, only further income is refused while frozen. |

## Alerts & logs

A flagged attempt is broadcast in chat to whoever holds `notify-permission` (default `xplayercurrencies.admin.fraud.alerts`, `op`), always logged to console/the log file regardless of who's online, and recorded like any other transaction - visible in `/currencies admin logs <player>` under the "Fraud alerts" filter.

## Manual control

```
/currencies admin fraud freeze <player> <currency> [seconds]
/currencies admin fraud unfreeze <player> <currency>
/currencies admin fraud status <player> <currency>
```

Requires `xplayercurrencies.admin`. `freeze` defaults to `freeze-duration-seconds` if no explicit duration is given. Works on an offline player too.

Next: [Commands reference](/home/xplayercurrencies/reference/commands.md).


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter, and the optional `goal` query parameter:

```
GET https://docs.xandtech.fr/home/xplayercurrencies/features/fraud-detection.md?ask=<question>&goal=<endgoal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is optional and describes the broader end goal you are ultimately trying to accomplish on behalf of the user. GitBook uses it to tailor the answer towards what is most useful for that goal.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
