From 60a3bba165f0cfeb53681fb2d40c85a2a9823e9d Mon Sep 17 00:00:00 2001 From: William Date: Wed, 13 Jul 2022 10:48:34 +0100 Subject: [PATCH] Additional error handling --- .../husksync/api/BaseHuskSyncAPI.java | 6 +++--- .../husksync/listener/EventListener.java | 16 ++++++++------- .../husksync/player/OnlineUser.java | 20 +++++++++++++------ 3 files changed, 26 insertions(+), 16 deletions(-) diff --git a/common/src/main/java/net/william278/husksync/api/BaseHuskSyncAPI.java b/common/src/main/java/net/william278/husksync/api/BaseHuskSyncAPI.java index fe1fc24f..3827e8c6 100644 --- a/common/src/main/java/net/william278/husksync/api/BaseHuskSyncAPI.java +++ b/common/src/main/java/net/william278/husksync/api/BaseHuskSyncAPI.java @@ -72,7 +72,7 @@ public abstract class BaseHuskSyncAPI { public final CompletableFuture> getUserData(@NotNull User user) { return CompletableFuture.supplyAsync(() -> { if (user instanceof OnlineUser) { - return Optional.of(((OnlineUser) user).getUserData().join()); + return ((OnlineUser) user).getUserData(plugin.getLoggingAdapter()).join(); } else { return plugin.getDatabase().getCurrentUserData(user).join().map(UserDataSnapshot::userData); } @@ -103,8 +103,8 @@ public abstract class BaseHuskSyncAPI { * @since 2.0 */ public final CompletableFuture saveUserData(@NotNull OnlineUser user) { - return CompletableFuture.runAsync(() -> user.getUserData().thenAccept(userData -> - plugin.getDatabase().setUserData(user, userData, DataSaveCause.API).join())); + return CompletableFuture.runAsync(() -> user.getUserData(plugin.getLoggingAdapter()).thenAccept(optionalUserData -> optionalUserData.ifPresent( + userData -> plugin.getDatabase().setUserData(user, userData, DataSaveCause.API).join()))); } /** diff --git a/common/src/main/java/net/william278/husksync/listener/EventListener.java b/common/src/main/java/net/william278/husksync/listener/EventListener.java index 3d55888b..5c0f98d6 100644 --- a/common/src/main/java/net/william278/husksync/listener/EventListener.java +++ b/common/src/main/java/net/william278/husksync/listener/EventListener.java @@ -148,9 +148,10 @@ public abstract class EventListener { if (usersAwaitingSync.contains(user.uuid)) { return; } - plugin.getRedisManager().setUserServerSwitch(user).thenRun(() -> user.getUserData().thenAccept( - userData -> plugin.getRedisManager().setUserData(user, userData).thenRun( - () -> plugin.getDatabase().setUserData(user, userData, DataSaveCause.DISCONNECT).join()))); + plugin.getRedisManager().setUserServerSwitch(user).thenRun(() -> user.getUserData(plugin.getLoggingAdapter()).thenAccept( + optionalUserData -> optionalUserData.ifPresent( + userData -> plugin.getRedisManager().setUserData(user, userData).thenRun( + () -> plugin.getDatabase().setUserData(user, userData, DataSaveCause.DISCONNECT).join())))); usersAwaitingSync.remove(user.uuid); } @@ -163,8 +164,8 @@ public abstract class EventListener { if (disabling || !plugin.getSettings().getBooleanValue(Settings.ConfigOption.SYNCHRONIZATION_SAVE_ON_WORLD_SAVE)) { return; } - usersInWorld.forEach(user -> plugin.getDatabase().setUserData(user, user.getUserData().join(), - DataSaveCause.WORLD_SAVE).join()); + usersInWorld.forEach(user -> user.getUserData(plugin.getLoggingAdapter()).join().ifPresent( + userData -> plugin.getDatabase().setUserData(user, userData, DataSaveCause.WORLD_SAVE).join())); } /** @@ -207,8 +208,9 @@ public abstract class EventListener { public final void handlePluginDisable() { disabling = true; - plugin.getOnlineUsers().stream().filter(user -> !usersAwaitingSync.contains(user.uuid)).forEach(user -> - plugin.getDatabase().setUserData(user, user.getUserData().join(), DataSaveCause.SERVER_SHUTDOWN).join()); + plugin.getOnlineUsers().stream().filter(user -> !usersAwaitingSync.contains(user.uuid)).forEach( + user -> user.getUserData(plugin.getLoggingAdapter()).join().ifPresent( + userData -> plugin.getDatabase().setUserData(user, userData, DataSaveCause.SERVER_SHUTDOWN).join())); plugin.getDatabase().close(); plugin.getRedisManager().close(); diff --git a/common/src/main/java/net/william278/husksync/player/OnlineUser.java b/common/src/main/java/net/william278/husksync/player/OnlineUser.java index c9007828..26a63935 100644 --- a/common/src/main/java/net/william278/husksync/player/OnlineUser.java +++ b/common/src/main/java/net/william278/husksync/player/OnlineUser.java @@ -12,6 +12,7 @@ import org.jetbrains.annotations.NotNull; import java.util.ArrayList; import java.util.List; +import java.util.Optional; import java.util.UUID; import java.util.concurrent.CompletableFuture; import java.util.logging.Level; @@ -258,16 +259,23 @@ public abstract class OnlineUser extends User { public abstract void showMenu(@NotNull ItemEditorMenu menu); /** - * Get the player's current {@link UserData} + * Get the player's current {@link UserData} in an {@link Optional} + *

+ * If the user data could not be returned due to an exception, the optional will return empty * - * @return the player's current {@link UserData} + * @param logger The logger to use for handling exceptions + * @return the player's current {@link UserData} in an optional; empty if an exception occurs */ - public final CompletableFuture getUserData() { - return CompletableFuture.supplyAsync( - () -> new UserData(getStatus().join(), getInventory().join(), + public final CompletableFuture> getUserData(@NotNull Logger logger) { + return CompletableFuture.supplyAsync(() -> Optional.of(new UserData(getStatus().join(), getInventory().join(), getEnderChest().join(), getPotionEffects().join(), getAdvancements().join(), getStatistics().join(), getLocation().join(), getPersistentDataContainer().join(), - getMinecraftVersion().toString())); + getMinecraftVersion().toString()))) + .exceptionally(exception -> { + logger.log(Level.SEVERE, "Failed to fetch user data for online player " + username + " (" + exception.getMessage() + ")"); + exception.printStackTrace(); + return Optional.empty(); + }); } }