VonixGuardian Vonix Mods v2.3.2 Search GitHub
VonixGuardian/Reference/Commands

Commands#

Every command lives under /vg. Two alias roots redirect to the same tree: /co and /guardian. The /co alias exists so operators arriving from CoreProtect do not have to relearn the prefix.

/vg <subcommand> [arguments]
/co <subcommand> [arguments]
/guardian <subcommand> [arguments]

Subcommands marked with a console badge may be run from the server console or RCON. Those marked with a player badge require a player — they need a position, an inventory, or an entity to act on.

Command index#

Command Aliases Permission (default op)
/vg inspect i, inspector vonixguardian.inspect (2) player
/vg lookup l, page vonixguardian.lookup (2) both
/vg near — vonixguardian.near (2) player
/vg rollback rb, ro vonixguardian.rollback (3) both
/vg apply — rollback or restore both
/vg cancel — rollback or restore both
/vg restore rs, re vonixguardian.restore (3) both
/vg undo — vonixguardian.undo (3) both
/vg purge — vonixguardian.purge (4) both
/vg status stats, version vonixguardian.status (3) both
/vg consumer — vonixguardian.consumer (4) both
/vg reload — vonixguardian.reload (4) both
/vg config — vonixguardian.command.config (4) both
/vg entitylog — vonixguardian.command.config (4) both
/vg teleport tp vonixguardian.command.teleport (3) player
/vg give — vonixguardian.command.give (4) player
/vg migrate-db — vonixguardian.migrate_db (4) console
/vg help — root: vonixguardian.base (2) both

The op-level column is the vanilla fallback used when LuckPerms is absent. See Permissions for node resolution order and the per-node override map.


inspect#

/vg inspect

Toggles inspection mode for you. While it is on, left-clicking a block runs a position-anchored lookup on that block, and right-clicking a chest shows the container transactions recorded there.

/vg inspect        ← enable
[VonixGuardian] Inspect mode ENABLED. Left-click a block to look it up.
/vg inspect        ← disable
[VonixGuardian] Inspect mode disabled.

The inspector queries p:<x>,<y>,<z> r:2 t:30d r:#world_<key> — a 5×5×5 window around the clicked block, 30 days back, scoped to that block's world so identical coordinates in another dimension cannot leak in.

Player only

Console cannot inspect, because there is no block to click. Running it from console returns Inspect mode must be run by a player.

lookup#

/vg lookup [<page>[:<perPage>]] [filters]
/vg l [<page>[:<perPage>]] [filters]
/vg page [<page>[:<perPage>]] [filters]

Searches the audit log. All filters are optional; with none, the query is unbounded in time and global in space.

Pagination. If the first whitespace-separated token is purely numeric, or <n>:<m>, it is consumed as the page selector and removed from the filter:

/vg lookup 2              ← page 2, default page size
/vg lookup 2:20 u:Steve   ← page 2, 20 rows per page
/vg lookup u:Steve        ← page 1, default page size

Per-page is clamped to 1–50. The default comes from lookup.defaultPageSize (7 as shipped), also clamped to 1–50.

Counting. #count returns a single total instead of rows:

/vg lookup #count r:50 t:24h
[VonixGuardian] Count: 3

No results. You get a hint rather than silence:

[VonixGuardian] No results found. Try a wider radius (r:20+) or longer time
(t:24h+), or check filter tokens.

Scan limit. A lookup whose permission-filtered page would have to scan more than 100,000 raw rows fails closed rather than paging through them:

[VonixGuardian] Lookup aborted: the permission-filtered page exceeded the
100000-row scan limit. Narrow the time, radius, or action filter and try again.

Full parameter reference: Filters & parameters.

near#

/vg near

A shortcut for lookup r:5 t:1h centred on you. It takes no arguments.

/vg near            ≡   /vg lookup r:5 t:1h

Player only. Because it is a lookup, no default rollback radius is applied — which changes nothing here, since r:5 is explicit.

rollback#

/vg rollback [filters]
/vg rb [filters]
/vg ro [filters]

Reverses the matching actions in the world. Each row's inverse is computed (block_break → place the original state back, container_deposit → withdraw the same stacks, and so on) and applied newest-first.

Default radius. If you supply no numeric radius and no world or WorldEdit selector, rollback applies r:10 centred on you. This matches CoreProtect, and it is the single most common surprise: a rollback you expected to be global was scoped to 10 blocks. Use r:#global explicitly for a whole-world mutation.

/vg rollback u:Griefer t:24h              ← 10-block radius around you
/vg rollback u:Griefer t:24h r:#global    ← everything, everywhere
/vg rollback t:15m r:30                   ← anyone, last 15 minutes, 30 blocks

