diff --git a/src/main/java/io/papermc/lib/PaperLib.java b/src/main/java/io/papermc/lib/PaperLib.java index 768f1fc..308dbc9 100644 --- a/src/main/java/io/papermc/lib/PaperLib.java +++ b/src/main/java/io/papermc/lib/PaperLib.java @@ -1,12 +1,15 @@ package io.papermc.lib; -import io.papermc.lib.environments.CraftBukkitEnvironment; -import io.papermc.lib.environments.Environment; -import io.papermc.lib.environments.PaperEnvironment; -import io.papermc.lib.environments.SpigotEnvironment; -import io.papermc.lib.features.blockstatesnapshot.BlockStateSnapshotResult; +import java.util.concurrent.CompletableFuture; +import java.util.logging.Level; +import java.util.logging.Logger; + +import javax.annotation.Nonnull; +import javax.annotation.Nullable; + import org.bukkit.Chunk; import org.bukkit.Location; +import org.bukkit.OfflinePlayer; import org.bukkit.World; import org.bukkit.block.Block; import org.bukkit.entity.Entity; @@ -14,10 +17,11 @@ import org.bukkit.event.player.PlayerTeleportEvent.TeleportCause; import org.bukkit.plugin.Plugin; -import javax.annotation.Nonnull; -import java.util.concurrent.CompletableFuture; -import java.util.logging.Level; -import java.util.logging.Logger; +import io.papermc.lib.environments.CraftBukkitEnvironment; +import io.papermc.lib.environments.Environment; +import io.papermc.lib.environments.PaperEnvironment; +import io.papermc.lib.environments.SpigotEnvironment; +import io.papermc.lib.features.blockstatesnapshot.BlockStateSnapshotResult; /** * Utility methods that assist plugin developers accessing Paper features. @@ -201,6 +205,18 @@ public static BlockStateSnapshotResult getBlockState(@Nonnull Block block, boole public static CompletableFuture getBedSpawnLocationAsync(@Nonnull Player player, boolean isUrgent) { return ENVIRONMENT.getBedSpawnLocationAsync(player, isUrgent); } + + /** + * Gets an OfflinePlayer by the given name. If the Player is not cached, an optional web request + * can be made to look up the UUID of that player. Web requests will block the current Thread though. + * @param name The name of this OfflinePlayer. + * @param makeWebRequest Whether or not a web request for UUID lookups should be made. + * @return OfflinePlayer by the given name or null if the player is not cached and no web request was made. + */ + @Nullable + public static OfflinePlayer getOfflinePlayerIfCached(@Nonnull String name, boolean makeWebRequest) { + return ENVIRONMENT.getOfflinePlayerIfCached(name, makeWebRequest); + } /** * Detects if the current MC version is at least the following version. diff --git a/src/main/java/io/papermc/lib/environments/Environment.java b/src/main/java/io/papermc/lib/environments/Environment.java index dc586f9..7016a6b 100644 --- a/src/main/java/io/papermc/lib/environments/Environment.java +++ b/src/main/java/io/papermc/lib/environments/Environment.java @@ -13,21 +13,27 @@ import io.papermc.lib.features.chunkisgenerated.ChunkIsGenerated; import io.papermc.lib.features.chunkisgenerated.ChunkIsGeneratedApiExists; import io.papermc.lib.features.chunkisgenerated.ChunkIsGeneratedUnknown; +import io.papermc.lib.features.offlineplayers.GetOfflinePlayer; +import io.papermc.lib.features.offlineplayers.GetOfflinePlayerSpigot; + import org.bukkit.Bukkit; import org.bukkit.Chunk; import org.bukkit.Location; +import org.bukkit.OfflinePlayer; import org.bukkit.World; import org.bukkit.block.Block; import org.bukkit.entity.Entity; import org.bukkit.entity.Player; import org.bukkit.event.player.PlayerTeleportEvent.TeleportCause; -import javax.annotation.Nonnull; import java.util.concurrent.CompletableFuture; import java.util.regex.MatchResult; import java.util.regex.Matcher; import java.util.regex.Pattern; +import javax.annotation.Nonnull; +import javax.annotation.Nullable; + @SuppressWarnings("WeakerAccess") public abstract class Environment { @@ -40,6 +46,7 @@ public abstract class Environment { protected ChunkIsGenerated isGeneratedHandler = new ChunkIsGeneratedUnknown(); protected BlockStateSnapshot blockStateSnapshotHandler; protected BedSpawnLocation bedSpawnLocationHandler = new BedSpawnLocationSync(); + protected GetOfflinePlayer getOfflinePlayerHandler = new GetOfflinePlayerSpigot(); public Environment() { Pattern versionPattern = Pattern.compile("\\(MC: (\\d)\\.(\\d+)\\.?(\\d+?)?(?: Pre-Release )?(\\d)?\\)"); @@ -112,6 +119,11 @@ public BlockStateSnapshotResult getBlockState(Block block, boolean useSnapshot) public CompletableFuture getBedSpawnLocationAsync(Player player, boolean isUrgent) { return bedSpawnLocationHandler.getBedSpawnLocationAsync(player, isUrgent); } + + @Nullable + public OfflinePlayer getOfflinePlayerIfCached(@Nonnull String name, boolean makeWebRequest) { + return getOfflinePlayerHandler.getOfflinePlayerIfCached(name, makeWebRequest); + } public boolean isVersion(int minor) { return isVersion(minor, 0); diff --git a/src/main/java/io/papermc/lib/environments/PaperEnvironment.java b/src/main/java/io/papermc/lib/environments/PaperEnvironment.java index 04859a6..89a1203 100644 --- a/src/main/java/io/papermc/lib/environments/PaperEnvironment.java +++ b/src/main/java/io/papermc/lib/environments/PaperEnvironment.java @@ -8,7 +8,10 @@ import io.papermc.lib.features.bedspawnlocation.BedSpawnLocationPaper; import io.papermc.lib.features.blockstatesnapshot.BlockStateSnapshotOptionalSnapshots; import io.papermc.lib.features.chunkisgenerated.ChunkIsGeneratedApiExists; +import io.papermc.lib.features.offlineplayers.GetOfflinePlayerPaper; + import org.bukkit.Location; +import org.bukkit.Server; import org.bukkit.World; import org.bukkit.entity.HumanEntity; @@ -38,6 +41,13 @@ public PaperEnvironment() { bedSpawnLocationHandler = new BedSpawnLocationPaper(); } catch (NoSuchMethodException ignored) {} } + if (isVersion(16, 4)) { + try { + // Check for the new "getOfflinePlayerIfCached" method which was added in Paper API 1.16.4+ + Server.class.getDeclaredMethod("getOfflinePlayerIfCached", String.class); + getOfflinePlayerHandler = new GetOfflinePlayerPaper(); + } catch(NoSuchMethodException ignored) {} + } } @Override diff --git a/src/main/java/io/papermc/lib/features/offlineplayers/GetOfflinePlayer.java b/src/main/java/io/papermc/lib/features/offlineplayers/GetOfflinePlayer.java new file mode 100644 index 0000000..fe5fc38 --- /dev/null +++ b/src/main/java/io/papermc/lib/features/offlineplayers/GetOfflinePlayer.java @@ -0,0 +1,11 @@ +package io.papermc.lib.features.offlineplayers; + +import javax.annotation.Nonnull; +import javax.annotation.Nullable; + +import org.bukkit.OfflinePlayer; + +public interface GetOfflinePlayer { + @Nullable + OfflinePlayer getOfflinePlayerIfCached(@Nonnull String name, boolean makeWebRequest); +} diff --git a/src/main/java/io/papermc/lib/features/offlineplayers/GetOfflinePlayerPaper.java b/src/main/java/io/papermc/lib/features/offlineplayers/GetOfflinePlayerPaper.java new file mode 100644 index 0000000..44624a9 --- /dev/null +++ b/src/main/java/io/papermc/lib/features/offlineplayers/GetOfflinePlayerPaper.java @@ -0,0 +1,19 @@ +package io.papermc.lib.features.offlineplayers; + +import javax.annotation.Nonnull; +import javax.annotation.Nullable; + +import org.bukkit.Bukkit; +import org.bukkit.OfflinePlayer; + +public class GetOfflinePlayerPaper implements GetOfflinePlayer { + @Override + @Nullable + public OfflinePlayer getOfflinePlayerIfCached(@Nonnull String name, boolean makeWebRequest) { + if (makeWebRequest) { + return Bukkit.getOfflinePlayer(name); + } else { + return Bukkit.getOfflinePlayerIfCached(name); + } + } +} diff --git a/src/main/java/io/papermc/lib/features/offlineplayers/GetOfflinePlayerSpigot.java b/src/main/java/io/papermc/lib/features/offlineplayers/GetOfflinePlayerSpigot.java new file mode 100644 index 0000000..22a6b4d --- /dev/null +++ b/src/main/java/io/papermc/lib/features/offlineplayers/GetOfflinePlayerSpigot.java @@ -0,0 +1,15 @@ +package io.papermc.lib.features.offlineplayers; + +import javax.annotation.Nonnull; +import javax.annotation.Nullable; + +import org.bukkit.Bukkit; +import org.bukkit.OfflinePlayer; + +public class GetOfflinePlayerSpigot implements GetOfflinePlayer { + @Override + @Nullable + public OfflinePlayer getOfflinePlayerIfCached(@Nonnull String name, boolean makeWebRequest) { + return Bukkit.getOfflinePlayer(name); + } +}