# messages.yml

## `messages.yml`

Every chat-facing string the plugin sends comes from this file. Edit it to translate, customise, or just match your server's voice. Apply changes with `/tcpvc reload`.

### MiniMessage

All values use [MiniMessage](https://docs.advntr.dev/minimessage/format.html) syntax. The basics:

| You write                                     | You see              |
| --------------------------------------------- | -------------------- |
| `<red>Text</red>`                             | red text             |
| `<gradient:red:blue>Text</gradient>`          | red-to-blue gradient |
| `<bold>Text</bold>`                           | bold                 |
| `<hover:show_text:'<gray>Hint'>Click</hover>` | hover tooltip        |
| `<click:run_command:'/help'>here</click>`     | clickable text       |

The plugin doesn't process `&`-style legacy color codes — only MiniMessage. If you copy templates from another plugin's `messages.yml`, convert `&c` → `<red>`, `&l` → `<bold>`, etc.

### Placeholders

Some keys accept `{name}`-style placeholders the plugin substitutes at render time. The substitutions for each key are documented inline below.

### Auto-prefix

Every player-facing key gets the `prefix` template prepended automatically. Keys under these namespaces are **NOT** auto-prefixed (they carry their own framing):

* `gui.*` — GUI titles and inventory names
* `hologram.*` — hologram line content
* `announce.*` — server-wide broadcasts

### Schema check

When the plugin loads, it compares your `messages.yml` against the expected key list. If keys are missing (e.g. you're upgrading from an older version that didn't have them), you'll see a single warning in the console listing every missing key. Missing keys silently fall back to the default text bundled with the plugin — nothing breaks.

To regenerate `messages.yml` from defaults: stop the server, delete the file, restart.

### Top-level

```yaml
prefix: "<dark_aqua>[VaultCrates]</dark_aqua> "
```

The prefix prepended to every player-facing line. Customise this to match your server's branding.

### `command.*`

| Key                               | Shown when                                                                                                        |
| --------------------------------- | ----------------------------------------------------------------------------------------------------------------- |
| `command.no-permission`           | Player without `tcpvc.admin` runs an admin command                                                                |
| `command.player-only`             | Console runs a player-only command (`/tcpvc gui`, `/tcpvc about`, `/tcpvc set`, `/tcpvc unset`, `/tcpvc preview`) |
| `command.unknown-subcommand`      | `/tcpvc <typo>` — placeholder `{sub}`                                                                             |
| `command.reload-success`          | `/tcpvc reload` succeeded — placeholder `{count}` (loaded crates)                                                 |
| `command.reload-failed`           | Reload threw — placeholder `{error}`                                                                              |
| `command.unknown-crate`           | `/tcpvc key give Steve typo …` — placeholders `{id}`, `{known}`                                                   |
| `command.invalid-tier`            | Bad `[tier]` argument — placeholder `{tier}`                                                                      |
| `command.invalid-amount`          | Bad `[amount]` argument — placeholder `{amount}`                                                                  |
| `command.tier-not-configured`     | The crate doesn't configure the tier you asked for — `{crate}`, `{tier}`                                          |
| `command.tier-required`           | Crate has both tiers; you didn't specify — `{crate}`                                                              |
| `command.no-tiers`                | Crate has zero tiers configured — `{crate}`                                                                       |
| `command.player-offline`          | `/tcpvc key give Steve …` and Steve isn't online — `{player}`                                                     |
| `command.key-given`               | Single-player give success — `{amount}`, `{crate}`, `{tier}`, `{player}`                                          |
| `command.key-given-all`           | Give-all success — `{amount}`, `{crate}`, `{tier}`, `{count}`                                                     |
| `command.key-give-all-no-players` | `give-all` with zero players online                                                                               |
| `command.set-look-at-vault`       | Tried to `/tcpvc set` without looking at a vault — `{type}`                                                       |
| `command.set-success`             | Set succeeded — `{location}`, `{crate}`                                                                           |
| `command.set-already-registered`  | Vault already registered as another crate — `{crate}`                                                             |
| `command.set-not-vault`           | Looked-at block isn't a vault                                                                                     |
| `command.unset-success`           | Unset succeeded — `{location}`                                                                                    |
| `command.unset-not-registered`    | Vault wasn't registered                                                                                           |
| `command.list-empty`              | Zero registered vaults in any loaded chunk                                                                        |
| `command.list-header`             | First line of `/tcpvc list` — `{count}`, `{page}`, `{totalPages}`                                                 |
| `command.list-row`                | One row in the list — `{crate}`, `{world}`, `{x}`, `{y}`, `{z}`                                                   |
| `command.list-more`               | Footer prompting next page — `{nextPage}`                                                                         |

### `open.*`

The most-shown lines on a busy server — every player sees these every time they open a crate.

| Key                            | Shown when                                                                    |
| ------------------------------ | ----------------------------------------------------------------------------- |
| `open.no-tier`                 | Tier the player tried to open isn't configured for the crate — `{tier}`       |
| `open.need-key`                | Player right-clicked without the right key — `{crate}`, `{tierLabel}`         |
| `open.no-bulk-keys`            | Shift-right-click but player has 0 matching keys — `{crate}`, `{tierLabel}`   |
| `open.already-opened`          | Already opened (per-player or server-wide cooldown) — `{crate}`               |
| `open.already-opened-one-time` | Already opened a one-time crate — `{crate}`                                   |
| `open.server-wide-locked`      | Vault locked for everyone in server-wide mode — `{time}` (formatted duration) |
| `open.success`                 | Single-open success header — `{crate}`, `{count}`, `{overflow}`               |
| `open.success-bulk`            | Bulk-open success header — `{crate}`, `{keys}`, `{count}`, `{overflow}`       |
| `open.overflow-suffix`         | Suffix appended when items dropped at feet — `{count}`                        |
| `open.line-item`               | One bullet in the loot summary — `{description}`                              |
| `open.line-item-stacked`       | Bulk-open aggregated bullet — `{description}`, `{count}`                      |
| `open.full-inventory-hint`     | Spoken to the player when their inventory was full — `{seconds}`              |

### `announce.*`

Not auto-prefixed.

| Key                  | Shown when                                                                      |
| -------------------- | ------------------------------------------------------------------------------- |
| `announce.broadcast` | A loot entry with `announce: true` is rolled — `{player}`, `{prize}`, `{crate}` |

### Examples

#### Translate to French

```yaml
prefix: "<dark_aqua>[Coffres]</dark_aqua> "
open:
  success: "<gold>{crate}</gold> <gray>ouvert —</gray> <yellow>{count}</yellow><gray> récompense(s)</gray>{overflow}"
  need-key: "<red>Il vous faut une <yellow>{tierLabel}</yellow> Clé <yellow>{crate}</yellow> pour ouvrir ce coffre."
announce:
  broadcast: "<gold>★</gold> <yellow>{player}</yellow> <gray>vient de gagner</gray> <yellow>{prize}</yellow> <gray>du coffre</gray> <gold>{crate}</gold><gray> !"
```

#### Match your server's brand voice

```yaml
prefix: "<gradient:#FF6B6B:#FFE66D>[★ DragonMC ★]</gradient> "
announce:
  broadcast: "<click:run_command:'/spawn'><hover:show_text:'<gray>Click to teleport to spawn'><yellow>{player}</yellow></hover></click> <gray>scored</gray> <gold>{prize}</gold> <gray>from the</gray> {crate}<gray>!"
```

The `announce.broadcast` line above is clickable — clicking it teleports the reader to spawn (via the `/spawn` command, configured on most servers via Essentials or similar). MiniMessage's full event support is available everywhere.

### Reload

```
/tcpvc reload
```

Reloads `crates.yml` and `messages.yml` together. No server restart needed. Send a few test messages after reloading to verify your templates render correctly.

***

Next: **WildSpawners integration →**


---

# Agent Instructions: Querying This Documentation

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

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://darkstarworks.gitbook.io/plugins/mc/tcp-documentation/tcp-vaultcrates/installation/messages.yml.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
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.
