Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions docs/README.skills.md
Original file line number Diff line number Diff line change
Expand Up @@ -209,6 +209,7 @@ See [CONTRIBUTING.md](../CONTRIBUTING.md#adding-skills) for guidelines on how to
| [microsoft-docs](../skills/microsoft-docs/SKILL.md) | Query official Microsoft documentation to find concepts, tutorials, and code examples across Azure, .NET, Agent Framework, Aspire, VS Code, GitHub, and more. Uses Microsoft Learn MCP as the default, with Context7 and Aspire MCP for content that lives outside learn.microsoft.com. | None |
| [microsoft-skill-creator](../skills/microsoft-skill-creator/SKILL.md) | Create agent skills for Microsoft technologies using Learn MCP tools. Use when users want to create a skill that teaches agents about any Microsoft technology, library, framework, or service (Azure, .NET, M365, VS Code, Bicep, etc.). Investigates topics deeply, then generates a hybrid skill storing essential knowledge locally while enabling dynamic deeper investigation. | `references/skill-templates.md` |
| [migrating-oracle-to-postgres-stored-procedures](../skills/migrating-oracle-to-postgres-stored-procedures/SKILL.md) | Migrates Oracle PL/SQL stored procedures to PostgreSQL PL/pgSQL. Translates Oracle-specific syntax, preserves method signatures and type-anchored parameters, leverages orafce where appropriate, and applies COLLATE "C" for Oracle-compatible text sorting. Use when converting Oracle stored procedures or functions to PostgreSQL equivalents during a database migration. | None |
| [minecraft-plugin-development](../skills/minecraft-plugin-development/SKILL.md) | Use this skill when building or modifying Minecraft server plugins for Paper, Spigot, or Bukkit, including plugin.yml setup, commands, listeners, schedulers, player state, team or arena systems, configuration files, Adventure text, and version-safe API usage. Trigger for requests like "build a Minecraft plugin", "add a Paper command", "fix a Bukkit listener", "create plugin.yml", "implement a minigame mechanic", or "debug server plugin behavior". | `references/bootstrap-registration.md`<br />`references/config-data-and-async.md`<br />`references/maps-heroes-and-feature-modules.md`<br />`references/project-patterns.md`<br />`references/state-sessions-and-phases.md` |
| [mkdocs-translations](../skills/mkdocs-translations/SKILL.md) | Generate a language translation for a mkdocs documentation stack. | None |
| [model-recommendation](../skills/model-recommendation/SKILL.md) | Analyze chatmode or prompt files and recommend optimal AI models based on task complexity, required capabilities, and cost-efficiency | None |
| [msstore-cli](../skills/msstore-cli/SKILL.md) | Microsoft Store Developer CLI (msstore) for publishing Windows applications to the Microsoft Store. Use when asked to configure Store credentials, list Store apps, check submission status, publish submissions, manage package flights, set up CI/CD for Store publishing, or integrate with Partner Center. Supports Windows App SDK/WinUI, UWP, .NET MAUI, Flutter, Electron, React Native, and PWA applications. | None |
Expand Down
212 changes: 212 additions & 0 deletions skills/minecraft-plugin-development/SKILL.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,212 @@
---
name: minecraft-plugin-development
description: 'Use this skill when building or modifying Minecraft server plugins for Paper, Spigot, or Bukkit, including plugin.yml setup, commands, listeners, schedulers, player state, team or arena systems, configuration files, Adventure text, and version-safe API usage. Trigger for requests like "build a Minecraft plugin", "add a Paper command", "fix a Bukkit listener", "create plugin.yml", "implement a minigame mechanic", or "debug server plugin behavior".'
---

# Minecraft Plugin Development

Use this skill for Minecraft server plugin work in the Paper, Spigot, and Bukkit ecosystem.

This skill is especially useful for gameplay-heavy plugins such as combat systems, wave or boss encounters, war or team modes, arenas, kit systems, cooldown-based abilities, scoreboards, and config-driven game rules.

For grounded implementation patterns drawn from real Paper plugins, load these references as needed:

- [`references/project-patterns.md`](references/project-patterns.md) for high-level architecture patterns seen in real gameplay plugins
- [`references/bootstrap-registration.md`](references/bootstrap-registration.md) for `onEnable`, command wiring, listener registration, and shutdown expectations
- [`references/state-sessions-and-phases.md`](references/state-sessions-and-phases.md) for player session modeling, game phases, match state, and reconnect-safe logic
- [`references/config-data-and-async.md`](references/config-data-and-async.md) for config managers, database-backed player data, async flushes, and UI refresh tasks
- [`references/maps-heroes-and-feature-modules.md`](references/maps-heroes-and-feature-modules.md) for map rotation, hero or class systems, and modular feature growth

## Scope

- In scope: Paper, Spigot, Bukkit plugin development
- In scope: `plugin.yml`, commands, tab completion, listeners, schedulers, configs, permissions, Adventure text, player state, minigame flow
- In scope: Java-based server plugin architecture, debugging, refactoring, and feature implementation
- Out of scope by default: Fabric mods, Forge mods, client mods, Bedrock add-ons

If the user says "Minecraft plugin" but the stack is unclear, first determine whether the project is Paper/Spigot/Bukkit or a modding stack.

## Default Working Style

When this skill triggers:

1. Identify the server API and version target.
2. Identify the build system and Java version.
3. Inspect `plugin.yml`, the main plugin class, and command or listener registration.
4. Map the gameplay flow before editing code:
- player lifecycle
- game phases
- timers and scheduled tasks
- team, arena, or match state
- config and persistence
5. Make the smallest coherent change that keeps registration, config, and runtime behavior aligned.

If the plugin is gameplay-heavy or stateful, read [`references/project-patterns.md`](references/project-patterns.md) and [`references/state-sessions-and-phases.md`](references/state-sessions-and-phases.md) before editing.

## Project Discovery Checklist

Check these first when present:

- `plugin.yml`
- `pom.xml`, `build.gradle`, or `build.gradle.kts`
- the plugin main class extending `JavaPlugin`
- command executors and tab completers
- listener classes
- config bootstrap code for `config.yml`, messages, kits, arenas, or custom YAML files
- scheduler usage through Bukkit scheduler APIs
- any player data, team state, arena state, or match state containers

## Core Rules

### Prefer the concrete server API in the repo

- If the project already targets Paper APIs, keep using Paper-first APIs instead of downgrading to generic Bukkit unless compatibility is explicitly required.
- Do not assume an API exists across all versions. Check the existing dependency and surrounding code style first.

### Keep registration in sync

When adding commands, permissions, or listeners, update the relevant registration points in the same change:

- `plugin.yml`
- plugin startup registration in `onEnable`
- any permission checks in code
- any related config or message keys

### Respect main-thread boundaries

- Do not touch world state, entities, inventories, scoreboards, or most Bukkit API objects from async tasks unless the API explicitly permits it.
- Use async tasks for external I/O, heavy computation, or database work, then switch back to the main thread before applying gameplay changes.

### Model gameplay as state, not scattered booleans

For gameplay plugins, prefer explicit state objects over duplicated flags:

- match or game phase
- player role or class
- cooldown state
- team membership
- arena assignment
- alive, eliminated, spectating, or queued state

When the feature affects NightMare-style or War-style gameplay, look for hidden state transitions first before patching symptoms.

### Favor config-driven values

When the feature includes damage, cooldowns, rewards, durations, messages, map settings, or toggles:

- prefer config-backed values over hardcoding
- provide sensible defaults
- keep key names stable and readable
- validate or sanitize missing values

### Be careful with reload behavior

- Avoid promising safe hot reload unless the code already supports it well.
- On config reload, ensure in-memory caches, scheduled tasks, and gameplay state are handled consistently.

## Implementation Patterns

### Commands

For new commands:

- add the command to `plugin.yml`
- implement executor and tab completion when needed
- validate sender type before casting to `Player`
- separate parsing, permission checks, and gameplay logic
- send clear player-facing feedback for invalid usage

### Listeners

For event listeners:

- guard early and return early
- check whether the current player, arena, or game phase should handle the event
- avoid doing expensive work in hot events such as move, damage, or interact spam
- centralize repeated checks where practical

### Scheduled Tasks

For timers, rounds, countdowns, cooldowns, or periodic checks:

- store task handles when cancellation matters
- cancel tasks on plugin disable and when a match or arena ends
- avoid multiple overlapping tasks for the same gameplay concern unless explicitly intended
- prefer one authoritative game loop over many loosely coordinated repeating tasks

### Player and Match State

For per-player or per-match state:

- define ownership clearly
- clean up on quit, kick, death, match end, and plugin disable
- avoid memory leaks from stale maps keyed by `Player`
- prefer `UUID` for persistent tracking unless a live player object is strictly needed

### Text and Messages

When the project uses Adventure or MiniMessage:

- follow the existing formatting approach
- avoid mixing legacy color codes and Adventure styles without a reason
- keep message templates configurable when messages are gameplay-facing

## High-Risk Areas

Pay extra attention when editing:

- damage handling and custom combat logic
- death, respawn, spectator, and elimination flow
- arena join and leave flow
- scoreboard or boss bar updates
- inventory mutation and kit distribution
- async database or file access
- version-sensitive API calls
- shutdown and cleanup in `onDisable`

## Output Expectations

When implementing or revising plugin code:

- produce runnable Java code, not pseudo-code, unless the user asks for design only
- mention any required updates to `plugin.yml`, config files, build files, or resources
- call out version assumptions explicitly
- point out thread-safety or API-compatibility risks when they exist
- preserve the project's existing conventions and folder structure

When the requested change touches plugin startup, async data, match flow, class systems, or rotating maps, consult the matching reference file before editing.

## Validation Checklist

Before finishing, verify as many of these as the task allows:

- the command, listener, or feature is registered correctly
- `plugin.yml` matches the implemented behavior
- imports and API types match the targeted server stack
- scheduler usage is safe
- config keys referenced in code exist or have defaults
- state cleanup paths exist for match end, player quit, and plugin disable
- there are no obvious null, cast, or lifecycle hazards

## Common Gotchas

- Casting `CommandSender` to `Player` without checking
- Updating Bukkit state from async tasks
- Forgetting to register listeners or declare commands in `plugin.yml`
- Using `Player` objects as long-lived map keys when `UUID` is safer
- Leaving repeating tasks alive after a round, arena, or plugin shutdown
- Hardcoding gameplay constants that should live in config
- Assuming Paper-only APIs in a Spigot-targeted plugin
- Treating reload as free even though stateful plugins often break under reload

## Preferred Response Shape

For substantial requests, structure work like this:

1. Current plugin context and assumptions
2. Gameplay or lifecycle impact
3. Code changes
4. Required registration or config updates
5. Validation and remaining risks

For small requests, keep the answer concise but still mention any needed `plugin.yml`, config, or lifecycle updates.
Original file line number Diff line number Diff line change
@@ -0,0 +1,100 @@
# Bootstrap And Registration

Use this reference when changing `onEnable`, `onDisable`, command setup, event wiring, or startup ordering.

## Bootstrap pattern from real plugins

### NightMare-style bootstrap

Common traits:

- connect database first
- register configuration serialization when needed
- initialize multiple config managers
- create gameplay managers and GUI helpers
- apply lobby UI to already-online players
- register many listeners explicitly
- start repeating tasks
- register commands and tab completers last

This pattern works well when startup must assemble many gameplay subsystems before the server can safely accept interactions.

### War-style bootstrap

Common traits:

- save default config and bundled resources first
- construct config wrapper and progression config
- connect database and create repository/service layers
- construct scoreboard, map, hero, and game services
- wire service dependencies together
- start background tasks
- preload async cache, then schedule main-thread UI refreshes
- register listeners and commands after service graph is ready

This pattern works well when player data and async services are first-class dependencies.

## Command registration rules

Observed practices:

- `NightMare` declares all commands in `plugin.yml`, then sets executors and a tab completer in code.
- `War` declares `leave` in `plugin.yml`, then checks for null before assigning the executor.

Recommended rules:

- always add new commands to `plugin.yml`
- if a command may be optional or renamed, null-check `getCommand`
- if tab completion exists, register it in the same change
- keep usage, permission, and permission-message aligned with actual code behavior

## Listener registration rules

Observed practices:

- both plugins register listeners in one place during startup
- listener constructors receive only the services they actually need

Recommended rules:

- keep registration centralized in the main plugin class or a clearly named bootstrap helper
- inject services explicitly instead of having listeners discover globals everywhere
- if a listener depends on a task, GUI, or manager, construct that dependency first

## Repeating tasks and startup ordering

Observed practices:

- `NightMare` starts periodic tasks directly from startup for height checks and spectator sidebar refreshes
- `War` starts background tasks via services such as `PlayerDataService` and `GameService`

Recommended rules:

- start repeating tasks only after required state holders exist
- cancel them in shutdown
- if the task mutates gameplay state, ensure it runs on the main thread
- if the task does I/O or cache rebuilds, prefer async execution and hop back to main thread for Bukkit work

## Shutdown expectations

Observed practices:

- `NightMare` deletes games, unloads maps, flushes pending stats, closes DB resources, and clears sidebars
- `War` shuts down game service, player data service, map manager, then disconnects database

Recommended rules:

- stop tasks
- flush dirty data
- detach or clear UI objects
- unload temporary worlds if your plugin creates them
- close database pools last

## Contribution guidance for this skill

When generating code for startup or shutdown, mention:

- which config or resource files must exist
- which commands or listeners must be registered
- what tasks must be started or canceled
- what resources require cleanup on disable
Loading
Loading