Unofficial site, not affiliated with modrinth.com.What is this?
Плагины/CombatGunSSS
Все версииCombatGunSSS 2.0.7

CombatGunSSS 2.0.7

Release3 нед. назад

Список изменений

[2.0.7] - 2026-05-22

Fixed

🔴 StatsManager.flushBuffer() — Kill data silently lost under concurrent load (Critical)

  • Root cause: The old flush implementation called new HashMap<>(buffer) to snapshot the map, then immediately called buffer.clear(). The gap between these two statements allowed the main thread to call recordKill() and insert a new entry via computeIfAbsent. That new entry was then deleted by buffer.clear() — it was neither in the snapshot (inserted after it was taken) nor survived in the buffer (immediately cleared), so it was never written to SQLite.
  • Fix: Replaced the snapshot-and-clear pattern with a per-key drain loop: each entry is removed from the ConcurrentHashMap individually using remove(key). Since ConcurrentHashMap.remove() is per-key atomic, any new entry inserted by the main thread after its key has already been drained is guaranteed to remain in the map and be picked up by the next flush cycle. No kill data can be lost.

🔴 ThrowableManager — BukkitRunnable tasks not cancelled on plugin disable (Critical)

  • Root cause: onDisable() stopped the HUD task, bleeding tasks, reload tasks, and the SQLite connection — but never cancelled tasks created by ThrowableManager. The fuse-timer BukkitRunnable in handleThrow() and the smoke particle loop in detonateSmoke() continued to execute after the plugin was disabled, throwing IllegalPluginAccessException for every remaining tick until the tasks expired naturally.
  • Fix 1: Added a cancelAll() method to ThrowableManager that clears liveProjectiles and cancels all tracked smoke tasks.
  • Fix 2: detonateSmoke() now stores the returned BukkitTask reference in a ConcurrentHashMap<UUID, BukkitTask> keyed by a random UUID. The task removes its own entry when it completes normally. cancelAll() iterates this map and cancels every outstanding task.
  • Fix 3: CombatGunSSSPlugin.onDisable() now calls throwableManager.cancelAll() alongside the other existing cleanup calls.

🔴 GunListener — Duplicate import statement causes compiler warning (Low / Code Quality)

  • Root cause: GunListener.java contained two identical import java.util.concurrent.ThreadLocalRandom; declarations — one was introduced during a merge and never removed.
  • Fix: Removed the duplicate import. The class compiles cleanly with a single declaration.

🟡 GunListener.clearAds() — ADS exit incorrectly removes scope slowness (Medium)

  • Root cause: clearAds() used the condition existing.getAmplifier() <= 5 before removing the Slowness effect. This range is too broad: SCOPE_SLOWNESS = 3 falls within it. When a player was simultaneously scoped (Slowness level 3 applied by onSneak) and then exited ADS mode, clearAds() removed the Slowness effect entirely — stripping the scope movement penalty and leaving the player able to move at full speed while scoped.
  • Fix: Changed the condition to existing.getAmplifier() != SCOPE_SLOWNESS. ADS exit now only removes the Slowness effect when its amplifier level is not the scope level — leaving scope behaviour intact.

🟡 ReloadManager — Hardcoded English strings bypass i18n system (Medium)

  • Root cause: Four player-facing messages in ReloadManager were hardcoded English strings instead of routing through LangManager: "Magazine is already full!", "No <ammo> in inventory.", "Reload failed: no ammo left.", and the entire "✔ Reloaded! [x/y] -z ammo" completion message. Servers configured with language: vi displayed English during all reload feedback.
  • Fix: All four messages now call plugin.getLangManager().get(key) / .format(key, args) using the existing lang keys (gun.reload_full, gun.reload_no_ammo, gun.reload_failed, gun.reload_done) that were already defined in both lang/en.yml and lang/vi.yml but never wired up in ReloadManager.

🟡 BleedingManager.tryApply() — Inconsistent RNG usage (Medium)

  • Root cause: tryApply() used Math.random(), which delegates to a single shared java.util.Random instance. This is inconsistent with GunListener, which explicitly replaced static Random with ThreadLocalRandom.current() (with a comment explaining the reasoning). On servers with many simultaneous bleed chance rolls (burst fire hitting multiple targets), the shared lock in Math.random() causes minor contention.
  • Fix: Replaced Math.random() with ThreadLocalRandom.current().nextDouble(), consistent with the rest of the codebase.

🟡 ThrowableManager.detonateSmoke() — Inconsistent RNG usage (Medium)

  • Root cause: Same issue as BleedingManagerMath.random() used for particle position offsets inside a hot loop (20 calls per 4-tick interval per active smoke grenade).
  • Fix: Replaced all three Math.random() calls with ThreadLocalRandom.current().nextDouble().

🟡 AttachmentManager — Duplicate import statement (Code Quality)

  • Root cause: AttachmentManager.java contained two identical import org.bukkit.entity.Player; declarations introduced during a refactor.
  • Fix: Removed the duplicate import.

🟡 GunListener.getRecentDamage() — Mutable map reference exposed via public API (Medium)

  • Root cause: getRecentDamage() returned the internal HashMap<UUID, DamageRecord> reference directly. Any external code (addon plugins accessing GunListener via CombatGunAPI) calling getRecentDamage().clear() or .put(...) could silently corrupt kill-attribution logic without any indication.
  • Fix 1: getRecentDamage() now returns Collections.unmodifiableMap(recentDamage) — external callers can read the map but cannot mutate it.
  • Fix 2: Added getDamageRecord(UUID entityId) — a safer lookup method that returns the record only if it is non-null and within the TTL window. EntityDeathListener should use this instead of getRecentDamage().get(uuid) for correct TTL filtering.

The format is based on Keep a Changelog, and this project adheres to Semantic Versioning.

Метаданные

Канал релиза

Release

Номер версии

2.0.7

Загрузчики

Bukkit
Paper
Purpur
Spigot

Версии игры

1.21–1.21.11

Загрузок

175

Дата публикации

3 нед. назад

Загрузил

ID версии

Главная