Preview first. #preview renders the plan without touching the world:

/vg rollback u:Griefer t:24h r:#global #preview

Confirmation mode. If rollback.requireConfirm is true, every rollback stops after planning and waits for /vg apply. The shipped default is false, so rollbacks apply immediately.

Counting. #count plans without executing and reports the plan size:

/vg rollback u:Griefer t:24h #count
[VonixGuardian] Rollback count: planned=318 skipped=2

Progress. Long plans report every tenth page and at limit boundaries:

[VonixGuardian] Rollback planning: scanned=1200 planned=340 skipped=2

Result. Mutations report one authoritative summary line and, with #verbose, a second line of id counts:

[VonixGuardian] Rollback SUCCESS affected=318 planned=320 skipped=2 failed=0
compensated=0 repairRequired=0 batchId=17 closed=true
Status Meaning
SUCCESS Every planned step applied.
PARTIAL Some steps applied; the rest were skipped.
COMPENSATED A failure was rolled forward and the world was restored to its pre-mutation state.
REPAIR_REQUIRED A step could not be applied or compensated. Rows are listed in vg_repair_required.
FAILED Nothing was applied.

A successful mutation that matched nothing extra says so, because the usual cause is a radius that does not cover explosion splash:

[VonixGuardian] Rollback found 0 matching actions. Explosions record their blast
CENTER — try r:20+ or move to the source of the damage.

#silent suppresses the result block entirely on success. It is suppressed for success only — failures and previews still report.

Explosion centres

Explosion rows record the blast centre. A rollback with a tight radius can miss splash damage whose centre sits outside the radius. Widen r: for explosive damage, or use r:#global with a short t: window.

apply and cancel#

/vg apply
/vg cancel

apply executes the rollback or restore preview you most recently generated. cancel discards it. Both act only on your pending preview — previews are keyed per actor, and the console has its own key.

The preview is invalidated when you start a new rollback or restore, and the command re-checks your permission at apply time. If either changed, apply refuses and asks you to preview again:

[VonixGuardian] Pending rollback preview changed or expired; run preview again.

apply requires the rollback node for a rollback preview, or the restore node for a restore preview.

/vg rollback u:Griefer t:1h #preview
/vg apply                            ← commit exactly that plan

restore#

/vg restore [filters]
/vg rs [filters]
/vg re [filters]

Reapplies actions that were previously rolled back — either by replaying the forward inverse of a batch, or by re-applying actions matching a filter. Same filter language, same default 10-block radius, same #preview and #count behaviour as rollback.

Restore and rollback are two directions of the same engine; a restore is not a "history pop". Both mutate the world and both are recorded as batches.

undo#

/vg undo

Reverses your own last rollback or restore by executing its inverse against the exact rows that were affected. It is not a history-pop and it does not touch a newer mutation. With no prior batch:

[VonixGuardian] Nothing to undo.

Each actor has an independent undo stack entry, and the console has its own. If the stored entry predates row-level id tracking, undo drops it and says so rather than guessing:

[VonixGuardian] Undo: dropped 42 entries from history (legacy/empty entry —
world state not reverted).

purge#

/vg purge <t:duration> [other filters]

Permanently deletes rows older than the given time window. This is retention semantics, not a query window: t:30d keeps the last 30 days and deletes the rest.

/vg purge t:90d                  ← delete everything older than 90 days
/vg purge t:60d a:block          ← only block rows
/vg purge t:30d r:#world_nether  ← only the Nether

Age floors. A purge cannot delete recent data, and the floor depends on who runs it. Both are configurable.

Source Default floor Config key Minimum allowed
Console 24 hours purge.minAgeSecondsConsole 60 seconds
In-game 30 days purge.minAgeSecondsInGame 1 hour

A purge that violates its floor is refused before anything is deleted:

[VonixGuardian] Purge refused: purge requires a time filter at least 2592000s old
(CP-1:1 safety floor; use a larger t: window)

Reclaiming disk. #optimize runs dialect-specific storage maintenance after a successful purge: VACUUM on SQLite, OPTIMIZE TABLE on MySQL/MariaDB, VACUUM ANALYZE on PostgreSQL.

/vg purge t:90d #optimize

The optimize step is capped at five minutes and failure is swallowed — a purge that deleted rows is still a successful purge if maintenance does not complete.

Purge is irreversible

Purged rows are gone. There is no rollback of a purge, and no #preview for one. Take a database backup first if the range is large and the history matters.

status#

/vg status
/vg stats
/vg version

The canonical diagnostic. All three spellings render the same report. It is read-only and on-demand — there is no always-on debug spam.

