ajdnikov Dashboard

AnziUtils Documentation

Version 1.7.6Platform Paper 1.21+Java 21Storage SQLite or MySQLNetwork Redis

Welcome to the AnziUtils wiki! AnziUtils is an all-in-one administrative utility and security plugin offering VPN detection, alt-limiting, geolocation filters, combat logging, a custom grave system, dual staff profiles, network-wide staff tooling, and much more. Below you will find a complete breakdown of all modules, commands, permissions, and configuration options required to run the plugin optimally on your server.

Getting Started

AnziUtils runs on a single server out of the box and scales up to a full BungeeCord/Velocity network once you add MySQL and Redis.

Requirements

  • Java 21 or higher
  • Paper (or a Paper fork) running Minecraft 1.21+ — the plugin targets api-version: '1.21'
  • PacketEvents 2.x installed as its own plugin — a required dependency since 1.4 (see below)
  • A valid AnziUtils license key (issued in the Discord — see /claim)
  • Outbound internet access for GeoIP, VPN lookups, and license verification

Optional Integrations (softdepend)

PluginWhat it unlocks
WorldGuardCombat-log safe zones via combat-log.safe-zone-regions
PlaceholderAPIThe anziutils placeholder expansion
LuckPermsStaff target hierarchy and staff-profile rank separation
VaultStaff-profile balance separation

Required: PacketEvents

Since 1.4, AnziUtils declares depend: [packetevents], so the server will not load it without PacketEvents. It is used for the packet-level features: hiding vanished staff from other players' clients, ghosting staff-mode teleports, reduced debug info (F3 coordinates) in staff mode, and hiding a combat opponent's health. Built against PacketEvents 2.13.0; install the PacketEvents build for your server version.

Everything else is bundled. MySQL and Redis are optional external services used only for network setups.

Installation & License

Step 1: Download

Download the latest AnziUtils JAR file from the BuiltByBit release page.

Step 2: Install

  1. Stop your Minecraft server
  2. Navigate to your server's plugins/ directory
  3. Place the AnziUtils JAR file in this directory, together with the PacketEvents JAR
  4. Start your server once to generate the configuration files

Step 3: AnziLock License Setup

AnziUtils is protected by AnziLock, a signed license client that verifies your key against license.ajdnikov-dev.com on startup and then keeps a low-frequency heartbeat running in the background. Insert the key you received via Discord (see the /claim command in the Discord server) into plugins/AnziUtils/config.yml:

license:
  key: "YOUR_LICENSE_KEY_HERE"

AnziLock caches the last signed verification, so a brief outage of the license server will not take your server down — the plugin keeps running on the cached result for the duration of the offline grace period. If the key is missing or invalid, the plugin applies the configured failure action and logs the reason to the console.

Automatic Updates

Since 1.7.4, AnziUtils updates itself. When a new version is released, it checks your license again, downloads the new jar into plugins/update, and the server loads it on the next restart. The file is kept only if its size and checksum match the signed license answer. Nothing changes while the server is running.

  • Turn it off with auto-update: false in config.yml.
  • Players with anziutils.updates (ops by default) are told on join when a new version is waiting for a restart.
  • New settings are added to config.yml, messages.yml, discord.yml and rules.yml on start, with their comments. Your values stay, and the old file is kept as .bak.
  • Coming from 1.7.3 or older? Install 1.7.4 or newer by hand once. Every later version arrives by itself.

How the download is checked: AnziLock → Automatic Updates.

Support Dumps

Since 1.7.6, /au dump makes a private link for support. The page shows AnziUtils's own log next to the full server log, and your server's setup: software and version, uptime, TPS, RAM, disk, CPU, Java, worlds, every plugin, and config.yml and discord.yml with keys, passwords and webhooks blanked out. Only you see the link in chat: click it, or click [Copy], and send it to whoever helps you on Discord.

  • /au dump 6 covers only the last 6 hours. /au dump local uploads nothing and saves the dump in plugins/AnziUtils/dumps/ as a readable .txt and a .json.gz.
  • On the page you can filter and search both logs, show only the lines about AnziUtils (stack traces included), and save everything to your PC as .txt or .json. A saved .json opens again at license.ajdnikov-dev.com/dump after the link has expired.
  • The link works for dump.link-hours (24 by default, at most 168). You can remove it sooner on your licence page under Dumps.
  • IP addresses are replaced with x.x.x.x unless you set dump.hide-ips: false.
  • Needs anziutils.dump (ops by default).
dump:
  # Hours of AnziUtils's log to keep on disk (dump-logs/) and put in a dump.
  log-hours: 48
  # How long the link works, in hours (at most 168).
  link-hours: 24
  # Replace IP addresses in the logs with x.x.x.x.
  hide-ips: true

What a dump contains and how long it is kept: AnziLock → Support Dumps.

Step 4: Configuration

Edit the generated files in plugins/AnziUtils/:

  • config.yml — every module, database, Redis, and staff setting
  • messages.yml — every player-facing message
  • discord.yml — the webhook URL and per-event notification toggles
  • rules.yml — the contents of the automatic rule book

Apply changes without a restart using /au reload.

Database

AnziUtils stores IP history, geolocation results, alt links, staff profiles, and staff sessions in a database. Two backends are supported.

SQLite (default)

Zero setup. Keep database.type: sqlite for a single standalone server.

MySQL (networks)

On a BungeeCord/Velocity network, point every backend server at one shared MySQL database so IP history, alt limits, and staff profiles are tracked network-wide.

database:
  type: mysql
  mysql:
    host: mysql.example.com
    port: 3306
    database: anziutils
    username: anziutils
    password: "CHANGE_THIS_PASSWORD"
    use-ssl: false
    fallback-to-sqlite: false
    pool:
      maximum-pool-size: 10
      minimum-idle: 2
      connection-timeout-ms: 10000
      idle-timeout-ms: 600000
      max-lifetime-ms: 1800000

Create the database and user first:

CREATE DATABASE anziutils CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci;
CREATE USER 'anziutils'@'%' IDENTIFIED BY 'CHANGE_THIS_PASSWORD';
GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, INDEX, ALTER ON anziutils.* TO 'anziutils'@'%';
FLUSH PRIVILEGES;

Keep fallback-to-sqlite: false on networks. If MySQL goes down, a silent fallback would let one backend start writing to a local SQLite file and split your network state. With the fallback disabled the plugin disables itself safely instead.

Backend servers must also receive the real player IP from the proxy — set ip_forward: true on BungeeCord or configure player-info-forwarding-mode on Velocity.

Redis Network Synchronization

Redis is optional on a single server and recommended on a network. It synchronizes:

  • Network-wide panic mode
  • Shared smart-mutes
  • A live online-player registry used by /au gui and /au panel
  • Cross-server staff action routing (freeze, bring, back, announce, cleardrops, spectate, panic actions)
  • Instant return of combat-log items when a logger survives
  • Cached GeoIP and VPN lookup results
  • Cross-server security alerts

Every backend must share the same Redis host, database, and key prefix — but each needs a unique server-id.

redis:
  enabled: true
  host: redis.example.com
  port: 6379
  username: ""
  password: "CHANGE_THIS_PASSWORD"
  database: 0
  use-ssl: false
  timeout-ms: 5000
  key-prefix: "anziutils"
  server-id: "survival-1"         # unique on every backend
  heartbeat-seconds: 10
  registry-ttl-seconds: 30
  session-grace-seconds: 20
  action-timeout-seconds: 30
  spectate-lock-seconds: 45
  proxy-server-name: "survival-1" # name registered on the proxy
  cache:
    geo-ttl-seconds: 86400
    vpn-ttl-seconds: 3600

For Velocity, also enable BungeeCord-compatible plugin messaging in velocity.toml so the Connect messages used by network transfers work:

bungee-plugin-message-channel = true

Security: never expose Redis to the public internet. Keep it on a private network, require a password or ACL user, and enable TLS when Redis traffic leaves a trusted network.

Backend Switches vs. Network Leaves

With Redis enabled, moving between backends is recognized as a backend switch rather than a fresh join: rule books, VPN/GeoIP checks, database join rows, and join notifications are not repeated. Staff see a notification for the initial network join, and again only after the player has been gone for the full session-grace-seconds window.

