Skip to main content

Nexal Advent Calendar

A seasonal advent calendar that gives players a gift for every day from December 1st to 25th. Each calendar is a chest GUI with 25 doors that unlock day by day; players claim today's gift and any day they missed. A free and a premium calendar ship by default, each day runs console commands and hands out items, and everything from the timezone to the rewards can be edited in game from the admin panel.

Features​

  1. Festive Out of the Box - The free calendar is a Christmas tree of 25 gifts in a snowy night that lights up as gifts are opened; the premium calendar is a golden wall of presents that turns to gold. Special days (6th, 24th, 25th) stand out, and every door has its own locked, unlocked and opened look.
  2. 25-Day Calendar GUI - Every day is a door with a locked, unlocked and claimed look, placed anywhere in the chest from config.yml, with decorations around it.
  3. Catch Up on Missed Days - Any unlocked day that has not been claimed yet can still be claimed later in December.
  4. Multiple Calendars - A free default and a premium calendar ship by default, with vanilla rewards that grow toward Christmas; add as many as you like, each with its own claim permission.
  5. Command and Item Rewards - Each day runs console commands (%player% is the player) and gives items; items that do not fit are dropped at the player's feet.
  6. Rewards Above a Stack - An item reward can give any amount, handed out as several stacks.
  7. In-Game Reward Editor - See a calendar in its real layout, then add or delete commands (typed in chat) and item rewards (copied from your inventory) per day.
  8. Admin Panel - /ac admin opens settings, statistics, leaderboards, export and import.
  9. Settings Without YAML - Timezone, join reminder, reminder delay and each calendar's claim permission from the Configuration screen.
  10. Join Reminder - Players who have not claimed today's gift are reminded when they join.
  11. Timezone Support - Days roll over at midnight in the timezone you choose.
  12. Statistics and Leaderboards - Claims per calendar, top claimers overall and today, in chat or in the GUI.
  13. Dual Storage - JSON by default, MySQL or MariaDB with one setting, and export/import to move between them.
  14. Customizable Messages - Every player message lives in messages.yml with MiniMessage colors and sounds, and can be overridden per calendar or per day.
  15. Safe Upgrades - Configs written by older versions are fixed on startup.

Technologies​

  • Paper API 1.20.1+ - Minecraft server API (Spigot compatible)
  • Utilizer - Configuration, messages, items, tasks, GUIs
  • ACF - Command framework
  • nexal-core - JSON and SQL persistence (MariaDB/MySQL), help menu

Commands​

Aliases: /adventcalendar, /advent, /ac.

Player Commands​

CommandDescriptionPermission
/adventcalendarOpen the calendar selection panel (help menu from the console)nexaladventcalendar.open
/adventcalendar guiOpen the calendar selection panelnexaladventcalendar.open
/adventcalendar help [page]Show the help menuNone

Admin Commands​

CommandDescriptionPermission
/ac adminOpen the admin panel (admin help from the console)nexaladventcalendar.admin
/ac admin help [page]Show the admin help menunexaladventcalendar.admin
/ac admin open \<player> \<calendar>Open a calendar for a playernexaladventcalendar.admin
/ac admin testrewards \<calendar> \<day>Run a day's commands on yourself, and give its item rewards when run by a playernexaladventcalendar.admin
/ac admin statsClaim statistics for every calendarnexaladventcalendar.admin
/ac admin listtotal [calendar]Top 10 players by claims, in one calendar or allnexaladventcalendar.admin
/ac admin listtoday [calendar]Top 10 players who claimed today, ranked by claimsnexaladventcalendar.admin
/ac admin exportExport all user data to export/adventcalendar_users.jsonnexaladventcalendar.admin
/ac admin importImport user data from export/adventcalendar_users.json into the current storagenexaladventcalendar.admin

The selection panel's buttons run adventcalendar admin open %player% \<calendar> as console, so they work for every player even though the command itself is admin only. The older form /ac open \<player> \<calendar> still works, unlisted, so panels in configs from before 1.0.3 keep working.

Admin panel​

/ac admin opens a hub with:

  • Configuration: timezone (cycles through common zones), join reminder on/off, reminder delay, and per calendar its reward editor and whether it requires its claim permission
  • Statistics: tracked players and claims per calendar
  • Leaderboards: top 10 claimers per calendar, by most claims or who claimed today
  • Export Data and Import Data (shift click; import overwrites players already stored)

