Skip to main content
The mod kernel’s service registry is priority-ordered. By registering a service with a higher priority than Aether’s built-in implementation, your Native Mod becomes the active implementation for that service ID. Removing your registration automatically restores the next-lower-priority implementation.

API

Call context.registerService() inside onLoad:
AetherModServiceHandler is a fun interface with one suspend method:
ParameterDescription
idThe service identifier (e.g. "skills", "state", or a custom string).
descriptionOptional human-readable description of the service (defaults to "").
priorityHigher value wins. Aether core services use a deliberately low priority. Defaults to 100.
methodsThe list of AetherModServiceMethod instances describing the methods this implementation handles.
handlerAetherModServiceHandler invoked with the method name and a JSONObject of arguments; returns a JSONObject result.

Priority rules

Aether core services use a deliberately low priority so that Native Mods can override them with a standard priority value. Use priority 500 to reliably override any built-in service. Removing your registration (by calling the returned cleanup lambda) restores the next-lower-priority implementation, which may be another mod’s registration or Aether’s built-in.

Example — overriding the skills service

The following mod registers itself as the active implementation of the skills service and returns an empty skill list:
MyNativeMod.kt
context.registerService() returns a cleanup lambda. Call it to unregister the service before the mod is unloaded, or let onUnload handle it automatically.

Built-in services

The following services are registered by Aether core:

skills

MethodArguments
list
getSelection
setSelectionids, scope, session_id?
setSelectedskill_id, selected, scope, session_id?
Valid scope values: current, default / global, both / current_and_default.

state

MethodArguments
getpath
transactionoperations
You can expose entirely new services from a Native Mod — not just override existing ones. Other extensions discover them via aether.services.list() and invoke them via aether.services.invoke().