World-local systems — combat loggers, graves, redstone limiting, and automatic item-clear cycles — always stay on the backend they belong to.

Local Fallbacks

Every Redis-backed feature has a local fallback. If Redis is disabled or offline, the plugin keeps working on a per-server basis.

Security & Access Control

VPN / Proxy Detection

Connecting IPs are checked against proxycheck.io. Results are cached in Redis when it is enabled.

vpn-detection:
  enabled: true
  # true = kick the player, false = warn staff but let them join
  kick-on-vpn: true
  kick-message: "&cVPN/Proxy connections are not allowed on this server."

When kick-on-vpn is false, the player is allowed in but staff with anziutils.notify are warned — and, if smart-mute.mute-on-vpn-warn is enabled, the player is silently muted for the configured duration.

Alt Account Limiter

Restricts how many distinct accounts may connect from a single IP address, blocking botnets and ban evaders.

alt-limit:
  enabled: true
  max-accounts-per-ip: 3
  kick-message: "&cToo many accounts have connected from your IP address."

Country Filter (GeoIP)

Geolocation is resolved through ipwho.is. Use full country names exactly as that service returns them (for example "Slovenia" or "Germany") — not two-letter codes.

country-filter:
  # 'disabled', 'whitelist' (only these may join), or 'blacklist' (these are blocked)
  mode: disabled
  kick-message: "&cYou are not allowed to join from your country."
  countries:
    - "Slovenia"
    - "Croatia"
    - "Austria"

IP Exemptions

Two independent exemption paths bypass VPN detection and alt-limit checks entirely. The first is an IP list:

exempt-ips:
  - "127.0.0.1"

The second is the anziutils.exempt permission, which exempts the player wherever they connect from.

Panic Mode & Smart Mute

Panic Mode

Turn on an emergency lockdown with /au panic on when the server is hit by a bot raid, and lift it with /au panic off. With Redis enabled the state is published network-wide, so one toggle locks down every backend. Toggling notifies every online player with anziutils.notify or anziutils.admin, writes a console warning, and fires a Discord webhook. /au panic status shows whether it is on, which restrictions apply, and every configured action.

Panic mode has two halves: restrictions that tighten who can join and chat, and actions that do something to players — move them to another backend, kick them, show a title, broadcast, or run console commands.

Restrictions

Each restriction can be switched on or off on its own:

panic-mode:
  restrictions:
    country-whitelist: true       # only these countries may join
    allowed-countries:
      - "Slovenia"
    alt-limit: true               # tighten the alt limit
    max-accounts-per-ip: 1
    mute-new-players: true        # mute players who joined recently
    mute-new-players-minutes: 5

  # A player counts as "new" (target: new-players) if their first ever
  # join on the network was less than this many minutes ago.
  new-player-minutes: 60
  # Players with this permission are never touched by panic actions.
  bypass-permission: "anziutils.panic.bypass"

Actions

Actions are listed under three triggers:

TriggerRuns
on-enableOnce, when panic mode turns on
on-joinFor every player who joins a backend while panic mode is on
on-disableOnce, when panic mode turns off
TypeDoesKeys
sendMoves the targets to another backend through the proxyserver: proxy server name
kickKicks the targetsmessage: kick reason
messageChat message to the targetsmessage:
titleOn-screen title for the targetstitle:, message: (subtitle)
broadcastChat message to everyonemessage:
commandConsole command. With {player} it runs once per targetcommand:

Options available on every action:

OptionValuesDefault
targetall, non-staff, new-players, staffnon-staff
delaySeconds to wait before running0
serversOnly run on these server-ids, e.g. [lobby-1]every server
scopenetwork — every backend runs it for its own players; origin — only the server that toggled panicnetwork (origin for command)

Example — park new players in a limbo server during a raid, kick new players who try to come back to survival, and send everyone in limbo to the lobby once it is over:

panic-mode:
  actions:
    on-enable:
      - type: title
        target: new-players
        title: "&c&lLOCKDOWN"
        message: "&7Moving you to a waiting area..."
      - type: send
        target: new-players
        server: limbo
        delay: 3
    on-join:
      - type: kick
        target: new-players
        message: "&cThe server is in lockdown. Please try again in a few minutes."
        servers: [survival-1]
    on-disable:
      - type: send
        target: all
        server: lobby
        servers: [limbo]

send uses the same proxy messaging as the other network transfers, so on Velocity it needs bungee-plugin-message-channel = true.

Upgrading: the old flat keys (panic-mode.allowed-countries, panic-mode.max-accounts-per-ip, panic-mode.mute-new-players-minutes) are still read when panic-mode.restrictions is missing.

Smart Mute

Suspicious joins are silently muted — blocked from chat and from chat-driven commands — for a limited window, without an obvious kick that tells an attacker what tripped.

smart-mute:
  # Mute players who join on a VPN when kick-on-vpn is false
  mute-on-vpn-warn: true
  mute-duration-minutes: 5

Smart mutes are shared across the network through Redis.

Combat Logging

Players are combat-tagged when they enter PvP and see a live action bar timer. Disconnecting while tagged spawns a combat logger NPC that can be killed for the player's loot — safely across a whole BungeeCord/Velocity network, without item duplication.

Configuration

combat-log:
  enabled: true
  timer: 15                 # combat duration in seconds

  logger:
    mode: npc                     # npc = zombie stand-in, instant-death = kill on logout
    duration-seconds: 30          # how long the NPC stays (0 = same as timer)
    network-takeover-seconds: 60  # crash recovery window, see below

  graves: combat            # always | combat | off (see Graves)

  # Combat restrictions
  disable-enderpearls: true
  disable-golden-apples: true
  disable-chorus-fruit: true
  disable-totems: false
  disable-inventory-open: true
  disable-flying: true

  block-world-change: true
  block-server-switch: true

  post-combat-cooldown:          # see Post-Combat Cooldown below
    enabled: false
    seconds: 10
    block-commands: true
    allowed-commands: ["msg", "r", "tell", "w", "reply"]
    block-world-change: true
    block-teleports: true
    block-server-switch: true

  blocked-commands:
    - "home"
    - "spawn"
    - "tp"
    - "tpa"
    - "tpaccept"
    - "warp"
    - "auback"
    - "sethome"
    - "rtp"
    - "wild"

  safe-zone-regions:
    - "spawn"
    - "safezone"

  block-region-entry:            # keep tagged players out of regions
    enabled: true
    regions: []                  # empty = use safe-zone-regions
    knockback: true
    knockback-strength: 1.0

  join-grace-period: 3          # seconds after joining where tagging is impossible
  grave-protection-minutes: 5    # owner/killer-only looting window (more grave keys: see Graves)

Hidden Opponent Health

While two players are combat-tagged against each other, each one's client is told the other is at full health, so health-indicator mods and resource packs cannot show how close an opponent is to dying. Players who are not fighting each other still see real health. It is on by default and is not in the generated config.yml; add the key to turn it off:

combat-log:
  hide-health: false   # default: true

Network Combat Logging (Dupe-Proof)

The moment a tagged player disconnects — or switches backend through the proxy — their inventory and XP are moved out of the player and into the shared database (combat_escrow table). The items now exist in exactly one place, and each escrow can only be claimed once:

  • Logger killed: the items go into a grave, and the player dies on their next join — on any backend of the network.
  • Logger survives (or the player rejoins the same backend in time): the items are given back wherever the player is — instantly over Redis, otherwise within a few seconds.
  • Backend crashes: the escrow is recovered when that server starts again, or another backend takes it over after network-takeover-seconds and returns the items.

With logger.mode: instant-death no NPC is spawned; the player is treated as killed straight away.

Network requirements: every backend must use the same MySQL database and a unique redis.server-id — set it even if Redis itself is disabled. If you also run an inventory-sync plugin, make sure it saves after AnziUtils on quit; AnziUtils empties the inventory at LOWEST priority.

Anti-Escape Restrictions

Each restriction has its own bypass permission, so you can loosen individual rules for specific ranks:

  • Enderpearls
  • Golden Apples
  • Chorus Fruit
  • Totems of Undying
  • Creative flight and elytra gliding
  • Opening containers and the inventory
  • Blocked commands such as /tp, /spawn, /home
  • World changes — portals and plugin teleports (block-world-change)
  • Backend server switches through AnziUtils network transfers (block-server-switch)
  • Entering WorldGuard regions such as spawn (block-region-entry, see below)