Configuration → Rewards: \<calendar> shows the calendar in its real layout. Hovering a day lists its commands and item rewards; clicking it opens that day's editor:

  • One item per command and one per item reward. Shift+right click deletes either.
  • Left click an item reward to set its amount (typed in chat, any positive number). Amounts above a stack are shown as one full stack with the real amount in the lore.
  • Add Command: type the command in chat, without /. %player% is the player's name; cancel aborts.
  • Add Item Reward adds a copy of the item in your hand, or click any item in your own inventory to add a copy of it. Your items are never moved or taken, and nothing can be taken out of the editor.

Up to 18 commands and 18 item rewards per day.

Permissions​

PermissionDescriptionDefault
nexaladventcalendar.openOpen the calendar selection panel with /adventcalendar and /adventcalendar guitrue
nexaladventcalendar.calendar.defaultClaim rewards from the default calendartrue
nexaladventcalendar.calendar.premiumClaim rewards from the premium calendarfalse
nexaladventcalendar.adminAdmin panel and every admin command, including /ac admin openop

A calendar's claim permission is calendars.\<id>.claim-permission in config.yml; leave it empty to let everyone claim. A new calendar's permission is not declared by the plugin, so it defaults to operators until your permissions plugin grants it.

Configuration​

config.yml and messages.yml reload by themselves when saved. Changing storage needs a restart.

config.yml​

# Timezone that decides when a new calendar day starts.
# An invalid zone falls back to UTC and logs a warning.
timezone: "UTC"

# Where player claims are stored: json (data.json) or sql (MySQL/MariaDB).
# To switch: /ac admin export, change type, restart the server, /ac admin import.
storage:
type: json
sql:
host: localhost
port: 3306
database: minecraft
username: root
password: ""

# Reminder on join between December 1st and 25th, for players who have not
# claimed today's reward from the default calendar.
reminder:
enabled: true
delay-seconds: 5 # seconds after joining
message: # chat lines plus a sound
message: [...]
sound: "BLOCK_NOTE_BLOCK_CHIME"

# The calendar selection panel (/adventcalendar)
menu:
title: "..."
size: 5 # rows, 1 to 6
items: &#123;...&#125; # fill, border, decorations and one button per calendar,
# running "cmd adventcalendar admin open %player% \<id>"

calendars:
default:
title: "..."
size: 6 # rows, 1 to 6
claim-permission: "nexaladventcalendar.calendar.default" # empty: everyone
messages: &#123;...&#125; # optional: override on-claim, already-claimed, locked, no-permission
items:
day-1:
slot: 0, 2 # row, column
locked: &#123;...&#125; # item shown before the day
unlocked: &#123;...&#125; # item shown while the gift can be claimed
claimed: &#123;...&#125; # item shown after claiming
commands: # run as console on claim
- "minecraft:give %player% minecraft:cookie 16"
item-rewards: # given on claim; easiest to edit in game
- item: &#123;...&#125; # Bukkit item serialization, amount 1
amount: 500
messages: &#123;...&#125; # optional: override this day's messages

messages.yml​

Every player message is customizable, in MiniMessage with a color reference at the top of the file, and supports sounds and titles. The claim messages (reward-claimed, reward-already-claimed, reward-locked, claim-no-permission) can be overridden per calendar under calendars.\<id>.messages or per day under calendars.\<id>.items.day-N.messages, with the keys on-claim, already-claimed, locked and no-permission.

While /ac admin import runs, gifts cannot be opened: players get claim-import-running and can try again a moment later.

Upgrading​

On startup the plugin fixes files written by an older version and logs what it changed:

  • glow is removed from every ENCHANTED_BOOK item. An enchanted book already glows, and the glow enchant would show as "Infinity X" in its lore.
  • Claim permissions adventcalendar.calendar.\<id> are renamed to nexaladventcalendar.calendar.\<id>.
  • Messages added in a newer version are added to messages.yml; your own messages are kept.

Database Schema​

When using SQL storage, the plugin creates the following table:

adventcalendar_users​

ColumnTypeKeyDescription
idVARCHAR(36)PKPlayer UUID
calendar_claims_jsonMEDIUMTEXTJSON object: calendar id → list of claimed days (epoch days)

With JSON storage the same records live under adventcalendar_users in data.json.

Key Legend: PK = Primary Key

Installation​

  1. Download the plugin JAR
  2. Place it in the /plugins folder
  3. Start or restart the server
  4. Edit the rewards in game with /ac admin, or in config.yml
  5. Set storage in config.yml and restart if you want SQL