The report has these sections:

Section Contents
VonixGuardian Version.
Storage Backend type, schema version, DAO health (OK / UNHEALTHY).
Writer queue Consumer state, maintenance write-block, depth/max, submitted, gated, dropped, sink drops, quarantined, recovered, quarantine overflow and write-failure counters. Per-type submitted and dropped histograms when non-empty.
Rollback recovery Open rollback/restore batch ids with mode and affected count, plus vg_repair_required rows.
Coalescer Window, max tracked, active entries, suppressed, passed, evictions, cap drops. Omitted when coalescing is disabled.
Mixin hot events Kill-switch state, allocation rate, and per-type submit rates for the eight hot-tick mixin action types.
Event hooks The registered hook chain in order, plus the internal hook count.
Per-world overrides Count and list of worlds with a per-world config file.
Blacklist file Rule count, when blacklist.txt is loaded.
Auto-purge Enabled state and retention, or 0 = unbounded with the suggested 90-day horizon.
Permissions Default op level and the number of per-node overrides.
Public API API version.

Reading the rollback recovery section

An open batch means a rollback or restore did not finish. Boot does not replay it — by design, so a half-applied mutation is not applied a second time. Inspect the listed ids with /vg lookup and #verbose before re-running anything.

consumer#

/vg consumer                 ← report current state
/vg consumer pause
/vg consumer resume
/vg consumer toggle

Controls the async writer. Pausing stops rows reaching the database but does not stop events being queued:

[VonixGuardian] Consumer PAUSED — incoming events are buffered, not written.

Resuming drains the buffer:

[VonixGuardian] Consumer RESUMED — draining buffered events.

The bare form reports state and depth:

[VonixGuardian] Consumer is currently RUNNING (queue.depth=0)

Pausing is not free

A paused consumer keeps buffering until queue.maxSize (50,000 as shipped) is reached, then events are dropped with a WARN. Pause for maintenance windows, not indefinitely.

reload#

/vg reload

Re-reads config/vonixguardian/config.json from disk and hot-swaps the subsections that are safe to change in-process. It also reloads blacklist.txt and the per-world override files. The reload runs off the server thread.

Output names what took effect and what did not:

[VonixGuardian] Hot-swapped: 2 actions, purge
[VonixGuardian] Requires restart: 1 database
[VonixGuardian] Errors: 0 (none)

Keys reported as requires restart were detected on disk but are not applied; the old in-memory value stays live. If validation fails, the whole reload aborts and the live config is unchanged.

See Configuration for the complete hot-swap matrix.

config#

/vg config get <key>
/vg config set <key> <value>

Reads and writes individual keys without opening the file. set persists the change to disk, then runs the same validated reload path as /vg reload, so the value is live immediately — or reported as needing a restart.

/vg config get lookup.maxRadius
[VonixGuardian] lookup.maxRadius = 10000

/vg config set purge.autoPurgeSeconds 7776000
[VonixGuardian] Updated purge.autoPurgeSeconds = 7776000 (hot-swapped: purge)

Both operations are serialised under a config mutation lock, so two concurrent config set calls cannot clobber each other's full-file write.

Settable keys. Only these are accepted; anything else reports Unknown or read-only config key.

Group Keys
General theme, language
Log file logFile.enabled
Lookup lookup.defaultPageSize, lookup.maxRadius, lookup.maxResultRows
Privacy privacy.hashIps
Purge purge.minAgeSecondsConsole, purge.minAgeSecondsInGame, purge.autoPurgeSeconds, purge.autoPurgeTime
Actions actions.logBlocks, actions.logContainers, actions.logItems, actions.logEntities, actions.logExplosions, actions.logChat, actions.logCommands, actions.logSessions, actions.logSigns, actions.logInteractions, actions.logWorldEvents, actions.entityBlockChangeCoalesceWindowMs, actions.entityBlockChangeMaxTracked, actions.entityChangeLogAllEntities, actions.mixinHotEvents, actions.itemBlacklist, actions.entityBlacklist
Storage storage.persistNbt
Rollback rollback.explosionSupplementalReach

List values (actions.itemBlacklist, actions.entityBlacklist) are set as a comma- or whitespace-separated string. none or [] clears the list.

/vg config set actions.itemBlacklist none
/vg config set actions.entityBlacklist minecraft:zombie,create:contraption

Not settable by command

database.*, queue.*, permissions.*, lookup.maxConcurrent, logFile.directory, logFile.gzipRotated, logFile.retentionDays, logFile.forceSyncOnFlush, privacy.salt, rollback.mutationBatchSize and rollback.requireConfirm are file-only. Edit config.json and reload or restart.