Note on server switches: block-server-switch covers AnziUtils' own transfers (/au back, /au bring, /au spectate). A player who leaves the backend another way — a proxy /server command, for instance — is still treated as a combat logger, and the NPC spawns on the backend they left.

WorldGuard Safe Zones

Region names listed under safe-zone-regions (case-insensitive) never apply a combat tag, so players can move through spawn and protected areas safely. Requires WorldGuard.

Blocking Region Entry

A safe zone is no use if a player can run into it mid-fight. With block-region-entry, combat-tagged players cannot enter the listed regions: walking, riding, ender pearls, chorus fruit, and teleports into them are all stopped. Leaving a region is always allowed. Requires WorldGuard.

The border works like a wall: a player who reaches it stops and bounces back a little. It never lifts anyone into the air. Players knocked into it by a hit, an explosion or a wind charge only stop, so they are not thrown back at their attacker. Since 1.7.5, a vanilla "Flying is not enabled" kick right after the border stopped someone is not counted as combat logging.

  • regions: region names (case-insensitive). Leave it empty to use your safe-zone-regions.
  • knockback / knockback-strength: also shove players who walk into the border back out, sideways only. 1.0 is about two blocks, 2.0 about four.
  • Bypass: anziutils.combatlog.bypass.regionentry (or the universal anziutils.combatlog.bypass).

It is on by default, including on configs from before 1.7.3 that have no block-region-entry block. Set enabled: false to turn it off.

Post-Combat Cooldown

An optional cooldown that starts when a combat tag ends: the timer ran out, or the opponent died or their combat logger was killed. It stops a player from winning a fight and instantly running /home, /spawn, or /server. The remaining time shows on the action bar. Getting hit again replaces the cooldown with a normal combat tag.

combat-log:
  post-combat-cooldown:
    enabled: false        # off by default
    seconds: 10
    block-commands: true  # every command except allowed-commands
    allowed-commands:
      - "msg"
      - "r"
      - "tell"
      - "w"
      - "reply"
    block-world-change: true    # portals and teleports into another world
    block-teleports: true       # /tp, /home, /warp... in the same world (pearls and chorus fruit still work)
    block-server-switch: true   # AnziUtils network transfers (/au back, /au bring, /au spectate, panic moves)

Bypass: anziutils.combatlog.bypass.cooldown (or anziutils.combatlog.bypass). Show the remaining time on a scoreboard with %anziutils_pvp_cooldown%.

Join Grace Period

join-grace-period blocks combat tagging for the first few seconds after joining, preventing spawn-kill loops. Set it to 0 to disable.

Secure Player Graves

Instead of scattering items on the ground, a death can spawn a player-head grave at the death location. combat-log.graves decides which deaths do:

ModeGrave is spawned
alwaysOn every player death, and when a combat logger is killed
combat (default)Only when a player dies while combat-tagged, or a combat logger is killed
offNever — items and XP drop on the ground like vanilla

Graves work in always mode even when combat tagging itself is disabled.

How It Works

  1. A player dies (in combat, or any death in always mode), or their combat logger is killed
  2. Their items and XP are collected into a grave
  3. An interactive player head marks the grave location
  4. Floating holograms above it show the owner, the stored XP and item count, and the grave's age
  5. The player clicks the head to open the grave and retrieve their items
  6. Once the protection timer expires, anyone can loot it

Anti-Theft Protection

For the first grave-protection-minutes only the grave's owner or their killer can interact with it. After that it becomes public loot — which keeps grave-raiding in the game without making deaths feel cheap. Set the value to 0 to disable protection entirely.

Grave Settings

combat-log:
  graves: combat
  grave-protection-minutes: 5   # owner/killer-only window, 0 = no protection
  grave-xp-retain-percent: 100  # share of XP kept in the grave (0-100)
  grave-item-loss:              # random share of item stacks destroyed on death
    min-percent: 0
    max-percent: 0              # 0 / 0 = nothing is ever lost
  grave-despawn-minutes: 0      # 0 = graves never despawn
  grave-compass: true           # compass to the grave on respawn
  grave-history-days: 14        # how long deaths stay in /au graves list
  • XP retention: 100 keeps all of it — more than vanilla, which drops at most 100 XP.
  • Item loss: each death picks a random percentage between min-percent and max-percent, and that share of item stacks is destroyed instead of going into the grave.
  • Despawn timer: graves disappear after grave-despawn-minutes and the hologram counts down. Admins can still give the items back with /au graves restore.
  • Death compass: on respawn the player is always told where their grave is, and with grave-compass: true also gets a compass pointing to it. The compass is removed once the grave is gone.
  • Indestructible: explosions, flowing water and lava, pistons, and mobs cannot destroy a grave. If the head goes missing anyway, it is put back.

Graves persist across server restarts.

Settings GUI

/au graves on its own opens a settings menu for the grave mode, XP retention, item loss, protection time, despawn time, and the compass toggle, plus a button for the grave history. Changes are saved to config.yml.

Grave History & Restore

Every grave's original items are kept in the plugin database for grave-history-days days; graves that still exist are never removed from it. With database.type: mysql the history is shared by every backend, so /au graves list shows deaths from all servers (with the server name). An old grave-history.yml is imported automatically on first start.

CommandDescription
/au graves list [player] [page]Recent deaths with location, item count, and status (standing, looted by…, despawned, restored), with clickable [TP] [Items] [Restore] buttons.
/au graves view <id>Read-only view of what the grave held at death.
/au graves tp <id>Teleport to the death spot, sending you to the right backend if it was on another server.
/au graves restore <id> [grave] [force]Give the items and XP back. Players who are offline or on another backend get them as soon as they are on any server of the network, and each restore is delivered only once. Add grave to place a new grave at the death spot instead (run it on the server where the grave was). Graves the owner already looted, or that were already restored, need force so items are not duplicated by accident.

All /au graves commands need anziutils.admin.

Staff Account System

The Staff Account system lets staff members operate two completely separated player profiles: a normal profile (the one they play on as a regular player) and a staff profile (used when actively moderating). Switching is instant, and nearby players are not told who is staff.

How It Works

  1. A staff member runs /au staff (shortcut /staff) to enter staff mode.
  2. Their backend server, world, coordinates, yaw/pitch, and gamemode are saved to the database as the /auback target.
  3. Inventory, ender chest, statistics, balance, and LuckPerms groups swap to the staff profile, according to staff-account.separate.
  4. Staff godmode activates — no damage, and no combat tags.
  5. When they teleport, position/rotation/sound packets are hidden from non-admin players (ghosting).
  6. Running /au back (shortcut /auback) returns them to the saved location and gamemode and exits staff mode. Running /au staff again while in staff mode does the same thing — it acts as /au back, so leaving staff mode is always a single command.

Because the session is stored centrally, a reload or a backend switch restores the correct session instead of stranding the staff member without a valid /auback target.

Ranks are applied additively. Entering or leaving staff mode never removes a player's existing LuckPerms groups.

While in staff mode, an action bar reminder is shown (and briefly blinks every few seconds) so staff do not forget which profile they are on. The text lives in messages.yml under staff-mode-actionbar and staff-mode-actionbar-blink.

Configuration

staff-account:
  enabled: true
  separate:
    inventory: true      # main inventory, armor, offhand
    ender-chest: true
    stats: true          # vanilla statistics (playtime, kills, deaths, ...)
    ranks: true          # requires LuckPerms
    currency: true       # requires Vault + an economy plugin

  block-in-combat: true       # no escaping combat via a profile swap
  block-while-frozen: true
  godmode: true               # invulnerable in staff mode, also blocks combat tags
  ghost-on-teleport: true     # hide position/rotation/sound packets from non-admins
  teleport-view-distance: 3   # view distance after a staff teleport (0 = don't change)
  require-back-to-exit: true  # leaving staff mode always returns you to the saved location
  actionbar:                  # reminder shown while in staff mode
    enabled: true
    blink: true               # briefly flash it so it's hard to forget
    blink-interval-seconds: 10
    blink-duration-seconds: 1.5

  # Players allowed to use some staff-only commands without staff mode.
  # Easiest to manage in-game with /au exempt.
  command-exceptions:
    Notch:
      - tp
      - tphere

  staff-only-commands:
    - "ban"
    - "tempban"
    - "ipban"
    - "kick"
    - "mute"
    - "tempmute"
    - "warn"
    - "vanish"
    - "v"
    - "freeze"
    - "bring"
    - "tp"
    - "tpo"
    - "tphere"
    - "teleport"

