BlazeBans API/Reacting to events

Event reference

Seven Bukkit events, registered the normal way.

java
getServer().getPluginManager().registerEvents(new MyListener(), this);

All seven are Cancellable, but cancelling means something different on each. That is the part worth reading carefully.

The seven

EventFiresCancelling
BlazeBansPunishmentCreateEventBefore a punishment is storedPrevents creation entirely
BlazeBansPunishmentCreatedEventAfter it is storedDoes not undo it. Suppresses the follow-up
BlazeBansPunishmentRevokeEventBefore a revocationPrevents the revocation
BlazeBansPunishmentRevokedEventAfter it is revokedDoes not undo it. Suppresses the follow-up
BlazeBansPunishmentEnforceEventBefore one enforcement actionSkips that action only
BlazeBansMutedChatEventA muted player's chat is about to be blockedLets the message through
BlazeBansMutedCommandEventA muted player's command is about to be blockedLets the command through

Before creation

java
@EventHandler
public void onPunishmentCreate(BlazeBansPunishmentCreateEvent event) {
    PunishmentCreateRequest request = event.request();

    if (request.reason().isBlank()) {
        request.reason("Reason supplied by MyPlugin");
    }

    if (request.type() == PunishmentType.BAN && isProtected(request.targetName())) {
        event.setCancelled(true);
    }
}

request() is mutable, and every field on it can be changed. Type, target, staff, duration, reason, proof, scope, and silent are all in play before the record is written.

This is the only place you can change a punishment before it exists. Cancelling here means nothing is stored, nothing is announced, and the caller gets an empty Optional.

After creation

java
@EventHandler
public void onPunishmentCreated(BlazeBansPunishmentCreatedEvent event) {
    Punishment punishment = event.punishment();
    getLogger().info("Created " + punishment.id() + " for " + punishment.targetName());
}

punishment() is the stored record, with its real ID.

Cancelling this event does not undo the punishment. It suppresses BlazeBans' immediate follow-up: removing an online player, notifying the victim, the staff broadcast, the Discord post, and any ladder actions.

That distinction matters. A cancelled ban-created event can stop the player being kicked right now, and the ban is still stored and still enforced at their next login. If you want the punishment not to happen, cancel the create event instead.

This event also carries enforcementDelay(), covered in Enforcement and exemptions.

Before and after revocation

java
@EventHandler
public void onPunishmentRevoke(BlazeBansPunishmentRevokeEvent event) {
    PunishmentRevokeRequest request = event.request();
    getLogger().info("Revoking for " + request.target());
    request.reason(request.reason() + " (reviewed by MyPlugin)");
}

The revoke request exposes types() and target() as read-only, and staffName() and reason() as mutable. Cancelling prevents the revocation.

BlazeBansPunishmentRevokedEvent fires afterwards with the updated record. Cancelling it suppresses the follow-up output only; the revocation is already stored.

Muted chat and commands

These two work backwards from the others, and it catches people out.

java
@EventHandler
public void onMutedChat(BlazeBansMutedChatEvent event) {
    // Cancelling tells BlazeBans NOT to block this message.
    if (isStaffChannel(event.message())) {
        event.setCancelled(true);
    }
}

The event fires when BlazeBans is about to block something. Cancelling the BlazeBans event means "do not block it", so cancellation is an exemption.

Another plugin can still cancel the underlying chat or command event independently. You are only telling BlazeBans to stand down.

BlazeBansMutedChatEvent gives you punishment(), playerName(), playerUuid(), and message(). BlazeBansMutedCommandEvent gives the same with command() instead of message().

Enforcement

java
@EventHandler
public void onEnforcement(BlazeBansPunishmentEnforceEvent event) {
    if (event.enforcementType() == BlazeBansEnforcementType.BAN_LOGIN) {
        getLogger().info("Denying login for " + event.playerName());
    }
}

Fires before each individual enforcement action, with enforcementType(), punishment(), playerName(), and playerUuid().

TypeAction
BAN_LOGINDenying a login, or removing an online banned player
KICKKicking a player
MUTE_CHATBlocking a muted player's message
MUTE_COMMANDBlocking a configured command while muted

Cancelling skips that one action. It does not revoke the punishment, and it does not stop the next attempt. A cancelled BAN_LOGIN lets the player in this time; the ban is still active and still denies the next login.

Priorities

Ordinary Bukkit priorities apply.

java
@EventHandler(priority = EventPriority.HIGHEST)
public void onPunishmentCreate(BlazeBansPunishmentCreateEvent event) { }

Use LOWEST to modify a request before other plugins see it, HIGHEST to have the final say on cancellation. If you only observe, set ignoreCancelled = true so you are not told about punishments that never happened:

java
@EventHandler(ignoreCancelled = true)
public void onPunishmentCreate(BlazeBansPunishmentCreateEvent event) { }

Which event to use

You want toListen to
Block a punishment before it existsBlazeBansPunishmentCreateEvent
Change a reason, duration, or scopeBlazeBansPunishmentCreateEvent
Log or forward a punishment that happenedBlazeBansPunishmentCreatedEvent
Play an effect before the player is removedBlazeBansPunishmentCreatedEvent with a delay
Stop an unban going throughBlazeBansPunishmentRevokeEvent
Let one command work while mutedBlazeBansMutedCommandEvent, cancelled
Stop a specific kick or login denialBlazeBansPunishmentEnforceEvent

A listener covering the common cases

java
package com.example.myaddon;

import net.blazebans.api.event.BlazeBansMutedCommandEvent;
import net.blazebans.api.event.BlazeBansPunishmentCreateEvent;
import net.blazebans.api.event.BlazeBansPunishmentCreatedEvent;
import net.blazebans.api.punishment.PunishmentType;
import java.util.Locale;
import org.bukkit.event.EventHandler;
import org.bukkit.event.EventPriority;
import org.bukkit.event.Listener;

public final class MyListener implements Listener {

    @EventHandler(priority = EventPriority.LOW)
    public void onCreate(BlazeBansPunishmentCreateEvent event) {
        if (event.request().reason().isBlank()) {
            event.request().reason("No reason given");
        }
    }

    @EventHandler(ignoreCancelled = true)
    public void onCreated(BlazeBansPunishmentCreatedEvent event) {
        if (event.punishment().type() == PunishmentType.BAN && !event.punishment().silent()) {
            forwardToMySystem(event.punishment());
        }
    }

    @EventHandler
    public void onMutedCommand(BlazeBansMutedCommandEvent event) {
        if (event.command().toLowerCase(Locale.ROOT).startsWith("/appeal")) {
            event.setCancelled(true);
        }
    }
}