From e38c5977ec72a3bd11fe029bbd92f598e50045fd Mon Sep 17 00:00:00 2001 From: xHyroM Date: Wed, 30 Aug 2023 18:21:56 +0200 Subject: [PATCH] fix: remove record if balance is < 0 before, there was easy duplication bug --- .../provider/sql/SqlStorageProvider.java | 96 +++++++++++-------- .../lighteco/common/task/UserSaveTask.java | 2 + .../sponge/SpongeLightEcoBootstrap.java | 40 +++++++- .../lighteco/sponge/SpongeLightEcoPlugin.java | 4 +- 4 files changed, 101 insertions(+), 41 deletions(-) diff --git a/common/src/main/java/dev/xhyrom/lighteco/common/storage/provider/sql/SqlStorageProvider.java b/common/src/main/java/dev/xhyrom/lighteco/common/storage/provider/sql/SqlStorageProvider.java index 42d11d5..aa73b80 100644 --- a/common/src/main/java/dev/xhyrom/lighteco/common/storage/provider/sql/SqlStorageProvider.java +++ b/common/src/main/java/dev/xhyrom/lighteco/common/storage/provider/sql/SqlStorageProvider.java @@ -25,6 +25,8 @@ public class SqlStorageProvider implements StorageProvider { private static String LOAD_WHOLE_USER; private static final String GET_TOP_X_USERS_LOCAL = "SELECT uuid, balance FROM {prefix}_{context}_users WHERE currency_identifier = ? ORDER BY balance DESC LIMIT ?;"; private static final String GET_TOP_X_USERS_GLOBAL = "SELECT uuid, balance FROM {prefix}_users WHERE currency_identifier = ? ORDER BY balance DESC LIMIT ?;"; + private static final String DELETE_GLOBAL_USER_IF_BALANCE = "DELETE FROM {prefix}_{context}_users WHERE uuid = ? AND currency_identifier = ? AND balance = ?;"; + private static final String DELETE_LOCAL_USER_IF_BALANCE = "DELETE FROM {prefix}_{context}_users WHERE uuid = ? AND currency_identifier = ? AND balance = ?;"; private final LightEcoPlugin plugin; private final ConnectionFactory connectionFactory; @@ -110,13 +112,8 @@ public class SqlStorageProvider implements StorageProvider { String uniqueIdString = user.getUniqueId().toString(); try (Connection c = this.connectionFactory.getConnection()) { - try (PreparedStatement psGlobal = c.prepareStatement(this.statementProcessor.apply(SAVE_USER_GLOBAL_CURRENCY)); - PreparedStatement psLocal = c.prepareStatement(this.statementProcessor.apply(SAVE_USER_LOCAL_CURRENCY))) { - - saveBalances(psGlobal, psLocal, user, uniqueIdString); - - psGlobal.executeBatch(); - psLocal.executeBatch(); + try { + saveBalances(c, user, uniqueIdString); } catch (SQLException e) { throw new SQLException("Failed to save user " + user.getUniqueId(), e); } @@ -130,19 +127,10 @@ public class SqlStorageProvider implements StorageProvider { try { c.setAutoCommit(false); - try (PreparedStatement psGlobal = c.prepareStatement(this.statementProcessor.apply(SAVE_USER_GLOBAL_CURRENCY)); - PreparedStatement psLocal = c.prepareStatement(this.statementProcessor.apply(SAVE_USER_LOCAL_CURRENCY))) { + for (User user : users) { + String uniqueIdString = user.getUniqueId().toString(); - for (User user : users) { - String uniqueIdString = user.getUniqueId().toString(); - - saveBalances(psGlobal, psLocal, user, uniqueIdString); - } - - psGlobal.executeBatch(); - psLocal.executeBatch(); - } catch (SQLException e) { - throw new SQLException("Failed to save users", e); + saveBalances(c, user, uniqueIdString); } c.commit(); @@ -185,32 +173,64 @@ public class SqlStorageProvider implements StorageProvider { } } - private void saveBalances(PreparedStatement psGlobal, PreparedStatement psLocal, User user, String uniqueIdString) throws SQLException { - for (Currency currency : this.plugin.getCurrencyManager().getRegisteredCurrencies()) { - BigDecimal balance = user.getBalance(currency.getProxy()); + private void saveBalances(Connection c, User user, String uniqueIdString) throws SQLException { + try (PreparedStatement psGlobal = c.prepareStatement(this.statementProcessor.apply(SAVE_USER_GLOBAL_CURRENCY)); + PreparedStatement psLocal = c.prepareStatement(this.statementProcessor.apply(SAVE_USER_LOCAL_CURRENCY)); + PreparedStatement psDeleteGlobal = c.prepareStatement(this.statementProcessor.apply(DELETE_GLOBAL_USER_IF_BALANCE)); + PreparedStatement psDeleteLocal = c.prepareStatement(this.statementProcessor.apply(DELETE_LOCAL_USER_IF_BALANCE))) { - if (balance.compareTo(BigDecimal.ZERO) == 0) continue; + for (Currency currency : this.plugin.getCurrencyManager().getRegisteredCurrencies()) { + BigDecimal balance = user.getBalance(currency.getProxy()); - switch (currency.getType()) { - case GLOBAL -> { - psGlobal.setString(1, uniqueIdString); - psGlobal.setString(2, currency.getIdentifier()); - psGlobal.setBigDecimal(3, balance); - if (SqlStatements.mustDuplicateParameters(this.connectionFactory.getImplementationName())) - psGlobal.setBigDecimal(4, balance); + if (balance.compareTo(BigDecimal.ZERO) == 0) { + switch (currency.getType()) { + case GLOBAL -> { + psDeleteGlobal.setString(1, uniqueIdString); + psDeleteGlobal.setString(2, currency.getIdentifier()); + psDeleteGlobal.setBigDecimal(3, balance); - psGlobal.addBatch(); + psDeleteGlobal.addBatch(); + } + case LOCAL -> { + psDeleteLocal.setString(1, uniqueIdString); + psDeleteLocal.setString(2, currency.getIdentifier()); + psDeleteLocal.setBigDecimal(3, balance); + + psDeleteLocal.addBatch(); + } + } + + continue; } - case LOCAL -> { - psLocal.setString(1, uniqueIdString); - psLocal.setString(2, currency.getIdentifier()); - psLocal.setBigDecimal(3, balance); - if (SqlStatements.mustDuplicateParameters(this.connectionFactory.getImplementationName())) - psLocal.setBigDecimal(4, balance); - psLocal.addBatch(); + switch (currency.getType()) { + case GLOBAL -> { + psGlobal.setString(1, uniqueIdString); + psGlobal.setString(2, currency.getIdentifier()); + psGlobal.setBigDecimal(3, balance); + if (SqlStatements.mustDuplicateParameters(this.connectionFactory.getImplementationName())) + psGlobal.setBigDecimal(4, balance); + + psGlobal.addBatch(); + } + case LOCAL -> { + psLocal.setString(1, uniqueIdString); + psLocal.setString(2, currency.getIdentifier()); + psLocal.setBigDecimal(3, balance); + if (SqlStatements.mustDuplicateParameters(this.connectionFactory.getImplementationName())) + psLocal.setBigDecimal(4, balance); + + psLocal.addBatch(); + } } } + + psGlobal.executeBatch(); + psLocal.executeBatch(); + psDeleteGlobal.executeBatch(); + psDeleteLocal.executeBatch(); + } catch (SQLException e) { + throw new SQLException("Failed to save user " + user.getUniqueId(), e); } } } diff --git a/common/src/main/java/dev/xhyrom/lighteco/common/task/UserSaveTask.java b/common/src/main/java/dev/xhyrom/lighteco/common/task/UserSaveTask.java index d26991f..59f29d4 100644 --- a/common/src/main/java/dev/xhyrom/lighteco/common/task/UserSaveTask.java +++ b/common/src/main/java/dev/xhyrom/lighteco/common/task/UserSaveTask.java @@ -21,6 +21,8 @@ public class UserSaveTask implements Runnable { .filter(User::isDirty) .toArray(User[]::new); + System.out.println("Saving " + users.length + " users"); + if (users.length == 0) { return; } diff --git a/sponge-8/src/main/java/dev/xhyrom/lighteco/sponge/SpongeLightEcoBootstrap.java b/sponge-8/src/main/java/dev/xhyrom/lighteco/sponge/SpongeLightEcoBootstrap.java index 87795bb..9fe84f7 100644 --- a/sponge-8/src/main/java/dev/xhyrom/lighteco/sponge/SpongeLightEcoBootstrap.java +++ b/sponge-8/src/main/java/dev/xhyrom/lighteco/sponge/SpongeLightEcoBootstrap.java @@ -1,12 +1,20 @@ package dev.xhyrom.lighteco.sponge; import com.google.inject.Inject; +import dev.xhyrom.lighteco.common.plugin.bootstrap.LightEcoBootstrap; import dev.xhyrom.lighteco.common.plugin.bootstrap.LoaderBootstrap; +import dev.xhyrom.lighteco.common.plugin.logger.PluginLogger; +import dev.xhyrom.lighteco.common.plugin.scheduler.SchedulerAdapter; import org.apache.logging.log4j.Logger; import org.spongepowered.plugin.builtin.jvm.Plugin; +import java.io.InputStream; +import java.nio.file.Path; +import java.util.List; +import java.util.UUID; + @Plugin("lighteco-sponge") -public class SpongeLightEcoBootstrap implements LoaderBootstrap { +public class SpongeLightEcoBootstrap implements LightEcoBootstrap, LoaderBootstrap { private final SpongeLightEcoPlugin plugin; @Inject @@ -30,4 +38,34 @@ public class SpongeLightEcoBootstrap implements LoaderBootstrap { public void onDisable() { this.plugin.disable(); } + + @Override + public Object getLoader() { + return null; + } + + @Override + public PluginLogger getLogger() { + return null; + } + + @Override + public SchedulerAdapter getScheduler() { + return null; + } + + @Override + public Path getDataDirectory() { + return null; + } + + @Override + public List getOnlinePlayers() { + return null; + } + + @Override + public InputStream getResourceStream(String filename) { + return null; + } } diff --git a/sponge-8/src/main/java/dev/xhyrom/lighteco/sponge/SpongeLightEcoPlugin.java b/sponge-8/src/main/java/dev/xhyrom/lighteco/sponge/SpongeLightEcoPlugin.java index 4aefad7..ae1fef7 100644 --- a/sponge-8/src/main/java/dev/xhyrom/lighteco/sponge/SpongeLightEcoPlugin.java +++ b/sponge-8/src/main/java/dev/xhyrom/lighteco/sponge/SpongeLightEcoPlugin.java @@ -1,9 +1,9 @@ package dev.xhyrom.lighteco.sponge; import dev.xhyrom.lighteco.api.LightEco; -import dev.xhyrom.lighteco.api.manager.CommandManager; import dev.xhyrom.lighteco.api.manager.ContextManager; import dev.xhyrom.lighteco.api.platform.Platform; +import dev.xhyrom.lighteco.common.manager.command.CommandManager; import dev.xhyrom.lighteco.common.manager.currency.StandardCurrencyManager; import dev.xhyrom.lighteco.common.manager.user.StandardUserManager; import dev.xhyrom.lighteco.common.plugin.AbstractLightEcoPlugin; @@ -11,8 +11,8 @@ import lombok.Getter; import org.checkerframework.checker.nullness.qual.NonNull; import org.spongepowered.api.entity.living.player.Player; +@Getter public class SpongeLightEcoPlugin extends AbstractLightEcoPlugin { - @Getter private final SpongeLightEcoBootstrap bootstrap; @Getter