Staff-Only Commands

Commands listed under staff-only-commands are blocked for anyone holding anziutils.staffaccount while they are on their normal profile. This stops staff from moderating while playing as a regular player.

Command Exceptions (e.g. /tp without staff mode)

Some people — a builder, an event host, the owner — need /tp on their normal profile. Give them an exception instead of removing the command from the list:

CommandEffect
/au exempt add SteveSteve can use /tp (and /teleport) without staff mode
/au exempt add Alex tp tphereSpecific commands only
/au exempt add Admin allEvery staff-only command
/au exempt remove Steve [commands]Remove some or all of Steve's exceptions
/au exempt listShow everyone with an exception

Exceptions are saved under staff-account.command-exceptions in config.yml (player name or UUID → list of commands, * for all). tp also covers teleport. If you prefer permissions, grant anziutils.staffaccount.exempt.<command> (for example anziutils.staffaccount.exempt.tp) or anziutils.staffaccount.exempt.*.

Commands

CommandPermissionDescription
/au staff (shortcuts /staff, /staffaccount) anziutils.staffaccount Enters staff mode. While in staff mode, it acts exactly like /au back: returns you to your saved location and exits staff mode in one step.
/au back (shortcuts /auback, /staffback) anziutils.back (included in anziutils.staffaccount) In staff mode: returns to your pre-staff backend, location, and gamemode, then exits staff mode. Outside staff mode: teleports to your last location.
/au exempt <add|remove|list> [player] [commands] anziutils.admin Manage staff-only command exceptions.

Network Staff Tools

With Redis enabled, the staff commands work across the whole network rather than one backend.

Staff Panel

/au panel (shortcut /staffgui) opens the AnziUtils — Staff Panel, a single inventory menu for staff mode, vanish, freeze, bring, announcements, panic mode, drop clearing, and spectating. Targeted actions open a player picker listing everyone online across the network, with their current backend shown in the lore.

Cross-Server Commands

Every command below is a /au subcommand; the short form in brackets works too.

CommandBehaviour
/au freeze <player> (/freeze)Toggles freeze on whichever backend the player is online on. The freeze persists through server switches.
/au bring <player> (/bring)Transfers the remote player to the admin's backend, then teleports them to the admin.
/au back (/auback)In staff mode, transfers staff back to the backend where staff mode started and restores the saved coordinates. Outside staff mode, returns the player to their last location, transferring them to the right backend first.
/au announce [-t <seconds>] <message> (/announce)Broadcast to every backend: always in chat, plus on screen as a title, action bar, and/or boss bar. See Network Announcements.
/au cleardrops (/cleardrops)Clears ground items on every backend, respecting the item-clear filters.
/au spectate [stop] (/randomplayer, /rp)Spectates a random network player while vanished. Each admin reserves one target through an atomic Redis lock, so two admins never land on the same player. stop releases the reservation.

Staff Target Hierarchy

Targeted staff commands (freeze, bring, spectate) respect a rank hierarchy, so moderators cannot act on admins — and no staff member can target themselves.

staff-hierarchy:
  enabled: true
  require-luckperms: true
  • The target's highest LuckPerms group weight must be the same as or lower than the actor's.
  • Console and server operators (op) bypass the check entirely.
  • With require-luckperms: true the check fails closed — if LuckPerms or a user's rank data is unavailable, the action is blocked rather than allowed.

Vanish

/au vanish (shortcut /vanish) hides the staff member from other players. Sounds they generate are suppressed for nearby observers, and entity visibility is handled at the packet level so they do not give themselves away. Vanish has two modes:

ModeBehaviour
invisibleHidden in the world, but still listed in the tab list.
leaveSends a fake leave message and hides you from the tab list too. Un-vanishing sends a fake join message.

Usage: /vanish [on|off|leave|invisible]. /vanish mode [leave|invisible] sets (or toggles) your preferred mode, which is remembered.

vanish:
  default-mode: invisible       # mode used until a player picks one
  fake-messages: true           # fake leave/join messages in leave mode
  fake-message-style: vanilla   # vanilla = same as the real join/leave line, custom = messages.yml
  fake-messages-scope: network  # network = every backend (needs Redis), server = this backend only

Keep fake-message-style: vanilla unless another plugin changes your real join/leave messages — hacked clients compare the two. With custom, match that plugin's format in vanish-fake-quit / vanish-fake-join in messages.yml.

Vanish state and the preferred mode follow the player across backends. Vanish is applied before the join completes, so server switches never show join/leave messages or tab entries. Vanished players never earn advancements, can always fly (including after gamemode and world changes), are ignored by mobs, sculk sensors, and wardens, and do not trigger pressure plates.

Last Location (/au back)

Outside staff mode, /au back (shortcut /auback) teleports a player to their last location: where they were before their last teleport, death, or server switch. With Redis the location is shared, so the player is first sent to the right backend. It needs anziutils.back, which anziutils.staffaccount includes.

back:
  on-death: true          # record the death location
  on-server-leave: true   # record the location when leaving a backend, so /auback undoes a server switch
  expire-minutes: 1440    # forget the last location after this long (Redis only)

In staff mode, /au back always returns to where staff mode was entered instead. auback is in the default combat blocked-commands list, so it cannot be used to escape a fight.

Network Announcements

/au announce [-t <seconds>] <message> (shortcut /announce) sends a message to every backend. It always goes to chat, and can also show on screen as a title, action bar, and/or boss bar.

  • Long messages are split into lines shown one after another. Lines break between words, so a word is only cut when it is longer than a whole line. Color codes carry over to the next line.
  • The heading (“Announcement”) only shows with the first line; the remaining lines appear underneath on their own.
  • Display time is set per line with stay-seconds, or for one announcement with -t — e.g. /announce -t 10 Restart in 5 minutes.
  • /announcements [on|off] lets any player choose chat only (off) or on-screen again (on). The choice is saved and, with Redis, follows the player across backends.
  • Chat tip: a clickable tip under announcements tells players about /announcements off. Each player sees it at most once per hint.interval-minutes.
announcements:
  # Where it shows on screen: any of title, actionbar, bossbar. Use [] for chat only.
  display: [title]
  # How long each line stays on screen (override per announcement with -t)
  stay-seconds: 5.0
  # Longer messages are split into lines of at most this many characters
  max-line-length: 40
  title:
    heading: "&6&lAnnouncement"   # shown above the first line only
    fade-in-seconds: 0.5
    fade-out-seconds: 1.0
  bossbar:
    color: YELLOW                 # PINK, BLUE, RED, GREEN, YELLOW, PURPLE, WHITE
    style: PROGRESS               # PROGRESS, NOTCHED_6, NOTCHED_10, NOTCHED_12, NOTCHED_20
  hint:
    enabled: true
    interval-minutes: 30          # 0 = tip under every announcement
DisplayBehaviour
titleThe line appears as the subtitle under the heading. A title holds only one line, which is why long messages are paged.
actionbarThe line shows above the hotbar and is refreshed every second so it stays for the full time.
bossbarThe line shows at the top of the screen and the bar drains over the whole announcement.

Displays can be combined, e.g. display: [title, bossbar]. Players who ran /announcements off only get the chat line. The toggle and tip messages are announce-screen-on, announce-screen-off, and announce-hint in messages.yml.

Server Utilities

Item Clearer

Periodically clears ground items to keep entity counts under control.

item-clear:
  enabled: true
  interval-minutes: 5
  excluded-worlds:
    - "world_the_end"

/au cleardrops runs an immediate clear using the same filters.

Redstone Limiter

Throttles runaway redstone per chunk so a lag machine cannot tank the server.

redstone-limiter:
  enabled: true
  max-pulses-per-second: 150
  cooldown-seconds: 5
  alert-admins: true

When a chunk crosses the threshold it is suppressed for cooldown-seconds, and players with anziutils.admin are notified if alert-admins is on.

Chat @Mention Tagging

Mentioning a player's name in chat highlights it and plays a sound for them.

