> For the complete documentation index, see [llms.txt](https://docs.marioded.com/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.marioded.com/api-introduction/concepts.md).

# Services, recordings, and sessions

Get to know the services and data objects before creating your first recording.

Before we write the integration, let's give names to the objects we will work with. Reverse has three runtime entry points, and each one exposes services for a particular job.

## The runtime entry points

Use the entry point for the server your plugin runs on:

```java
ReverseRecorder recorder = ReverseRecorder.get().orElseThrow();
```

This asks Bukkit for the active recorder provider. It does not create a new recorder. The player and lobby expose the same discovery pattern through `ReversePlayer.get()` and `ReverseLobby.get()`.

An empty Optional means the provider is unavailable, for example because that role is absent or did not finish initialization. Declare the dependency in your plugin descriptor, then discover it during `onEnable`.

## A service performs an operation

The entry point gives us the service that owns the operation:

```java
RecorderService recording = recorder.getRecorderService();
RecordSession session = recording.startRecording(world);
```

Here, `RecorderService` controls capture. Other services handle playback, catalog access, rendering, or UI controls. Borrow these services from Reverse rather than constructing its implementation classes.

{% hint style="info" %}
**You own the integration, not the runtime.** Close your own resources and retire your own registrations. Do not close Reverse's shared storage or availability service from your plugin.
{% endhint %}

## `RecordSession`: a recording in progress

`RecordSession` represents live capture. Keep its UUID with your match:

```java
UUID sessionId = session.getUniqueId();
```

Later, stop that session through the recorder service:

```java
recording.stopSession(sessionId);
```

The stop operation returns a stage because saving takes time. Stopping capture and completing a save are different lifecycle points; we will handle both in the first tutorial.

## `Replay`: a saved recording's metadata

A catalog entry exposes `Replay`: its ID, name, description, owners, timing, world ID, and terrain identifier. This is enough to draw a list or details screen without loading all events.

`LoadedReplay` adds the immutable event stream needed for playback. Use catalog queries for browsing; load the full replay when you need its timeline.

## `PlaybackSession`: one viewing instance

A `PlaybackSession` is an active viewing of a saved recording. It has its own viewer list, cursor, pause state, speed, and entity mappings.

One recording can be played by several independent sessions. Several viewers in **one** session share its controls and timeline. Viewer-specific hotbar state does not create a separate playback cursor.

## Which UUID should I keep?

| Value                | Meaning                                           | Use it for                                                                     |
| -------------------- | ------------------------------------------------- | ------------------------------------------------------------------------------ |
| Recording session ID | The live recording and the replay it will produce | Stop the exact match recording; store its resulting replay reference.          |
| Replay ID            | A saved recording                                 | Catalog queries, loading, playback, and lobby selection.                       |
| Playback session ID  | One active viewing instance                       | Track that viewing session independently of other sessions of the same replay. |
| Bukkit world ID      | The source world                                  | Identify the world, not a particular recording of it.                          |

The terrain identifier is separate and is a **string**, not necessarily a UUID. It can refer to captured chunks or a named template.

## Owners are not participants

* **Owners** decide who may access the finished recording through the catalog.
* **Participants** decide which players are selected for capture.
* **Bounds** select the spatial area to record.

For example, a moderator can own a recording without being one of its participants. We will keep these choices separate in the next tutorials.

## Let's create a recording

{% content-ref url="/pages/Oe1TaTGh7xnJGD8C5Gmi" %}
[Creating your first recording](/api-introduction/first-recording.md)
{% endcontent-ref %}


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation by asking a question.

Perform an HTTP GET request on the following URL with the `ask` and `goal` query parameters:

```
GET https://docs.marioded.com/api-introduction/concepts.md?ask=<question>&goal=<user_goal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is what the user is ultimately trying to achieve, the reason they need the answer. Sharing it helps GitBook give you a better, more relevant answer. A goal is most helpful when it describes the outcome the user wants rather than restating the question. For example, with `ask=how do I create an API token`, a goal like `automate deployments from our CI pipeline` lets GitBook tailor the answer to that use case.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
