lightkeeper-parent 1.2.0-SNAPSHOT API
LightKeeper API
LightKeeper runs integration tests for Minecraft plugins against real Paper and Spigot servers. Tests use a typed Java API to create worlds and synthetic players, interact with plugins, capture events, and assert the resulting server state.
This overview introduces the API entry points and a typical test. For dependencies, server provisioning, and configuration, start with the LightKeeper documentation site. The package and class documentation here describes the API in detail.
Start with LightkeeperAssertions
LightkeeperAssertions
is the main entry point for assertions. Statically import its assertThat method to check worlds,
players, menus, captured events, and other LightKeeper objects. Follow the returned assertion types to discover
the checks and navigation available for each subject.
import static nl.pim16aap2.lightkeeper.framework.assertions.LightkeeperAssertions.assertThat;
The same import also provides ordinary AssertJ assertions for strings, collections, and other Java values. See the assertions package for the full set of supported subjects.
A first test
Once Maven's prepare-server goal has provisioned a runtime and
lightkeeper.runtimeManifestPath points to its manifest,
LightkeeperExtension
manages the server lifecycle and injects
ILightkeeperFramework
into test methods. The framework groups operations under server(), worlds(),
bots(), and events().
import nl.pim16aap2.lightkeeper.framework.BlockPos;
import nl.pim16aap2.lightkeeper.framework.ILightkeeperFramework;
import nl.pim16aap2.lightkeeper.framework.LightkeeperExtension;
import nl.pim16aap2.lightkeeper.framework.WorldHandle;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.extension.ExtendWith;
import static nl.pim16aap2.lightkeeper.framework.assertions.LightkeeperAssertions.assertThat;
@ExtendWith(LightkeeperExtension.class)
class MyPluginIT
{
@Test
void world_shouldContainPlacedBlock(ILightkeeperFramework framework)
{
// setup
final WorldHandle world = framework.worlds().main();
// execute
world.setBlockAt(new BlockPos(1, 100, 0), "minecraft:stone");
// verify
assertThat(world).hasBlockAt(1, 100, 0).ofType("minecraft:stone");
}
}
Waiting for plugin effects
Assertions are eager and read-only: they check the state observed when called and never wait implicitly.
Handles query live server state; snapshots and collection navigation freeze an observation.
For asynchronous effects, use
LightkeeperAssertions.eventually
and recreate the complete assertion chain inside its callback.
For example, given a player created through framework.bots(), if your plugin's
myplugin run command sends done after background work completes:
import nl.pim16aap2.lightkeeper.framework.assertions.LightkeeperAssertions;
import java.time.Duration;
import static nl.pim16aap2.lightkeeper.framework.assertions.LightkeeperAssertions.assertThat;
// inside the test: execute the command once, outside the retry callback
player.executeCommand("myplugin run");
// re-read the messages on every attempt, for up to ten seconds
LightkeeperAssertions.eventually(
Duration.ofSeconds(10),
() -> assertThat(player)
.receivedMessages()
.contains("done")
);
Explore the API
ILightkeeperFrameworkprovides access to server control, worlds, bots, and event capture. For manual lifecycle management, useLightkeeper.startand close the returned framework with try-with-resources.WorldHandle,PlayerHandle, andMenuHandleexpose world, player, and menu interactions.EventCaptureHandlerecords Bukkit events for inspection and assertions.- The framework package contains the public handles, builders, specifications, and snapshots used in tests.
- The protocol package and the runtime package document the wire messages and runtime manifest for readers working on lower-level integrations.