chat-mentions:
  enabled: true
  sound: ENTITY_EXPERIENCE_ORB_PICKUP
  color: "YELLOW"

Command Watch

Sends a Discord notification whenever a watched command is executed — an audit trail for the commands that matter. Matching is on the base command, so op matches /op Player.

command-watch:
  enabled: true
  commands:
    - "op"
    - "deop"
    - "stop"
    - "ban"
    - "ban-ip"
    - "pardon"
    - "gamemode"
    - "whitelist"
    - "kick"

Interactive Rule Books

New players automatically receive a written book of your server rules the first time they join. The contents live in rules.yml, where each list entry is one page:

enabled: true

book:
  title: "&6Server Rules"
  author: "&cServer Administration"
  pages:
    - "&lWelcome to the server!&r\n\nPlease read through our rulebook carefully."
    - "&l1. No Cheating/Hacking&r\nAny use of modified clients will result in a permanent ban."
    - "&l2. Be Respectful&r\nDo not harass, flame, or dox other players."

Use \n to start a new line within a page.

CommandDescription
/au book give <player>Hand the rule book to a specific player.
/au book resetBump the book generation so every player receives the updated book as if they had never joined.

With Redis enabled, a player switching backends does not receive a duplicate book.

Discord Webhook Integration

Discord settings live in their own file, plugins/AnziUtils/discord.yml. Set the master toggle and your webhook URL, then enable the events you care about.

enabled: false
webhook-url: "https://discord.com/api/webhooks/YOUR_ID/YOUR_TOKEN"
bot-name: "AnziUtils"
bot-avatar: "https://mc-heads.net/avatar/MHF_Question/128"

notifications:
  vpn-detection: ...
  alt-limit: ...
  combat-log-death: ...
  combat-log-rejoin: ...
  panic-mode: ...
  command-watch: ...

Available Notifications

EventFires when
vpn-detectionA connecting IP is flagged as a VPN or proxy
alt-limitAn IP exceeds the configured account limit
combat-log-deathA player disconnects while combat-tagged and the NPC is killed
combat-log-rejoinA combat logger returns to the server
panic-modePanic mode is toggled on or off
command-watchA watched command from command-watch.commands is executed

Each event has its own enabled flag plus embed title, description, and color, so you can route only the alerts you want into your staff channel.

Test Your Webhook

Run /au test to send test payloads and confirm the integration works.

Commands

Everything lives under one command: /au (also /anziutils and /anzi). Run /au on its own for a clickable help menu that only lists what you are allowed to use. Every argument tab-completes, and a mistyped subcommand gets a did you mean…? suggestion.

Lookup & Administration

CommandDescriptionPermission
/au lookup <player|ip> [page]IP history, clickable linked accounts, and geolocation. /au <player> works too.anziutils.command
/au guiBrowse online players and their IP data.anziutils.gui
/au panic [on|off|status]Network lockdown; status lists active restrictions and actions.anziutils.admin
/au exempt <add|remove|list> [player] [commands]Let players use staff-only commands (e.g. /tp) without staff mode.anziutils.admin
/au book give <player>Give the rule book to a player.anziutils.book
/au book resetRegenerate rule books for all players.anziutils.book
/au reloadReload config.yml and messages.yml.anziutils.command
/au dump [hours] [local]A private link with AnziUtils' log, the full server log and your server's setup, for support. See Support Dumps.anziutils.dump
/au debugGeoIP, Redis, and database diagnostics.anziutils.admin
/au testSend test payloads to the Discord webhook.anziutils.admin

Staff Tools

CommandDescriptionPermission
/au panelOpen the network staff action panel.anziutils.staffgui
/au staffEnter staff mode. In staff mode it acts as /au back and exits.anziutils.staffaccount
/au backTeleport to your last location (before a teleport, death, or server switch). In staff mode, return to where you entered it and exit staff mode.anziutils.back
/au vanish [on|off|leave|invisible|mode]Toggle vanish. leave sends a fake leave message and hides you from the tab list; invisible keeps you in it. mode sets your preferred mode.anziutils.admin
/au freeze <player>Freeze or unfreeze a player, anywhere on the network.anziutils.admin
/au bring <player>Transfer and teleport a player to you.anziutils.admin
/au spectate [stop]Spectate a random network player while vanished.anziutils.randomplayer
/au announce [-t <seconds>] <message>Network-wide announcement in chat and on screen. Long messages are shown line by line; -t sets how long each line stays.anziutils.admin
/au announcements [on|off]Choose whether announcements show on your screen or only in chat (/announcements and /togglebroadcast work too).anziutils.announcements (everyone)
/au cleardropsImmediately clear ground items (respects filters).anziutils.admin

Graves

CommandDescriptionPermission
/au gravesOpen the grave settings GUI.anziutils.admin
/au graves list [player] [page]Recent deaths across the network, with TP / Items / Restore buttons.anziutils.admin
/au graves view <id>Read-only view of a grave's original items.anziutils.admin
/au graves tp <id>Teleport to the death spot, on any backend.anziutils.admin
/au graves restore <id> [grave] [force]Give the items and XP back, or place a new grave. See Grave History.anziutils.admin

Shortcuts

The short commands still work, so existing habits and scripts keep working: /vanish, /freeze, /bring, /announce, /announcements, /cleardrops, /staff (/staffaccount), /auback (/staffback), /staffgui (/staffpanel), /randomplayer (/rp), and the older /anziutilsgui, /anziutilsreload, /anziutilsdebug, /anziutilstest, /anziutilsbook, /anziutilsbooksreset.

Permissions

Administrative

PermissionDescriptionDefault
anziutils.adminStaff tools (vanish, freeze, bring, announce, cleardrops), grave settings and history (/au graves), panic mode, command exceptions, debug, and test. Also allows seeing true IPs in placeholders.OP
anziutils.command/au lookup and /au reload.OP
anziutils.guiAccess to /au gui.OP
anziutils.notifyReceives VPN, alt, country, and suspicious-join alerts in chat.OP
anziutils.bookAccess to /au book.OP
anziutils.staffaccountAccess to /au staff and the staff-mode /au back, plus staff godmode, ghosting, and staff-only command enforcement. Includes anziutils.back.OP
anziutils.back/au back to your last location (before a teleport, death, or server switch), network-wide.OP
anziutils.staffguiAccess to /au panel.OP
anziutils.randomplayerAccess to /au spectate.OP
anziutils.announcementsUse /announcements to show announcements on screen or only in chat.everyone
anziutils.updatesTold on join when a new version has been downloaded and is waiting for a restart. See Automatic Updates.OP
anziutils.dumpUse /au dump. See Support Dumps.OP

Server operators always pass these staff and admin checks, whether or not the permission is set.

Bypasses

PermissionDescriptionDefault
anziutils.exemptExempts the player from VPN detection, alt limits, country filtering, and smart mutes.false
anziutils.combatlog.bypassUniversal bypass — the player is never combat tagged.false
anziutils.combatlog.bypass.enderpearlsCan throw enderpearls while in combat.false
anziutils.combatlog.bypass.goldenapplesCan eat golden apples in combat.false
anziutils.combatlog.bypass.chorusfruitCan eat chorus fruit in combat.false
anziutils.combatlog.bypass.totemsCan trigger totems in combat.false
anziutils.combatlog.bypass.inventoryCan open containers and the inventory in combat.false
anziutils.combatlog.bypass.flightCan fly or use an elytra in combat.false
anziutils.combatlog.bypass.commandsCan use blocked commands in combat.false
anziutils.combatlog.bypass.worldchangeCan change worlds while in combat.false
anziutils.combatlog.bypass.serverswitchCan switch backend servers while in combat.false
anziutils.combatlog.bypass.regionentryCan enter blocked WorldGuard regions while in combat.false
anziutils.combatlog.bypass.cooldownSkips the post-combat cooldown.false
anziutils.staffaccount.exempt.<command>Use that staff-only command without staff mode (e.g. .exempt.tp). .exempt.* covers all of them.false
anziutils.panic.bypassNever moved, kicked, or messaged by panic-mode actions.false

PlaceholderAPI

When PlaceholderAPI is installed, AnziUtils registers the anziutils expansion automatically. It persists across /papi reload.

