Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view

Large diffs are not rendered by default.

Original file line number Diff line number Diff line change
Expand Up @@ -11,16 +11,27 @@
import com.bencodez.advancedcore.api.time.TimeType;
import com.bencodez.advancedcore.api.time.events.DateChangedEvent;

/**
* Handles automatic backups of plugin data.
*/
public class BackupHandle implements Listener {
private static BackupHandle instance = new BackupHandle();

/**
* Gets the singleton instance.
*
* @return the backup handler instance
*/
public static BackupHandle getInstance() {
return instance;
}

private BackupHandle() {
}

/**
* Checks for and deletes old backups older than 5 days.
*/
public void checkOldBackups() {
for (File file : new File(AdvancedCorePlugin.getInstance().getDataFolder(), "Backups").listFiles()) {
long lastModified = file.lastModified();
Expand All @@ -31,6 +42,11 @@ public void checkOldBackups() {
}
}

/**
* Handles date change events to create daily backups.
*
* @param e the date changed event
*/
@EventHandler
public void onPostDateChange(DateChangedEvent e) {
if (!e.getTimeType().equals(TimeType.DAY) || !AdvancedCorePlugin.getInstance().getOptions().isCreateBackups()) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,9 @@
import com.bencodez.advancedcore.api.user.UserManager;
import com.bencodez.advancedcore.api.user.UserStartup;

/**
* Resolves Bedrock player names and detects Bedrock players.
*/
public final class BedrockNameResolver {

private final BedrockDetect bedrockDetect;
Expand All @@ -25,6 +28,11 @@ public final class BedrockNameResolver {
private final Map<String, Boolean> cache = new ConcurrentHashMap<>();
private final Map<String, String> ciIndex = new ConcurrentHashMap<>();

/**
* Creates a new Bedrock name resolver.
*
* @param plugin the plugin instance
*/
public BedrockNameResolver(AdvancedCorePlugin plugin) {
this.plugin = plugin;
this.bedrockDetect = new BedrockDetect(plugin::debug);
Expand Down Expand Up @@ -56,10 +64,23 @@ public void onFinish() {
});
}

/**
* Checks if a player is a Bedrock player by name.
*
* @param name the player name
* @return true if the player is a Bedrock player
*/
public boolean isBedrock(String name) {
return isBedrockName(name);
}

/**
* Checks if a player is a Bedrock player by UUID and name.
*
* @param uuid the player UUID
* @param name the player name
* @return true if the player is a Bedrock player
*/
public boolean isBedrock(UUID uuid, String name) {
// 1) UUID is authoritative if present
if (uuid != null) {
Expand Down Expand Up @@ -138,6 +159,11 @@ public boolean isBedrock(UUID uuid, String name) {

// ------------ EXISTING METHODS (unchanged behavior) ------------

/**
* Learns whether a user is a Bedrock player.
*
* @param user the user to learn from
*/
public void learn(AdvancedCoreUser user) {
if (user == null)
return;
Expand All @@ -147,6 +173,11 @@ public void learn(AdvancedCoreUser user) {
putLearned(name, user.isBedrockUser());
}

/**
* Learns whether a player is a Bedrock player.
*
* @param player the player to learn from
*/
public void learn(Player player) {
if (player == null)
return;
Expand All @@ -165,9 +196,12 @@ public void learn(Player player) {

/**
* Detect whether a name corresponds to a Bedrock player.
*
*
* IMPORTANT: This method does NOT add prefixes. It only returns a boolean. Use
* {@link #resolve(String)} if you want canonical (possibly prefixed) names.
*
* @param name the player name
* @return true if the player is a Bedrock player
*/
public boolean isBedrockName(String name) {
if (name == null || name.isEmpty())
Expand Down Expand Up @@ -216,6 +250,12 @@ public boolean isBedrockName(String name) {
return bedrockPrefix != null && !bedrockPrefix.isEmpty() && name.startsWith(bedrockPrefix);
}

/**
* Resolve a name to its canonical form and determine if it's a Bedrock player.
*
* @param incomingName the player name to resolve
* @return the result containing the canonical name and Bedrock status
*/
public Result resolve(String incomingName) {
if (incomingName == null || incomingName.isEmpty())
return new Result(incomingName, false, "empty-name");
Expand Down Expand Up @@ -292,10 +332,19 @@ public Result resolve(String incomingName) {
return new Result(incomingName, false, "unknown-default-java");
}

/**
* Get the prefixed name if the player is a Bedrock player.
*
* @param name the player name
* @return the prefixed name if Bedrock, otherwise the original name
*/
public String getPrefixedIfBedrock(String name) {
return addPrefixIfNeeded(name, isBedrockName(name));
}

/**
* Clear the cache and case-insensitive index.
*/
public void clearCache() {
cache.clear();
ciIndex.clear();
Expand Down Expand Up @@ -436,11 +485,24 @@ private Player findOnlineByNameOrStripped(String name) {
return (javaCandidate != null) ? javaCandidate : bedrockCandidate;
}

/**
* Result of name resolution containing the final name, Bedrock status, and rationale.
*/
public static final class Result {
/** The final resolved name. */
public final String finalName;
/** Whether the player is a Bedrock player. */
public final boolean isBedrock;
/** The rationale for the resolution decision. */
public final String rationale;

/**
* Instantiates a new result.
*
* @param finalName the final resolved name
* @param isBedrock whether the player is Bedrock
* @param rationale the rationale for the decision
*/
public Result(String finalName, boolean isBedrock, String rationale) {
this.finalName = finalName;
this.isBedrock = isBedrock;
Expand All @@ -451,6 +513,9 @@ public Result(String finalName, boolean isBedrock, String rationale) {
// ====================== Embedded BedrockDetect with DEBUG
// ======================

/**
* Bedrock detection using Floodgate and Geyser APIs.
*/
public static class BedrockDetect {
private volatile boolean floodgateAvailable = false;
private volatile boolean geyserAvailable = false;
Expand All @@ -464,16 +529,27 @@ public static class BedrockDetect {

private final Consumer<String> debug;

/**
* Instantiates a new Bedrock detector with no debug output.
*/
public BedrockDetect() {
this(s -> {
});
}

/**
* Instantiates a new Bedrock detector with debug output.
*
* @param debug the debug consumer
*/
public BedrockDetect(Consumer<String> debug) {
this.debug = (debug != null) ? debug : (s -> {
});
}

/**
* Load Floodgate and Geyser APIs.
*/
public void load() {
loadFloodgate();
loadGeyser();
Expand Down Expand Up @@ -514,6 +590,12 @@ private void loadGeyser() {
}
}

/**
* Check if a player is a Bedrock player by UUID.
*
* @param uuid the player UUID
* @return true if the player is a Bedrock player
*/
public boolean isBedrock(UUID uuid) {
if (uuid == null)
return false;
Expand Down Expand Up @@ -543,6 +625,12 @@ public boolean isBedrock(UUID uuid) {
return false;
}

/**
* Get the Floodgate player object.
*
* @param uuid the player UUID
* @return the Floodgate player object or null
*/
public Object getFloodgatePlayer(UUID uuid) {
if (!floodgateAvailable || fgGetPlayer == null || uuid == null)
return null;
Expand All @@ -554,10 +642,20 @@ public Object getFloodgatePlayer(UUID uuid) {
}
}

/**
* Check if Floodgate API is available.
*
* @return true if Floodgate is available
*/
public boolean isFloodgateAvailable() {
return floodgateAvailable;
}

/**
* Check if Geyser API is available.
*
* @return true if Geyser is available
*/
public boolean isGeyserAvailable() {
return geyserAvailable;
}
Expand Down
Loading