From 5beabfad3adab9e325ec5ea9d70ec6f6ccc3aca2 Mon Sep 17 00:00:00 2001 From: RootBeer Date: Thu, 7 May 2026 10:30:52 -0400 Subject: [PATCH 1/5] Rewrite Bungee expansion and give it more adequate naming & more --- LICENSE | 2 +- README.md | 3 - pom.xml | 36 ++--- .../ProxyExpansion.java} | 132 +++++++++--------- 4 files changed, 86 insertions(+), 87 deletions(-) delete mode 100644 README.md rename src/main/java/com/extendedclip/papi/{bungeeexpansion/BungeeExpansion.java => proxyexpansion/ProxyExpansion.java} (50%) diff --git a/LICENSE b/LICENSE index 3d90694..818433e 100644 --- a/LICENSE +++ b/LICENSE @@ -671,4 +671,4 @@ into proprietary programs. If your program is a subroutine library, you may consider it more useful to permit linking proprietary applications with the library. If this is what you want to do, use the GNU Lesser General Public License instead of this License. But first, please read -. \ No newline at end of file +. diff --git a/README.md b/README.md deleted file mode 100644 index bdab0e8..0000000 --- a/README.md +++ /dev/null @@ -1,3 +0,0 @@ -# Bungeecord-Expansion -Expansion for bungeecord placeholders -[![Build Status](http://ci.extendedclip.com/buildStatus/icon?job=Bungeecord-Expansion)](http://ci.extendedclip.com/job/Bungeecord-Expansion/) diff --git a/pom.xml b/pom.xml index d820ae1..62d4d33 100644 --- a/pom.xml +++ b/pom.xml @@ -2,23 +2,25 @@ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> 4.0.0 - com.extendedclip.papi.bungeeexpansion - bungee-expansion - 2.2 + com.extendedclip.papi.proxyexpansion + proxy-expansion + 1.0 - Expansion-Bungee - PlaceholderAPI expansion for bungeecord placeholders + Expansion-Proxy + PlaceholderAPI expansion for proxy placeholders. - 1.8 - 1.8 + 25 + 25 + UTF-8 - spigot-repo - https://hub.spigotmc.org/nexus/content/repositories/snapshots/ + papermc + https://repo.papermc.io/repository/maven-public/ + placeholderapi https://repo.extendedclip.com/content/repositories/placeholderapi/ @@ -27,31 +29,33 @@ - org.spigotmc - spigot-api - 1.15.2-R0.1-SNAPSHOT + io.papermc.paper + paper-api + [26.1.2.build,) provided + me.clip placeholderapi - 2.10.6 + 2.12.2 provided + ${project.name}-${project.version} org.apache.maven.plugins maven-jar-plugin - 3.2.0 + 3.5.0 - ${project.name} false false + true @@ -59,4 +63,4 @@ - \ No newline at end of file + diff --git a/src/main/java/com/extendedclip/papi/bungeeexpansion/BungeeExpansion.java b/src/main/java/com/extendedclip/papi/proxyexpansion/ProxyExpansion.java similarity index 50% rename from src/main/java/com/extendedclip/papi/bungeeexpansion/BungeeExpansion.java rename to src/main/java/com/extendedclip/papi/proxyexpansion/ProxyExpansion.java index e53cb4e..d75d0e1 100644 --- a/src/main/java/com/extendedclip/papi/bungeeexpansion/BungeeExpansion.java +++ b/src/main/java/com/extendedclip/papi/proxyexpansion/ProxyExpansion.java @@ -1,8 +1,7 @@ -package com.extendedclip.papi.bungeeexpansion; +package com.extendedclip.papi.proxyexpansion; import com.google.common.base.Splitter; import com.google.common.collect.Iterables; -import com.google.common.io.ByteArrayDataInput; import com.google.common.io.ByteArrayDataOutput; import com.google.common.io.ByteStreams; import me.clip.placeholderapi.expansion.Configurable; @@ -12,19 +11,25 @@ import org.bukkit.OfflinePlayer; import org.bukkit.entity.Player; import org.bukkit.plugin.messaging.PluginMessageListener; -import org.bukkit.scheduler.BukkitTask; +import org.jetbrains.annotations.NotNull; +import org.jspecify.annotations.NonNull; import java.io.ByteArrayInputStream; import java.io.DataInputStream; -import java.lang.reflect.Field; +import java.util.ArrayList; import java.util.Collections; -import java.util.HashMap; import java.util.Map; +import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.Executors; +import java.util.concurrent.ScheduledExecutorService; +import java.util.concurrent.ScheduledFuture; +import java.util.concurrent.TimeUnit; import java.util.concurrent.atomic.AtomicReference; import java.util.function.Consumer; import java.util.logging.Level; -public final class BungeeExpansion extends PlaceholderExpansion implements PluginMessageListener, Taskable, Configurable { +@SuppressWarnings("unused") +public final class ProxyExpansion extends PlaceholderExpansion implements PluginMessageListener, Taskable, Configurable { private static final String MESSAGE_CHANNEL = "BungeeCord"; private static final String SERVERS_CHANNEL = "GetServers"; @@ -33,34 +38,27 @@ public final class BungeeExpansion extends PlaceholderExpansion implements Plugi private static final Splitter SPLITTER = Splitter.on(",").trimResults(); + private final Map counts = new ConcurrentHashMap<>(); + private final AtomicReference> cached = new AtomicReference<>(); - private final Map counts = new HashMap<>(); - private final AtomicReference cached = new AtomicReference<>(); - - private static Field inputField; - - static { - try { - inputField = Class.forName("com.google.common.io.ByteStreams$ByteArrayDataInputStream").getDeclaredField("input"); - inputField.setAccessible(true); - } catch (Exception e) { - e.printStackTrace(); - } - } + private ScheduledExecutorService executor; @Override + @NotNull public String getIdentifier() { - return "bungee"; + return "proxy"; } @Override + @NotNull public String getAuthor() { return "clip"; } @Override + @NotNull public String getVersion() { - return "2.3"; + return "1.0"; } @Override @@ -68,41 +66,38 @@ public Map getDefaults() { return Collections.singletonMap(CONFIG_INTERVAL, 30); } - @Override public String onRequest(final OfflinePlayer player, String identifier) { - final int value; - - switch (identifier.toLowerCase()) { - case "all": - case "total": - value = counts.values().stream().mapToInt(Integer::intValue).sum(); - break; - default: - value = counts.getOrDefault(identifier.toLowerCase(), 0); - break; - } + final int value = switch (identifier.toLowerCase()) { + case "all", "total" -> counts.values().stream().mapToInt(Integer::intValue).sum(); + default -> counts.getOrDefault(identifier.toLowerCase(), 0); + }; return String.valueOf(value); } @Override public void start() { - final BukkitTask task = Bukkit.getScheduler().runTaskTimer(getPlaceholderAPI(), () -> { + if (executor == null) { + executor = Executors.newSingleThreadScheduledExecutor(r -> { + final Thread thread = new Thread(r, "ProxyExpansion-Scheduler"); + thread.setDaemon(true); + return thread; + }); + } + + final ScheduledFuture task = executor.scheduleAtFixedRate(() -> { if (counts.isEmpty()) { sendServersChannelMessage(); - } - else { + } else { counts.keySet().forEach(this::sendPlayersChannelMessage); } + }, 2L, getLong(CONFIG_INTERVAL, 30), TimeUnit.SECONDS); - }, 20L * 2L, 20L * getLong(CONFIG_INTERVAL, 30)); - - - final BukkitTask prev = cached.getAndSet(task); + final ScheduledFuture prev = cached.getAndSet(task); if (prev != null) { - prev.cancel(); + prev.cancel(false); } else { Bukkit.getMessenger().registerOutgoingPluginChannel(getPlaceholderAPI(), MESSAGE_CHANNEL); Bukkit.getMessenger().registerIncomingPluginChannel(getPlaceholderAPI(), MESSAGE_CHANNEL, this); @@ -111,50 +106,55 @@ public void start() { @Override public void stop() { - final BukkitTask prev = cached.getAndSet(null); + final ScheduledFuture prev = cached.getAndSet(null); if (prev == null) { return; } - prev.cancel(); + prev.cancel(false); counts.clear(); + if (executor != null) { + executor.shutdownNow(); + executor = null; + } + Bukkit.getMessenger().unregisterOutgoingPluginChannel(getPlaceholderAPI(), MESSAGE_CHANNEL); Bukkit.getMessenger().unregisterIncomingPluginChannel(getPlaceholderAPI(), MESSAGE_CHANNEL, this); } - @Override - public void onPluginMessageReceived(final String channel, final Player player, final byte[] message) { + public void onPluginMessageReceived(final @NonNull String channel, final @NonNull Player player, final byte @NonNull [] message) { if (!MESSAGE_CHANNEL.equals(channel)) { return; } - //noinspection UnstableApiUsage - final ByteArrayDataInput in = ByteStreams.newDataInput(message); - try { - DataInputStream stream = (DataInputStream) inputField.get(in); + try (DataInputStream in = new DataInputStream(new ByteArrayInputStream(message))) { switch (in.readUTF()) { - case PLAYERS_CHANNEL: - if (stream.available() == 0) return; // how ? - final String server = in.readUTF(); - if (stream.available() == 0) { // how ? x2 - getPlaceholderAPI().getLogger().log(Level.SEVERE, String.format("[%s] Could not get the player count from server %s.", getName(), server)); - counts.put(server.toLowerCase(), 0); - } else counts.put(server.toLowerCase(), in.readInt()); - break; - case SERVERS_CHANNEL: - SPLITTER.split(in.readUTF()).forEach(serverName -> counts.putIfAbsent(serverName.toLowerCase(), 0)); - break; + case PLAYERS_CHANNEL -> { + if (in.available() == 0) { + return; + } + + final String server = in.readUTF(); + if (in.available() == 0) { + getPlaceholderAPI().getLogger().log(Level.SEVERE, String.format("[%s] Could not get the player count from server %s.", getName(), server)); + counts.put(server.toLowerCase(), 0); + } else { + counts.put(server.toLowerCase(), in.readInt()); + } + } + case SERVERS_CHANNEL -> + SPLITTER.split(in.readUTF()).forEach(serverName -> counts.putIfAbsent(serverName.toLowerCase(), 0)); } } catch (Exception e) { - e.printStackTrace(); + getPlaceholderAPI().getLogger().log(Level.SEVERE, String.format("[%s] Failed to handle plugin message on channel %s.", getName(), channel), e); } } - private void sendServersChannelMessage() { - sendMessage(SERVERS_CHANNEL, out -> { }); + sendMessage(SERVERS_CHANNEL, _ -> { + }); } private void sendPlayersChannelMessage(final String serverName) { @@ -162,12 +162,11 @@ private void sendPlayersChannelMessage(final String serverName) { } private void sendMessage(final String channel, final Consumer consumer) { - final Player player = Iterables.getFirst(Bukkit.getOnlinePlayers(), null); + final Player player = Iterables.getFirst(new ArrayList<>(Bukkit.getOnlinePlayers()), null); if (player == null) { return; } - //noinspection UnstableApiUsage final ByteArrayDataOutput out = ByteStreams.newDataOutput(); out.writeUTF(channel); @@ -175,5 +174,4 @@ private void sendMessage(final String channel, final Consumer Date: Thu, 7 May 2026 10:53:48 -0400 Subject: [PATCH 2/5] Some POM cleanup --- pom.xml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/pom.xml b/pom.xml index 62d4d33..14b8f2d 100644 --- a/pom.xml +++ b/pom.xml @@ -1,4 +1,4 @@ - 4.0.0 @@ -12,6 +12,7 @@ 25 25 + UTF-8 From 0dcac4c8382338dc13955a14fbafa5c985d0618a Mon Sep 17 00:00:00 2001 From: RootBeer Date: Thu, 7 May 2026 10:59:14 -0400 Subject: [PATCH 3/5] Finalize more cleanups to POM --- pom.xml | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/pom.xml b/pom.xml index 14b8f2d..1261367 100644 --- a/pom.xml +++ b/pom.xml @@ -1,4 +1,6 @@ - + 4.0.0 @@ -14,6 +16,10 @@ 25 UTF-8 + UTF-8 + UTF-8 + + 25 From 64a42fb08e897ab068acaf8b4678676c75f7ecbe Mon Sep 17 00:00:00 2001 From: RootBeer Date: Mon, 11 May 2026 12:58:23 -0400 Subject: [PATCH 4/5] Drop unneeded/duplicate annotation --- .../com/extendedclip/papi/proxyexpansion/ProxyExpansion.java | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/main/java/com/extendedclip/papi/proxyexpansion/ProxyExpansion.java b/src/main/java/com/extendedclip/papi/proxyexpansion/ProxyExpansion.java index d75d0e1..a40b74a 100644 --- a/src/main/java/com/extendedclip/papi/proxyexpansion/ProxyExpansion.java +++ b/src/main/java/com/extendedclip/papi/proxyexpansion/ProxyExpansion.java @@ -12,7 +12,6 @@ import org.bukkit.entity.Player; import org.bukkit.plugin.messaging.PluginMessageListener; import org.jetbrains.annotations.NotNull; -import org.jspecify.annotations.NonNull; import java.io.ByteArrayInputStream; import java.io.DataInputStream; @@ -124,7 +123,7 @@ public void stop() { } @Override - public void onPluginMessageReceived(final @NonNull String channel, final @NonNull Player player, final byte @NonNull [] message) { + public void onPluginMessageReceived(final @NotNull String channel, final @NotNull Player player, final byte @NotNull [] message) { if (!MESSAGE_CHANNEL.equals(channel)) { return; } From 8538bdaf96c34124e66c40bcd45ede385559ed4f Mon Sep 17 00:00:00 2001 From: RootBeer Date: Mon, 11 May 2026 13:05:45 -0400 Subject: [PATCH 5/5] Resupply original branding and re-support Spigot --- README.md | 3 +++ pom.xml | 18 ++++++++-------- .../BungeeExpansion.java} | 21 +++++++++---------- 3 files changed, 22 insertions(+), 20 deletions(-) create mode 100644 README.md rename src/main/java/com/extendedclip/papi/{proxyexpansion/ProxyExpansion.java => bungeeexpansion/BungeeExpansion.java} (91%) diff --git a/README.md b/README.md new file mode 100644 index 0000000..0482ddd --- /dev/null +++ b/README.md @@ -0,0 +1,3 @@ +# BungeeCord-Expansion +Expansion for BungeeCord placeholders +[![Build Status](http://ci.extendedclip.com/buildStatus/icon?job=BungeeCord-Expansion)](http://ci.extendedclip.com/job/BungeeCord-Expansion/) diff --git a/pom.xml b/pom.xml index 1261367..5efd6b9 100644 --- a/pom.xml +++ b/pom.xml @@ -4,12 +4,12 @@ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> 4.0.0 - com.extendedclip.papi.proxyexpansion - proxy-expansion - 1.0 + com.extendedclip.papi.bungeeexpansion + bungee-expansion + 3.0 - Expansion-Proxy - PlaceholderAPI expansion for proxy placeholders. + Expansion-Bungee + PlaceholderAPI expansion for BungeeCord placeholders. 25 @@ -24,8 +24,8 @@ - papermc - https://repo.papermc.io/repository/maven-public/ + spigot-repo + https://hub.spigotmc.org/nexus/content/repositories/snapshots/ @@ -36,8 +36,8 @@ - io.papermc.paper - paper-api + org.spigotmc + spigot-api [26.1.2.build,) provided diff --git a/src/main/java/com/extendedclip/papi/proxyexpansion/ProxyExpansion.java b/src/main/java/com/extendedclip/papi/bungeeexpansion/BungeeExpansion.java similarity index 91% rename from src/main/java/com/extendedclip/papi/proxyexpansion/ProxyExpansion.java rename to src/main/java/com/extendedclip/papi/bungeeexpansion/BungeeExpansion.java index a40b74a..739df98 100644 --- a/src/main/java/com/extendedclip/papi/proxyexpansion/ProxyExpansion.java +++ b/src/main/java/com/extendedclip/papi/bungeeexpansion/BungeeExpansion.java @@ -1,4 +1,4 @@ -package com.extendedclip.papi.proxyexpansion; +package com.extendedclip.papi.bungeeexpansion; import com.google.common.base.Splitter; import com.google.common.collect.Iterables; @@ -11,7 +11,7 @@ import org.bukkit.OfflinePlayer; import org.bukkit.entity.Player; import org.bukkit.plugin.messaging.PluginMessageListener; -import org.jetbrains.annotations.NotNull; +import org.jspecify.annotations.NonNull; import java.io.ByteArrayInputStream; import java.io.DataInputStream; @@ -27,8 +27,7 @@ import java.util.function.Consumer; import java.util.logging.Level; -@SuppressWarnings("unused") -public final class ProxyExpansion extends PlaceholderExpansion implements PluginMessageListener, Taskable, Configurable { +public final class BungeeExpansion extends PlaceholderExpansion implements PluginMessageListener, Taskable, Configurable { private static final String MESSAGE_CHANNEL = "BungeeCord"; private static final String SERVERS_CHANNEL = "GetServers"; @@ -43,21 +42,21 @@ public final class ProxyExpansion extends PlaceholderExpansion implements Plugin private ScheduledExecutorService executor; @Override - @NotNull + @NonNull public String getIdentifier() { - return "proxy"; + return "bungee"; } @Override - @NotNull + @NonNull public String getAuthor() { return "clip"; } @Override - @NotNull + @NonNull public String getVersion() { - return "1.0"; + return "3.0"; } @Override @@ -79,7 +78,7 @@ public String onRequest(final OfflinePlayer player, String identifier) { public void start() { if (executor == null) { executor = Executors.newSingleThreadScheduledExecutor(r -> { - final Thread thread = new Thread(r, "ProxyExpansion-Scheduler"); + final Thread thread = new Thread(r, "BungeeExpansion-Scheduler"); thread.setDaemon(true); return thread; }); @@ -123,7 +122,7 @@ public void stop() { } @Override - public void onPluginMessageReceived(final @NotNull String channel, final @NotNull Player player, final byte @NotNull [] message) { + public void onPluginMessageReceived(final @NonNull String channel, final @NonNull Player player, final byte @NonNull [] message) { if (!MESSAGE_CHANNEL.equals(channel)) { return; }