PlaceholderReturns
%anziutils_combat_time%Seconds remaining on the player's combat tag (0 when not in combat)
%anziutils_combat_active%true or false — whether the player is combat tagged
%anziutils_pvp_cooldown%Seconds remaining on the player's post-combat cooldown (0 when none)
%anziutils_country%The player's last known country
%anziutils_city%The player's last known city
%anziutils_ip%The player's IP address — returns Hidden unless the player has anziutils.admin

Full config.yml

The complete default configuration, for reference:

# =======================================
#   AnziUtils Configuration
# =======================================

# AnziLock License Configuration
license:
  # Insert the license key you received via Discord here (see /claim).
  key: ""

# Download new versions of AnziUtils automatically when they are released.
# They are checked against your license and load on the next restart.
# Players with anziutils.updates (ops by default) are told when one is waiting.
auto-update: true

# /au dump makes a private link with AnziUtils's log, the full server log and the server's setup
# to share with support. "dump local" only saves it in plugins/AnziUtils/dumps/.
dump:
  # Hours of AnziUtils's log to keep on disk (dump-logs/) and put in a dump.
  log-hours: 48
  # How long the link works, in hours (at most 168).
  link-hours: 24
  # Replace IP addresses in the logs with x.x.x.x.
  hide-ips: true

# Database Configuration
# Supported types: sqlite, mysql
#
# Single server: keep type 'sqlite' (default, zero setup).
# Network (BungeeCord/Velocity): use ONE shared MySQL database on every
# backend server so IP history, alt limits and staff profiles are tracked
# network-wide. Make sure your proxy forwards the real player IP
# (BungeeCord: ip_forward: true; Velocity: player-info-forwarding-mode).
database:
  type: sqlite
  # MySQL settings (only used when type is 'mysql')
  mysql:
    host: localhost
    port: 3306
    database: anziutils
    username: root
    password: ""
    use-ssl: false
    # If true, a failed MySQL connection silently falls back to local SQLite.
    # Networks should keep this FALSE so a broken MySQL never splits player
    # data across per-server SQLite files (the plugin disables safely instead).
    fallback-to-sqlite: false
    # HikariCP connection pool tuning (safe defaults for small servers)
    pool:
      maximum-pool-size: 10
      minimum-idle: 2
      connection-timeout-ms: 10000
      idle-timeout-ms: 600000
      max-lifetime-ms: 1800000

# Redis Synchronization (optional, for multi-server networks)
# Enables: network-wide panic mode, shared smart-mutes, a live online-player
# registry (network GUI), GeoIP/VPN result caching and cross-server alerts.
# Point every backend at the SAME Redis instance and give every backend a
# UNIQUE server-id. Local fallbacks keep the plugin fully working when
# Redis is offline or disabled.
redis:
  enabled: false
  host: localhost
  port: 6379
  username: ""
  password: ""
  database: 0
  use-ssl: false
  timeout-ms: 5000
  # Namespace for all keys this plugin writes.
  key-prefix: "anziutils"
  # MUST be unique per backend server (e.g. "lobby-1", "survival-1").
  # Also used by the combat-log escrow, so set it even when Redis is disabled.
  server-id: "survival-1"
  # How often this server refreshes its online-player registry entry.
  heartbeat-seconds: 10
  # Registry entries expire after this many seconds without a heartbeat.
  registry-ttl-seconds: 30
  # Grace period used to distinguish a backend switch from a true network leave.
  session-grace-seconds: 20
  # Expiry for pending cross-server teleports/actions.
  action-timeout-seconds: 30
  # Expiry for /randomplayer target reservations (refreshed while spectating).
  spectate-lock-seconds: 45
  # Optional proxy-registered backend name used by BungeeCord-compatible Connect
  # messages. Leave empty to use server-id. Velocity requires
  # bungee-plugin-message-channel: true in velocity.toml.
  proxy-server-name: ""
  cache:
    # How long successful GeoIP lookups are cached (seconds).
    geo-ttl-seconds: 86400
    # How long successful VPN/proxy checks are cached (seconds).
    vpn-ttl-seconds: 3600

# VPN / Proxy Detection
# Uses ip-api.com to check if a connecting IP is a VPN or proxy.
vpn-detection:
  enabled: true
  # If true, players connecting via VPN/proxy will be kicked.
  # If false, ops will be warned but the player can still join.
  kick-on-vpn: true
  kick-message: "&cVPN/Proxy connections are not allowed on this server."

# Alt Account Limiter
# Limits how many distinct accounts can connect from the same IP address.
alt-limit:
  enabled: true
  max-accounts-per-ip: 3
  kick-message: "&cToo many accounts have connected from your IP address."

# Exempt IPs
# IPs listed here bypass VPN detection and alt-limit checks entirely.
exempt-ips:
  - "127.0.0.1"

# Country Filter
# Restrict access based on player country (resolved via GeoIP).
# mode: 'disabled', 'whitelist', or 'blacklist'
#   whitelist = ONLY listed countries can join
#   blacklist = listed countries are BLOCKED
# Use full country names as returned by ipwho.is (e.g. "Slovenia", "Germany").
country-filter:
  mode: disabled
  kick-message: "&cYou are not allowed to join from your country."
  countries:
    - "Slovenia"
    - "Croatia"
    - "Austria"

# Panic Mode
# A network-wide lockdown against bot raids. Toggle it with:
#   /au panic on | off | status
# With Redis enabled, toggling on one server applies to EVERY backend, and
# each backend runs the actions below for its own players.
panic-mode:
  # --- Join restrictions while panic mode is ON ---
  restrictions:
    # Only let players from these countries join
    country-whitelist: true
    allowed-countries:
      - "Slovenia"
    # Lower the alt limit
    alt-limit: true
    max-accounts-per-ip: 1
    # Mute players who joined less than X minutes ago
    mute-new-players: true
    mute-new-players-minutes: 5

  # A player counts as "new" (target: new-players) if their first ever join
  # on the network was less than this many minutes ago.
  new-player-minutes: 60
  # Players with this permission are never touched by panic actions.
  bypass-permission: "anziutils.panic.bypass"

  # --- Actions ---
  # on-enable : runs once when panic mode turns ON
  # on-join   : runs for every player who joins while panic mode is ON
  # on-disable: runs once when panic mode turns OFF
  #
  # Action types:
  #   send      - move players to another backend   (server: <proxy server name>)
  #   kick      - kick players                       (message: <kick reason>)
  #   message   - chat message to the targets        (message: ...)
  #   title     - title on screen                    (title: ..., message: <subtitle>)
  #   broadcast - chat message to everyone            (message: ...)
  #   command   - console command; {player} = run once per target (command: ...)
  # Options for every action:
  #   target:  all | non-staff (default) | new-players | staff
  #   delay:   seconds to wait before running (default 0)
  #   servers: only run on these server-ids, e.g. [lobby-1]   (default: every server)
  #   scope:   network (every backend runs it) | origin (only the server that toggled)
  #            default: network, except 'command' which defaults to origin
  #
  # Example - move new players into a limbo server and kick them if they come back:
  #   on-enable:
  #     - type: title
  #       target: new-players
  #       title: "&c&lLOCKDOWN"
  #       message: "&7Moving you to a waiting area..."
  #     - type: send
  #       target: new-players
  #       server: limbo
  #       delay: 3
  #   on-join:
  #     - type: kick
  #       target: new-players
  #       message: "&cThe server is in lockdown. Please try again in a few minutes."
  #       servers: [survival-1]
  #   on-disable:
  #     - type: send
  #       target: all
  #       server: lobby
  #       servers: [limbo]
  actions:
    on-enable:
      - type: broadcast
        message: "&c&l[!] &cThe server is in lockdown mode. New connections are restricted."
    on-join:
      - type: message
        target: new-players
        message: "&c&l[!] &7The server is in lockdown - chat is limited for new players."
    on-disable:
      - type: broadcast
        message: "&a&l[!] &aLockdown lifted. Thanks for your patience!"

# Smart Mute
# Automatically mutes suspicious players for 5 minutes (blocks chat and commands).
smart-mute:
  # Mute player if they join with a VPN but kick-on-vpn is false
  mute-on-vpn-warn: true
  # Mute player if they join from a blacklisted/unwhitelisted country but aren't kicked (if we ever decide to warn instead of block)
  # (Currently country filter only blocks, but good for future proofing)
  mute-duration-minutes: 5

