ModularJobs
Developer

Events & services

The synchronous EventBus, lifecycle/payment events, and Bukkit services.

EventBus

Bridge.bridge().eventBus() is a synchronous, typed utility bus. Listeners register for an event class and receive events in priority order. Subscriptions can be removed explicitly; the plugin also releases all bridge-owned subscriptions when it disables.

var bus = Bridge.bridge().eventBus();
var subscription =
    bus.subscribe(JobLevelEvent.class, event -> {
      // event.getPlayerId(), event.getJob(), event.getNewLevel()
    });

bus.post(new JobLevelEvent(/* constructor arguments */));
subscription.unsubscribe();

Use postAsync(event) only for events whose listeners are safe to run away from the Bukkit thread. Bukkit wrapper events are still fired synchronously at the Paper boundary.

Lifecycle events

EventPayloadMutable?
JobJoinEventgetPlayerId(), getJob(), getPlayerJobState(), isRejoin()no
JobLeaveEventgetPlayerId(), getJob(), getPlayerJobState()no
JobLevelEventgetPlayerId(), getJob(), getPlayerJobState(), getOldLevel(), getNewLevel(), getReason() (EXPERIENCE / ADMIN_COMMAND / OTHER)no

Experience & payment events

EventPayloadMutable?
JobExperienceGainEventgetPlayerId(), getJob(), getPlayerJobState(), getExperienceGained() / setExperienceGained(...)yes — veto or alter the gain
JobsPrePaymentEventgetPlayerId(), getJob(), getJobTask(), getPayable()yes — pre-payment veto hook
JobsPaymentEventgetPlayerId(), getBase()yes — delivered-payment notification

All three implement Cancellable (isCancelled() / setCancelled(boolean)). The XP and pre-payment hooks are the main behavioral integration points.

Bukkit services

The plugin registers Bukkit services available to dependent plugins:

ServiceRegisteredNotes
ProfessionServicealwaysCore catalog/player-state facade
RecipeServiceprofession-apis.register-bukkit-services: trueLearned recipes (knows, learn, recipes)
BuffServicesame flagFood/combat consumable buffs (BuffSlot.FOOD/COMBAT)
StationServicesame flagStation-level crafting/gathering gates
NodeHarvestServicesame flagResource-node harvest integration
var svc = Bukkit.getServicesManager().load(ProfessionService.class);

ProfessionService: tracks(), resolve(String), level(UUID, String), experience(UUID, String), and ensureTrack(UUID, String).

Service facade (api)

The Bridge also exposes the plain interfaces integrators use directly:

InterfacePurpose
JobServiceComplete job trees, node-inherited tasks, player states, and join/leave operations
PreferencesServicePlayer page-size preference (getPageSize / setPageSize)
ExploitProtectionStoreProtections tracked per object (timers)
TimedBoostDataServiceSealed Target (GlobalTarget / PlayerTarget) + ActiveBoostData find/add/remove

On this page