entitylog#

/vg entitylog                       ← same as list
/vg entitylog list
/vg entitylog add <entity>
/vg entitylog remove <entity>

Manages the modded-entity griefing allowlist (actions.entityChangeAllowlist). This is the command that turns on auditing for a modded mob that breaks blocks.

/vg entitylog add isleofberk:night_fury
/vg entitylog add isleofberk:*
/vg entitylog add isleofberk
/vg entitylog list
/vg entitylog remove isleofberk

Three entry shapes are accepted:

Shape Example Matches
Exact registry key isleofberk:night_fury That one entity type.
Namespace wildcard isleofberk:* Every entity in that namespace.
Bare namespace isleofberk Equivalent to isleofberk:*.

Entries are lower-cased and stored verbatim, so list round-trips what you typed. Invalid input is rejected before anything touches disk:

[VonixGuardian] Invalid entity entry: 'isleo berk'. Use ns:path, ns:*, or ns.

Why an allowlist, not a blocklist

On Forge and NeoForge, LivingDestroyBlockEvent is a prospective query fired per mob tick — a flying dragon can fire it hundreds of thousands of times per second without destroying anything. Recording all of them would drown the write queue. The shipped policy is fail-closed: vanilla mobs known to genuinely change blocks are recorded, and modded mobs must be opted in here.

actions.entityChangeLogAllEntities=true bypasses the allowlist entirely and records everything. That restores pre-1.1.5 behaviour and will flood a modded pack. It is a diagnostic setting, not a production one.

teleport#

/vg teleport <world> <x> [y] <z>
/vg tp <world> <x> [y] <z>

Teleports you to a coordinate, typically one read from a lookup row.

/vg tp overworld 128 64 -342
/vg tp minecraft:the_nether -20 45 88

World accepts a full resource location, or the shorthands overworld, nether, end (which expand to minecraft:overworld, minecraft:the_nether, minecraft:the_end). Coordinates are plain numbers, 2 or 3 of them.

When you omit Y, your current Y is used, capped at 63 so you do not teleport into the void on a coordinate recorded underground:

/vg tp overworld 128 -342

Player only, and the target world must be loaded:

[VonixGuardian] Unknown world: the_moon

give#

/vg give <itemId> [amount]

Puts an item in your inventory, dropping it at your feet if the inventory is full. amount clamps to a minimum of 1 and defaults to 1.

/vg give minecraft:diamond 64
/vg give create:andesite_alloy 32
/vg give diamond                 ← namespace defaults to minecraft:

Player only. Unknown ids are rejected:

[VonixGuardian] Unknown item: minecraft:not_a_thing

migrate-db#

/vg migrate-db <sqlite|mysql|postgresql> CONFIRM

Copies the audit catalog from the active backend to the backend described by database.migrationTarget in config.json. Console only.

Without CONFIRM it prints what it would do and stops — this is the dry run:

[VonixGuardian] migrate-db: about to copy every audit row from 'sqlite' to 'mysql'.
[VonixGuardian] This is a one-way operation — the target must be at schema v9 and empty.
[VonixGuardian] To proceed, run: /vg migrate-db mysql CONFIRM

Preflight refusals, each with its own message:

  • No database.migrationTarget block in config.
  • The command's target type does not match migrationTarget.type.
  • Another maintenance write-block is already active.
  • The async pipeline did not go idle within 30 seconds.

The command blocks new audit writes, waits for the ring buffer, the worker's local batch, and any in-flight sink transaction to idle, then copies in 1,000-row chunks. That is a best-effort snapshot barrier, not a global database freeze.

Full procedure: Backend migration.

help#

/vg help

Prints the command summary. Bare /vg prints a shorter hint list. Bare /vg lookup, /vg rollback, /vg restore, and /vg purge print a three-line usage block with examples rather than brigadier's Unknown or incomplete command.

help is gated only by the root vonixguardian.base node.


Behaviour shared by mutating commands#

rollback, restore, undo, apply, purge, and migrate-db all run off-thread on a bounded worker pool, so they never stall a server tick. Two consequences worth knowing:

Saturation is visible, not silent. If the command worker queue is full, the command is rejected instead of queuing unboundedly:

[VonixGuardian] Command worker is saturated; retry shortly or reduce concurrent
heavy commands.

Output follows you. Results are routed back to your player entity by UUID at delivery time. If you disconnect mid-operation, the result goes to the console channel instead of being lost.

Superseded output is suppressed. Starting a second heavy command invalidates the first one's chat generation, so a slow rollback's result cannot overwrite the newer command's output.