# Combat Log Module
combat-log:
  enabled: true
  timer: 15 # Combat duration in seconds

  # What happens when a combat-tagged player disconnects (including switching
  # backend servers through the proxy). Their inventory and XP are moved into
  # the database the moment they leave, so the items exist in exactly one
  # place - this is what makes combat logging dupe-proof on Velocity/Bungee
  # networks (use the shared MySQL database on every backend).
  #  - If the logger is killed: the items go into a grave and the player dies
  #    on their next join, on ANY server of the network.
  #  - If the logger survives (or the player returns to the same server in
  #    time): the items are given back, on whichever server they are on.
  # Every backend needs a unique redis.server-id for this to work correctly.
  logger:
    # npc           = spawn a zombie stand-in that others can kill
    # instant-death = kill the player immediately (items go to a grave)
    mode: npc
    # How long the NPC stays (seconds). 0 = same as the combat timer.
    duration-seconds: 30
    # If the server that owns a logger crashes, other servers take over its
    # escrow after this many extra seconds and give the items back.
    network-takeover-seconds: 60
  # When a player head grave (with loot GUI) is spawned instead of vanilla drops:
  #   always = on every player death, and when a combat logger is killed
  #   combat = only when a player dies while combat-tagged, or a combat logger is killed
  #   off    = never; items and XP drop on the ground like vanilla
  # (Replaces the old "graves-enabled" option: true = combat, false = off.)
  graves: combat
  
  # Combat Restrictions
  disable-enderpearls: true
  disable-golden-apples: true
  disable-chorus-fruit: true
  disable-totems: false
  disable-inventory-open: true
  disable-flying: true

  # Block players in combat from crossing into another world
  # (portals, plugin teleports, etc.).
  block-world-change: true
  # Block players in combat from crossing to another backend server via
  # AnziUtils network transfers (/auback, /bring, /randomplayer, panic moves).
  # Switching away via proxy commands (e.g. /server) counts as combat logging.
  block-server-switch: true

  # Optional cooldown that starts when a combat tag ends (timer ran out, or the
  # opponent died / their combat logger was killed). While it runs the player
  # can't use commands, change worlds, be teleported, or switch servers - so
  # nobody can win a fight and instantly /home, /spawn or /server away.
  # Getting hit again replaces the cooldown with a normal combat tag.
  # Bypass: anziutils.combatlog.bypass or anziutils.combatlog.bypass.cooldown
  post-combat-cooldown:
    enabled: false
    seconds: 10
    # Block every command except the ones in allowed-commands.
    block-commands: true
    allowed-commands:
      - "msg"
      - "r"
      - "tell"
      - "w"
      - "reply"
    # Portals and any teleport into another world.
    block-world-change: true
    # Command and plugin teleports inside the same world (/tp, /home, /warp...).
    # Ender pearls and chorus fruit are not affected.
    block-teleports: true
    # AnziUtils network transfers (/auback, /bring, /randomplayer, panic moves).
    block-server-switch: true

  # Commands that are blocked while a player is in combat.
  # Use lowercase. Players with anziutils.combatlog.bypass skip this.
  blocked-commands:
    - "home"
    - "spawn"
    - "tp"
    - "tpa"
    - "tpaccept"
    - "warp"
    - "auback"
    - "sethome"
    - "rtp"
    - "wild"

  # WorldGuard Integration — region names where combat tagging is disabled.
  # Requires WorldGuard to be installed. Case-insensitive.
  safe-zone-regions:
    - "spawn"
    - "safezone"

  # Stop combat-tagged players from entering WorldGuard regions - walking,
  # riding, ender pearls, chorus fruit and teleports are all blocked, so
  # nobody can run into spawn mid-fight to escape. Leaving a region is always
  # allowed. Requires WorldGuard.
  # Bypass: anziutils.combatlog.bypass or anziutils.combatlog.bypass.regionentry
  block-region-entry:
    enabled: true
    # Region names (case-insensitive). Leave empty to use safe-zone-regions.
    regions: []
    # The border works like a wall: the player is stopped and bounces back a
    # little. With knockback on, players who walk into it on the ground also get
    # shoved back out. Anyone knocked into it by a hit, explosion or wind charge
    # only stops, so they aren't thrown back at their attacker. Nobody is ever
    # lifted into the air.
    knockback: true
    # How hard walking players get shoved back (sideways only). 1.0 = about two
    # blocks, 2.0 = about four.
    knockback-strength: 1.0

  # Grace period (seconds) after joining where players can't be combat-tagged.
  # Prevents spawn-killing loops. Set to 0 to disable.
  join-grace-period: 3

  # Grave protection (minutes) — only the owner or their killer can loot.
  # After this time, anyone can loot the grave. Set to 0 to disable.
  grave-protection-minutes: 5

  # How much of a player's XP is kept in their grave (0-100).
  # 100 = all of it (more than vanilla, which drops at most 100 XP).
  # Admins can also change these grave settings in-game with /au graves.
  grave-xp-retain-percent: 100
  # Random item loss on death. Each death picks a random percentage between
  # min and max, and that share of the item stacks is destroyed instead of
  # going into the grave. 0 / 0 = nothing is ever lost.
  grave-item-loss:
    min-percent: 0
    max-percent: 0

  # Graves despawn this many minutes after the death and their items are lost.
  # Admins can still give them back with /au graves restore <id>. 0 = never.
  grave-despawn-minutes: 0
  # Give players a compass pointing to their grave when they respawn
  # (they are always told the grave's coordinates).
  grave-compass: true
  # How many days deaths stay in the admin grave history (/au graves list),
  # which keeps a copy of every grave's items for restoring. Graves that
  # still exist are never removed from it. Stored in the database, so with
  # database.type: mysql every server shares it and restores reach players
  # on whichever server they join.
  grave-history-days: 14

# Chat @Mention Tagging
chat-mentions:
  enabled: true
  sound: ENTITY_EXPERIENCE_ORB_PICKUP
  color: "YELLOW"

# Item Clearer
# Periodically clears ground items to reduce lag.
item-clear:
  enabled: true
  # Interval between automatic clears (in minutes)
  interval-minutes: 5
  # Worlds to exclude from clearing
  excluded-worlds:
    - "world_the_end"

# Redstone Limiter
# Throttles excessive redstone activity per chunk to prevent lag machines.
redstone-limiter:
  enabled: true
  # Maximum redstone pulses per chunk per second before throttling
  max-pulses-per-second: 150
  # How long (seconds) a throttled chunk stays suppressed
  cooldown-seconds: 5
  # Notify players with anziutils.admin when a chunk is throttled
  alert-admins: true

# Command Watch (Discord Broadcast)
# Sends a Discord notification when a player executes a watched command.
command-watch:
  enabled: true
  # Commands to monitor (without leading /).
  # Matches the base command only (e.g. "op" matches "/op Player").
  commands:
    - "op"
    - "deop"
    - "stop"
    - "ban"
    - "ban-ip"
    - "pardon"
    - "gamemode"
    - "whitelist"
    - "kick"

# Staff Target Hierarchy
# Targeted staff commands (freeze, bring, randomplayer) can only be used on
# players whose highest LuckPerms group weight is the same as or lower than
# the actor's. Console and server operators (op) bypass this check. With require-luckperms true, targeted commands
# fail closed when LuckPerms or one of the users is unavailable.
staff-hierarchy:
  enabled: true
  require-luckperms: true

