Compatibility
Minecraft: Java Edition
Platforms
Creators
Details
Changelog
Added Features Configurable Vault Limits: Introduced config.yml with max_vaults (default: 10). Admins can now easily increase/decrease the maximum number of vaults per player. Permissions (playervaults.use.<number>) scale automatically to the new max—grant additional perms as needed. Periodic Auto-Saving: New save_interval config (default: 300 seconds / 5 minutes) triggers automatic saves of modified vaults. Protects against data loss from crashes or unexpected shutdowns without relying solely on inventory close or plugin disable. Smart Preloading on Startup: Always preloads vaults for online players to ensure instant access. Optional preloading for offline players via preload_offline_vaults config (default: false). This prevents memory overload on large servers while keeping lazy-loading for rarely accessed offline data. Logs preload stats (e.g., "Preloaded vaults for X players") for easy monitoring. Dirty Flag System for Efficient Saves: Tracks vault modifications per player/vault using a lightweight boolean map. Only changed ("dirty") vaults are saved during periodic saves, on close, or shutdown—reducing unnecessary disk I/O and TPS impact. Interaction Detection: Added InventoryClickEvent listener to mark vaults as "dirty" on any click (item placement, removal, etc.). Ensures saves only occur after real changes, optimizing for idle sessions. Bug Fixes ItemStack Persistence & Deserialization: Original loadVault used getList with direct cast to ItemStack[], which failed silently on YAML-stored maps (resulting in empty vaults after restarts). Fixed: Now loads raw List<?> and explicitly deserializes each slot using ItemStack.deserialize(Map) for YAML maps, handles direct ItemStack objects, and treats invalid/null entries as empty slots. Preserves nulls (empty slots) correctly. Original saveVault used List.of(vault.getContents()), creating a List<ItemStack[]> instead of List<ItemStack>, breaking deserialization. Fixed: Switched to Arrays.asList(vault.getContents()) for proper List<ItemStack> serialization. Bukkit's ConfigurationSerializable now handles enchants, NBT, amounts, and custom data reliably across restarts. Vault Number Validation: Enforced max_vaults limit in preloading, creation, and saving—skips out-of-range vaults to prevent config bloat or errors. Original hardcoded 10 is now flexible. UUID Handling in Preload: Original had no preloading; new version safely parses UUID strings from Vaults.yml keys, skips invalid ones, and avoids double-loading online players. Save on Shutdown: Original saved all vaults; now only saves dirty ones, but ensures all modified data is persisted. Clears maps properly to free memory. Error Resilience: Added try-catch for UUID/vault number parsing in preload and events. Logs warnings for invalid config entries (e.g., bad vault numbers) without crashing. Improvements Performance & Memory Optimization: Lazy-loading remains for unloaded vaults (fallback in getVault), but preloading is now targeted (online-first, optional offline) to avoid loading thousands of unused inventories on startup. Dirty flags eliminate redundant saves: Unchanged vaults (e.g., opened but untouched) skip saving on close/periodic, reducing file writes and lag on busy servers. Periodic saves are scoped to dirty vaults only, minimizing TPS dips (e.g., no full scans of clean data every 5 minutes). Synchronous saves (main thread) for YAML thread-safety, but low-frequency and efficient—ideal for most servers. (Async could be added later if needed.) Code Structure & Maintainability: Refactored into modular methods: preloadPlayerVaults(UUID) for reusable loading, saveDirtyVaults() for targeted saves. Consistent UUID usage (instead of mixing Player/OfflinePlayer) for offline compatibility. Auto-generates config.yml with defaults via saveDefaultConfig() and explicit sets—reloadable with /reload (restart recommended for max_vaults changes). Enhanced logging: Startup info, preload counts, save errors, and invalid data warnings for easier debugging. Security & Usability: Vault titles and permissions unchanged, but now dynamically respect max_vaults in command feedback (e.g., "between 1 and X"). Handles edge cases like list size mismatches in loading (extras ignored, shorts fill with empties). Full persistence guarantee: Data survives startups, shutdowns, restarts, and crashes (via periodic saves). Players' items remain until manually removed. Event Handling: InventoryCloseEvent: Now checks dirty flag before saving—skips if clean. New InventoryClickEvent: Quick title check to mark dirty without content diffs (lightweight and accurate). Configuration Changes New config.yml (auto-created with defaults):
max_vaults: 10 save_interval: 300 # Seconds between auto-saves (0 to disable) preload_offline_vaults: false # true to load all offline players' vaults on startup



