Skip to content

Commit

Permalink
Mysql: Track local changes and only write to database when different
Browse files Browse the repository at this point in the history
  • Loading branch information
Kale-Ko committed Jul 3, 2024
1 parent 4f6af17 commit 495d4f8
Show file tree
Hide file tree
Showing 2 changed files with 24 additions and 26 deletions.
2 changes: 1 addition & 1 deletion gradle.properties
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ org.gradle.caching=true

java_version=11

project_version=3.9.4
project_version=3.10.0
project_description=An advanced configuration library for Java with support for local files, mysql databases, and more.

bjsl_version=1.10.7
Expand Down
Original file line number Diff line number Diff line change
@@ -1,13 +1,11 @@
package io.github.kale_ko.ejcl.mysql;

import io.github.kale_ko.bjsl.elements.ParsedObject;
import io.github.kale_ko.bjsl.elements.ParsedPrimitive;
import io.github.kale_ko.bjsl.processor.ObjectProcessor;
import io.github.kale_ko.bjsl.processor.reflection.InitializationUtil;
import io.github.kale_ko.ejcl.PathResolver;
import io.github.kale_ko.ejcl.StructuredConfig;
import io.github.kale_ko.ejcl.exception.ConfigClosedException;
import io.github.kale_ko.ejcl.exception.ConfigInitializationException;
import io.github.kale_ko.ejcl.exception.ConfigNotLoadedException;
import io.github.kale_ko.ejcl.exception.mysql.MaximumReconnectsException;
import io.github.kale_ko.ejcl.exception.mysql.MySQLException;
import io.github.kale_ko.ejcl.mysql.driver.MySQL;
Expand All @@ -17,9 +15,7 @@
import java.sql.ResultSet;
import java.sql.SQLException;
import java.time.Instant;
import java.util.ArrayList;
import java.util.List;
import java.util.Properties;
import java.util.*;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;

Expand Down Expand Up @@ -109,6 +105,13 @@ public class StructuredMySQLConfig<T> extends StructuredConfig<T> {
*/
protected long configExpires = -1L;

/**
* A copy of the data that was fetched
*
* @since 3.10.0
*/
protected @Nullable ParsedObject configBackup = null;

/**
* The lock used when saving and loading the config
*
Expand Down Expand Up @@ -329,7 +332,7 @@ public void load(boolean save) throws IOException {
assert this.connection != null;

synchronized (SAVELOAD_LOCK) {
ParsedObject object = this.processor.toElement(this.config).asObject();
ParsedObject object = ParsedObject.create();

try (ResultSet result = MySQL.query(this.connection, "SELECT path,value FROM " + this.table)) {
while (result.next()) {
Expand All @@ -341,6 +344,8 @@ public void load(boolean save) throws IOException {

this.config = this.processor.toObject(object, this.clazz);
this.configExpires = Instant.now().getEpochSecond() + this.cacheLength;

this.configBackup = this.processor.toElement(this.config).asObject();
}

if (save) {
Expand Down Expand Up @@ -374,40 +379,33 @@ public void save() throws IOException {
assert this.connection != null;

synchronized (SAVELOAD_LOCK) {
ParsedObject currentObject = ParsedObject.create();

try (ResultSet result = MySQL.query(this.connection, "SELECT path,value FROM " + this.table)) {
while (result.next()) {
currentObject.set(result.getString("path"), ParsedPrimitive.fromString(result.getString("value")));
}
} catch (SQLException e) {
throw new IOException(e);
}

ParsedObject object = this.processor.toElement(this.config).asObject();
List<String> keys = PathResolver.getKeys(object, false);
Set<String> keys = PathResolver.getKeys(object, false);
Set<String> oldKeys = PathResolver.getKeys(this.configBackup, false);

Set<String> toDelete = new HashSet<>(oldKeys);
toDelete.removeAll(keys);

List<String> queryArgs = new ArrayList<>();
for (String key : keys) {
Object value = PathResolver.resolve(object, key, false);
Object oldValue = PathResolver.resolve(this.configBackup, key, false);

if (!currentObject.has(key) || !currentObject.get(key).asPrimitive().asString().equals(value != null ? value.toString() : "null")) {
if (!((value == null && oldValue == null) || (value != null && (value == oldValue || value.equals(oldValue))))) {
queryArgs.add(key);
queryArgs.add(value != null ? value.toString() : "null");
}

if (currentObject.has(key)) {
currentObject.remove(key);
}
}

this.configBackup = object;

try {
if (!queryArgs.isEmpty()) {
MySQL.executeBatch(this.connection, "REPLACE INTO " + this.table + " (path, value) VALUES (?, ?);", 2, queryArgs);
}

if (!currentObject.getKeys().isEmpty()) {
MySQL.executeBatch(this.connection, "DELETE FROM " + this.table + " WHERE path=?;", 1, currentObject.getKeys());
if (!toDelete.isEmpty()) {
MySQL.executeBatch(this.connection, "DELETE FROM " + this.table + " WHERE path=?;", 1, List.copyOf(toDelete));
}
} catch (SQLException e) {
throw new IOException(e);
Expand Down

0 comments on commit 495d4f8

Please sign in to comment.