Add support for split storage
This commit is contained in:
parent
5c19dd8b15
commit
3fd62a80e2
@ -47,6 +47,18 @@ log-notify: true
|
|||||||
# Fill out connection info below if you're using MySQL or MongoDB
|
# Fill out connection info below if you're using MySQL or MongoDB
|
||||||
storage-method: h2
|
storage-method: h2
|
||||||
|
|
||||||
|
# This block enables support for split datastores.
|
||||||
|
# Only touch this if you're sure that you know what you're doing.
|
||||||
|
# I (the author) do not endorse nor recommend the use of this feature.
|
||||||
|
split-storage:
|
||||||
|
enabled: false
|
||||||
|
methods:
|
||||||
|
user: h2
|
||||||
|
group: h2
|
||||||
|
track: h2
|
||||||
|
uuid: h2
|
||||||
|
log: h2
|
||||||
|
|
||||||
data:
|
data:
|
||||||
address: localhost:3306
|
address: localhost:3306
|
||||||
database: minecraft
|
database: minecraft
|
||||||
|
@ -47,6 +47,18 @@ log-notify: true
|
|||||||
# Fill out connection info below if you're using MySQL or MongoDB
|
# Fill out connection info below if you're using MySQL or MongoDB
|
||||||
storage-method: h2
|
storage-method: h2
|
||||||
|
|
||||||
|
# This block enables support for split datastores.
|
||||||
|
# Only touch this if you're sure that you know what you're doing.
|
||||||
|
# I (the author) do not endorse nor recommend the use of this feature.
|
||||||
|
split-storage:
|
||||||
|
enabled: false
|
||||||
|
methods:
|
||||||
|
user: h2
|
||||||
|
group: h2
|
||||||
|
track: h2
|
||||||
|
uuid: h2
|
||||||
|
log: h2
|
||||||
|
|
||||||
data:
|
data:
|
||||||
address: localhost:3306
|
address: localhost:3306
|
||||||
database: minecraft
|
database: minecraft
|
||||||
|
@ -28,6 +28,9 @@ import me.lucko.luckperms.LuckPermsPlugin;
|
|||||||
import me.lucko.luckperms.constants.Patterns;
|
import me.lucko.luckperms.constants.Patterns;
|
||||||
import me.lucko.luckperms.storage.DatastoreConfiguration;
|
import me.lucko.luckperms.storage.DatastoreConfiguration;
|
||||||
|
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
public abstract class LPConfiguration<T extends LuckPermsPlugin> {
|
public abstract class LPConfiguration<T extends LuckPermsPlugin> {
|
||||||
|
|
||||||
@Getter(AccessLevel.PROTECTED)
|
@Getter(AccessLevel.PROTECTED)
|
||||||
@ -118,4 +121,19 @@ public abstract class LPConfiguration<T extends LuckPermsPlugin> {
|
|||||||
public String getStorageMethod() {
|
public String getStorageMethod() {
|
||||||
return getString("storage-method", defaultStorage);
|
return getString("storage-method", defaultStorage);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public boolean getSplitStorage() {
|
||||||
|
return getBoolean("split-storage.enabled", false);
|
||||||
|
}
|
||||||
|
|
||||||
|
public Map<String, String> getSplitStorageOptions() {
|
||||||
|
Map<String, String> map = new HashMap<>();
|
||||||
|
map.put("user", getString("split-storage.methods.user", defaultStorage));
|
||||||
|
map.put("group", getString("split-storage.methods.group", defaultStorage));
|
||||||
|
map.put("track", getString("split-storage.methods.track", defaultStorage));
|
||||||
|
map.put("uuid", getString("split-storage.methods.uuid", defaultStorage));
|
||||||
|
map.put("log", getString("split-storage.methods.log", defaultStorage));
|
||||||
|
|
||||||
|
return map;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -0,0 +1,136 @@
|
|||||||
|
package me.lucko.luckperms.storage;
|
||||||
|
|
||||||
|
import com.google.common.collect.ImmutableMap;
|
||||||
|
import me.lucko.luckperms.LuckPermsPlugin;
|
||||||
|
import me.lucko.luckperms.api.LogEntry;
|
||||||
|
import me.lucko.luckperms.data.Log;
|
||||||
|
import me.lucko.luckperms.groups.Group;
|
||||||
|
import me.lucko.luckperms.tracks.Track;
|
||||||
|
import me.lucko.luckperms.users.User;
|
||||||
|
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.Set;
|
||||||
|
import java.util.UUID;
|
||||||
|
|
||||||
|
public class SplitDatastore extends Datastore {
|
||||||
|
private final Map<String, Datastore> backing;
|
||||||
|
private final Map<String, String> types;
|
||||||
|
|
||||||
|
protected SplitDatastore(LuckPermsPlugin plugin, Map<String, Datastore> backing, Map<String, String> types) {
|
||||||
|
super(plugin, "Split Storage");
|
||||||
|
this.backing = ImmutableMap.copyOf(backing);
|
||||||
|
this.types = ImmutableMap.copyOf(types);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void init() {
|
||||||
|
backing.values().forEach(Datastore::init);
|
||||||
|
for (Datastore ds : backing.values()) {
|
||||||
|
if (!ds.isAcceptingLogins()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
setAcceptingLogins(true);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void shutdown() {
|
||||||
|
backing.values().forEach(Datastore::shutdown);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean logAction(LogEntry entry) {
|
||||||
|
return backing.get(types.get("log")).logAction(entry);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Log getLog() {
|
||||||
|
return backing.get(types.get("log")).getLog();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean loadUser(UUID uuid, String username) {
|
||||||
|
return backing.get(types.get("user")).loadUser(uuid, username);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean saveUser(User user) {
|
||||||
|
return backing.get(types.get("user")).saveUser(user);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean cleanupUsers() {
|
||||||
|
return backing.get(types.get("user")).cleanupUsers();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Set<UUID> getUniqueUsers() {
|
||||||
|
return backing.get(types.get("user")).getUniqueUsers();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean createAndLoadGroup(String name) {
|
||||||
|
return backing.get(types.get("group")).createAndLoadGroup(name);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean loadGroup(String name) {
|
||||||
|
return backing.get(types.get("group")).loadGroup(name);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean loadAllGroups() {
|
||||||
|
return backing.get(types.get("group")).loadAllGroups();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean saveGroup(Group group) {
|
||||||
|
return backing.get(types.get("group")).saveGroup(group);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean deleteGroup(Group group) {
|
||||||
|
return backing.get(types.get("group")).deleteGroup(group);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean createAndLoadTrack(String name) {
|
||||||
|
return backing.get(types.get("track")).createAndLoadTrack(name);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean loadTrack(String name) {
|
||||||
|
return backing.get(types.get("track")).loadTrack(name);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean loadAllTracks() {
|
||||||
|
return backing.get(types.get("track")).loadAllTracks();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean saveTrack(Track track) {
|
||||||
|
return backing.get(types.get("track")).saveTrack(track);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean deleteTrack(Track track) {
|
||||||
|
return backing.get(types.get("track")).deleteTrack(track);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean saveUUIDData(String username, UUID uuid) {
|
||||||
|
return backing.get(types.get("uuid")).saveUUIDData(username, uuid);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public UUID getUUID(String username) {
|
||||||
|
return backing.get(types.get("uuid")).getUUID(username);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getName(UUID uuid) {
|
||||||
|
return backing.get(types.get("uuid")).getName(uuid);
|
||||||
|
}
|
||||||
|
}
|
@ -28,48 +28,73 @@ import me.lucko.luckperms.LuckPermsPlugin;
|
|||||||
import me.lucko.luckperms.storage.methods.*;
|
import me.lucko.luckperms.storage.methods.*;
|
||||||
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.HashSet;
|
||||||
|
import java.util.Map;
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
|
|
||||||
@UtilityClass
|
@UtilityClass
|
||||||
public class StorageFactory {
|
public class StorageFactory {
|
||||||
private static final Set<String> TYPES = ImmutableSet.of("flatfile", "mongodb", "mysql", "sqlite", "h2");
|
private static final Set<String> TYPES = ImmutableSet.of("flatfile", "mongodb", "mysql", "sqlite", "h2");
|
||||||
|
|
||||||
|
@SuppressWarnings("unchecked")
|
||||||
public static Datastore getDatastore(LuckPermsPlugin plugin, String defaultMethod) {
|
public static Datastore getDatastore(LuckPermsPlugin plugin, String defaultMethod) {
|
||||||
Datastore datastore;
|
Datastore datastore;
|
||||||
|
|
||||||
plugin.getLog().info("Detecting storage method...");
|
plugin.getLog().info("Detecting storage method...");
|
||||||
String storageMethod = plugin.getConfiguration().getStorageMethod().toLowerCase();
|
if (plugin.getConfiguration().getSplitStorage()) {
|
||||||
|
plugin.getLog().info("Using split storage.");
|
||||||
|
|
||||||
if (!TYPES.contains(storageMethod)) {
|
// java sucks
|
||||||
plugin.getLog().severe("Storage method '" + storageMethod + "' not recognised. Using the default instead.");
|
Map<String, String> types = (Map<String, String>) plugin.getConfiguration().getSplitStorageOptions();
|
||||||
storageMethod = defaultMethod;
|
|
||||||
}
|
|
||||||
|
|
||||||
switch (storageMethod) {
|
types.entrySet().stream()
|
||||||
case "mysql":
|
.filter(e -> !TYPES.contains(e.getValue().toLowerCase()))
|
||||||
plugin.getLog().info("Using MySQL as storage method.");
|
.forEach(e -> {
|
||||||
datastore = new MySQLDatastore(plugin, plugin.getConfiguration().getDatabaseValues());
|
plugin.getLog().severe("Storage method for " + e.getKey() + " - " + e.getValue() + " not recognised. " +
|
||||||
break;
|
"Using the default instead.");
|
||||||
case "sqlite":
|
e.setValue(defaultMethod);
|
||||||
plugin.getLog().info("Using SQLite as storage method.");
|
});
|
||||||
datastore = new SQLiteDatastore(plugin, new File(plugin.getDataFolder(), "luckperms.sqlite"));
|
|
||||||
break;
|
Set<String> neededTypes = new HashSet<>();
|
||||||
case "h2":
|
neededTypes.addAll(types.values());
|
||||||
plugin.getLog().info("Using H2 as storage method.");
|
|
||||||
datastore = new H2Datastore(plugin, new File(plugin.getDataFolder(), "luckperms.db"));
|
Map<String, Datastore> backing = new HashMap<>();
|
||||||
break;
|
|
||||||
case "mongodb":
|
for (String type : neededTypes) {
|
||||||
plugin.getLog().info("Using MongoDB as storage method.");
|
backing.put(type, fromString(type, plugin));
|
||||||
datastore = new MongoDBDatastore(plugin, plugin.getConfiguration().getDatabaseValues());
|
}
|
||||||
break;
|
|
||||||
default:
|
datastore = new SplitDatastore(plugin, backing, types);
|
||||||
plugin.getLog().info("Using Flatfile (JSON) as storage method.");
|
|
||||||
datastore = new FlatfileDatastore(plugin, plugin.getDataFolder());
|
} else {
|
||||||
break;
|
String storageMethod = plugin.getConfiguration().getStorageMethod().toLowerCase();
|
||||||
|
if (!TYPES.contains(storageMethod)) {
|
||||||
|
plugin.getLog().severe("Storage method '" + storageMethod + "' not recognised. Using the default instead.");
|
||||||
|
storageMethod = defaultMethod;
|
||||||
|
}
|
||||||
|
|
||||||
|
datastore = fromString(storageMethod, plugin);
|
||||||
|
plugin.getLog().info("Using " + datastore.getName() + " as storage method.");
|
||||||
}
|
}
|
||||||
|
|
||||||
plugin.getLog().info("Initialising datastore...");
|
plugin.getLog().info("Initialising datastore...");
|
||||||
datastore.init();
|
datastore.init();
|
||||||
return datastore;
|
return datastore;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static Datastore fromString(String storageMethod, LuckPermsPlugin plugin) {
|
||||||
|
switch (storageMethod) {
|
||||||
|
case "mysql":
|
||||||
|
return new MySQLDatastore(plugin, plugin.getConfiguration().getDatabaseValues());
|
||||||
|
case "sqlite":
|
||||||
|
return new SQLiteDatastore(plugin, new File(plugin.getDataFolder(), "luckperms.sqlite"));
|
||||||
|
case "h2":
|
||||||
|
return new H2Datastore(plugin, new File(plugin.getDataFolder(), "luckperms.db"));
|
||||||
|
case "mongodb":
|
||||||
|
return new MongoDBDatastore(plugin, plugin.getConfiguration().getDatabaseValues());
|
||||||
|
default:
|
||||||
|
return new FlatfileDatastore(plugin, plugin.getDataFolder());
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -47,6 +47,20 @@ log-notify=true
|
|||||||
# Fill out connection info below if you're using MySQL or MongoDB
|
# Fill out connection info below if you're using MySQL or MongoDB
|
||||||
storage-method="h2"
|
storage-method="h2"
|
||||||
|
|
||||||
|
# This block enables support for split datastores.
|
||||||
|
# Only touch this if you're sure that you know what you're doing.
|
||||||
|
# I (the author) do not endorse nor recommend the use of this feature.
|
||||||
|
split-storage: {
|
||||||
|
enabled=false
|
||||||
|
methods: {
|
||||||
|
user="h2"
|
||||||
|
group="h2"
|
||||||
|
track="h2"
|
||||||
|
uuid="h2"
|
||||||
|
log="h2"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
data: {
|
data: {
|
||||||
address="localhost:3306"
|
address="localhost:3306"
|
||||||
database="minecraft"
|
database="minecraft"
|
||||||
|
Loading…
Reference in New Issue
Block a user