# Staff Dual Accounts
# Lets staff run /staffaccount to swap between a "staff" profile and a
# "normal" player profile. Each profile keeps its own separated data.
staff-account:
  enabled: true
  separate:
    # Inventory contents (main, armor, offhand)
    inventory: true
    # Ender chest contents
    ender-chest: true
    # Vanilla statistics (playtime, kills, deaths, etc.)
    stats: true
    # Apply saved profile groups additively (requires LuckPerms). Existing
    # player ranks are never removed when entering or leaving staff mode.
    ranks: true
    # Money balance (requires Vault + an economy plugin)
    currency: true
  # Block switching while combat-tagged (prevents escaping combat via profile swap)
  block-in-combat: true
  # Block switching while frozen by an admin
  block-while-frozen: true
  # Invulnerable while in staff mode (also prevents combat tags)
  godmode: true
  # After teleporting in staff mode, hide position/rotation/sound packets from
  # non-admin players so the staff member can't be tracked
  ghost-on-teleport: true
  # View distance applied when teleporting in staff mode (restored on /auback). 0 = don't change
  teleport-view-distance: 3
  # Leaving staff mode (/auback or /staffaccount) returns you to the saved location
  require-back-to-exit: true
  # Actionbar reminder shown while in staff mode (text in messages.yml:
  # staff-mode-actionbar / staff-mode-actionbar-blink)
  actionbar:
    enabled: true
    # Briefly flash the actionbar so it's harder to forget you're in staff mode
    blink: true
    # How often to blink, and how long each blink lasts
    blink-interval-seconds: 10
    blink-duration-seconds: 1.5
  # Players who may use some staff-only commands WITHOUT staff mode active.
  # Key = player name or UUID, value = list of commands ("*" = all of them).
  # "tp" also covers "teleport". Easiest way to manage this in-game:
  #   /au exempt add <player> [commands...]   (no commands = tp)
  #   /au exempt remove <player> [commands...]
  #   /au exempt list
  # You can also grant the permission anziutils.staffaccount.exempt.<command>
  # (e.g. anziutils.staffaccount.exempt.tp) or anziutils.staffaccount.exempt.*
  command-exceptions:
  #   Notch:
  #     - tp
  #     - tphere

  # Commands that only work while in staff mode (for players with anziutils.staffaccount)
  staff-only-commands:
    - "ban"
    - "tempban"
    - "ipban"
    - "kick"
    - "mute"
    - "tempmute"
    - "warn"
    - "vanish"
    - "v"
    - "freeze"
    - "bring"
    - "tp"
    - "tpo"
    - "tphere"
    - "teleport"

# Vanish (/vanish)
vanish:
  # Mode used by /vanish until a player picks one with /vanish mode:
  #   invisible - hidden in the world, still listed in the tab list
  #   leave     - fake leave message and hidden from the tab list too
  default-mode: invisible
  # Send fake leave/join messages (messages.yml: vanish-fake-quit / vanish-fake-join)
  fake-messages: true
  # vanilla - identical to the server's real join/leave line (recommended; hacked clients compare them)
  # custom  - use messages.yml; only if another plugin changes real join/leave messages, then match its format
  fake-message-style: vanilla
  # network = every backend shows them (needs Redis), server = only this backend
  fake-messages-scope: network

# /auback outside staff mode (last location). Shared across backends with Redis.
back:
  # Record the death location
  on-death: true
  # Record the location when leaving a backend, so /auback undoes a server switch
  on-server-leave: true
  # Forget the last location after this many minutes (Redis only)
  expire-minutes: 1440

# /announce — the chat line is always sent. Players can turn the on-screen part off
# for themselves with /announcements off (chat only) and back on with /announcements on.
announcements:
  # Where it shows on screen: any of title, actionbar, bossbar. Use [] for chat only.
  display: [title]
  # How long each line stays on screen. Override per announcement: /announce -t 10 <message>
  stay-seconds: 5.0
  # Long messages are split into lines (breaking between words) shown one after another
  max-line-length: 40
  title:
    # Big text shown above the first line only
    heading: "&6&lAnnouncement"
    fade-in-seconds: 0.5
    fade-out-seconds: 1.0
  bossbar:
    # PINK, BLUE, RED, GREEN, YELLOW, PURPLE, WHITE
    color: YELLOW
    # PROGRESS, NOTCHED_6, NOTCHED_10, NOTCHED_12, NOTCHED_20
    style: PROGRESS
  # Chat tip under announcements telling players about /announcements off (clickable)
  hint:
    enabled: true
    # Each player sees it at most once per this many minutes (0 = under every announcement)
    interval-minutes: 30

Troubleshooting

Q: The plugin disables itself on startup

A: Check the console for an [AnziLock] line. NO_KEY means license.key is still empty; a network error means the server could not reach license.ajdnikov-dev.com. Also confirm you are on Java 21 and Paper 1.21+.

Q: The server says AnziUtils is missing a dependency

A: Install PacketEvents. Since 1.4 it is a required dependency, and the server refuses to load AnziUtils without it.

Q: Every player is flagged as a VPN, or none are

A: VPN checks go to proxycheck.io and geolocation to ipwho.is. Make sure the server has outbound internet access, then run /au debug to see live API results and rate-limit status. If you are behind a proxy, confirm the real player IP is being forwarded (ip_forward on BungeeCord, player-info-forwarding-mode on Velocity) — otherwise every player appears to come from the proxy's IP.

Q: The alt limiter counts everyone as the same player

A: This is the proxy-forwarding problem above. Without forwarding, all connections share the proxy's IP.

Q: Combat logging is not triggering

A: Verify combat-log.enabled: true, that the players are not inside a region listed in safe-zone-regions, that they are past the join-grace-period, and that they do not hold anziutils.combatlog.bypass.

Q: A combat logger kept their items, or items were duplicated

A: On a network every backend must point at the same MySQL database and have a unique redis.server-id — two backends sharing an id will treat each other's escrows as their own. If you run an inventory-sync plugin, it must save the inventory after AnziUtils has emptied it on quit.

Q: Someone needs /tp without entering staff mode

A: Run /au exempt add <player>. See Command Exceptions.

Q: Graves are not spawning

A: Check combat-log.graves. With combat (the default) only combat deaths and killed loggers make a grave; use always for every death. With off, items and XP drop on the ground like vanilla.

Q: A player lost their grave

A: Run /au graves list <player>, find the death, and click [Restore] (or run /au graves restore <id>). Deaths stay in the history for grave-history-days days.

Q: Staff data is split between servers

A: Every backend must point at the same MySQL database with fallback-to-sqlite: false, and each backend needs a unique redis.server-id.

Q: /au bring, /au back, or a panic send does not transfer across servers

A: Cross-server transfers need Redis enabled on every backend, a correct proxy-server-name (or a server-id matching the proxy's registered name), and — on Velocity — bungee-plugin-message-channel = true.

Q: Discord webhook not working

A: Check discord.yml: the master enabled flag, the webhook URL, and the individual event toggle. Then run /au test.

Q: Need more help?

A: Join our Discord server for support and bug reports.

Upgrading from an Older Version

  • Commands: everything lives under /au. The old commands (/anziutilsgui, /staffgui, /randomplayer, …) still work as shortcuts, so habits and scripts keep working.
  • Panic mode: the old flat keys (panic-mode.allowed-countries, panic-mode.max-accounts-per-ip, panic-mode.mute-new-players-minutes) are still read when panic-mode.restrictions is missing. To get the on/off toggles and actions, copy the panic-mode block from a freshly generated config.yml.
  • Combat logging: set a unique redis.server-id on every backend (even with Redis disabled) and point all backends at one MySQL database. The combat_escrow table is created automatically. Escrows left over from a crash are recovered when the owning server starts again, or by another server after network-takeover-seconds.
  • Graves (1.7): combat-log.graves-enabled is replaced by combat-log.graves (always / combat / off). Old configs keep working: true maps to combat, false to off. An existing grave-history.yml is imported into the database on first start.
  • /au back (1.7): now also works outside staff mode, with its own permission anziutils.back (included in anziutils.staffaccount). See the new vanish and back sections in the default config.yml.
  • Announcements (1.7.1): copy the announcements block from a freshly generated config.yml to get the display modes, heading, and chat tip. Without it, announcements still show as a title with the default timing. Players get the new /announcements command automatically (anziutils.announcements, default: everyone).
  • Combat (1.7.3): combat-tagged players can no longer walk, pearl, or teleport into WorldGuard regions. This is on by default even without the new block-region-entry block, and uses your safe-zone-regions; set block-region-entry.enabled: false to keep the old behaviour. The new post-combat cooldown is off until you add post-combat-cooldown.enabled: true.
  • Automatic updates (1.7.4): install 1.7.4 or newer by hand once; after that new versions download by themselves and load on the next restart (auto-update in config.yml). From this version on, new settings are added to your config files automatically, so you no longer need to copy blocks from a fresh config.yml. See Automatic Updates.
  • Region border (1.7.5): the combat region border now stops players like a wall and never lifts them; knockback only shoves players who walk into it, sideways. No new settings or permissions.