Implement importing from any database in /mmoupdate

This commit is contained in:
riking 2013-06-08 21:51:42 -07:00
parent ab0541f1c1
commit 9034a36f07
9 changed files with 228 additions and 65 deletions

View File

@ -29,6 +29,8 @@ Version 1.4.06-dev
+ Added information about /party itemshare and /party expshare to the party help page
+ Added option to use scoreboards for power level display instead of Spout.
+ Added permission node to prevent inspecting hidden players
+ Added SQL to Flatfile database conversion
+ Added ability to use custom database managers and convert to/from them
= Fixed bug where spawned arrows could throw ArrayIndexOutOfBoundsException
= Fixed bug where custom Spout titles were overwritten by mcMMO.
= Fixed bug where Nether Quartz wasn't included in Smelting or item sharing

View File

@ -0,0 +1,42 @@
package com.gmail.nossr50.commands.database;
import java.util.List;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import com.gmail.nossr50.config.Config;
import com.gmail.nossr50.database.DatabaseManagerFactory;
import com.gmail.nossr50.locale.LocaleLoader;
import com.google.common.collect.ImmutableList;
public class MmoshowdbCommand implements TabExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
if (args.length != 0) {
return false;
}
else {
Class<?> clazz = DatabaseManagerFactory.getCustomDatabaseManagerClass();
if (clazz != null) {
sender.sendMessage(LocaleLoader.getString("Commands.mmoshowdb", clazz.getName()));
return true;
}
else {
if (Config.getInstance().getUseMySQL()) {
sender.sendMessage(LocaleLoader.getString("Commands.mmoshowdb", "sql"));
}
else {
sender.sendMessage(LocaleLoader.getString("Commands.mmoshowdb", "flatfile"));
}
return true;
}
}
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
return ImmutableList.of();
}
}

View File

@ -1,49 +1,148 @@
package com.gmail.nossr50.commands.database;
import java.util.List;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
import org.bukkit.command.ConsoleCommandSender;
import org.bukkit.command.TabExecutor;
import org.bukkit.entity.Player;
import com.gmail.nossr50.mcMMO;
import com.gmail.nossr50.config.Config;
import com.gmail.nossr50.database.DatabaseManager;
import com.gmail.nossr50.database.DatabaseManagerFactory;
import com.gmail.nossr50.datatypes.player.PlayerProfile;
import com.gmail.nossr50.locale.LocaleLoader;
import com.gmail.nossr50.runnables.database.FromFlatfileConversionTask;
import com.gmail.nossr50.runnables.database.ConversionTask;
import com.gmail.nossr50.util.player.UserManager;
import com.google.common.collect.ImmutableList;
public class MmoupdateCommand implements TabExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
if (!Config.getInstance().getUseMySQL()) {
sender.sendMessage("SQL Mode is not enabled."); // TODO: Localize
return true;
}
switch (args.length) {
case 0:
sender.sendMessage(LocaleLoader.getString("Commands.mmoupdate.Start"));
case 1:
String argType = args[0];
String oldType = validateName(sender, args[0]);
if (oldType == null) {
return true;
}
String newType = getCurrentDb();
if (newType.equals(oldType)) {
sender.sendMessage(LocaleLoader.getString("Commands.mmoupdate.Same", argType));
return true;
}
DatabaseManager oldDb;
if (oldType == "sql") {
oldDb = DatabaseManagerFactory.createSQLDatabaseManager();
}
else if (oldType == "flatfile") {
oldDb = DatabaseManagerFactory.createFlatfileDatabaseManager();
}
else try {
@SuppressWarnings("unchecked")
Class<? extends DatabaseManager> clazz = (Class<? extends DatabaseManager>) Class.forName(oldType);
oldDb = DatabaseManagerFactory.createCustomDatabaseManager((Class<? extends DatabaseManager>) clazz);
oldType = clazz.getSimpleName(); // For pretty-printing; we have the database now
}
catch (Throwable e) {
return false;
}
sender.sendMessage(LocaleLoader.getString("Commands.mmoupdate.Start", oldType, newType));
// Convert the online players right away, without waiting
// first, flush out the current data
UserManager.saveAll();
UserManager.clearAll();
new FromFlatfileConversionTask().runTaskAsynchronously(mcMMO.p);
for (Player player : mcMMO.p.getServer().getOnlinePlayers()) {
// Get the profile from the old database and save it in the new
PlayerProfile profile = oldDb.loadPlayerProfile(player.getName(), false);
if (profile.isLoaded()) {
mcMMO.getDatabaseManager().saveUser(profile);
}
// Reload from the current database via UserManager
UserManager.addUser(player);
}
sender.sendMessage(LocaleLoader.getString("Commands.mmoupdate.Finish"));
// Schedule the task for all users
new ConversionTask(oldDb, sender, oldType, newType).runTaskAsynchronously(mcMMO.p);
return true;
default:
return false;
break;
}
// If you don't do your research, you get lied to
if (!(sender instanceof ConsoleCommandSender)) {
sender.sendMessage(LocaleLoader.getString("Commands.mmoupdate.OpOnly"));
return true;
}
return false;
}
/**
* @return null - if type not recognized / class not found
* empty string - if type is same as current
* normalized string - if type is recognized
*/
private String validateName(CommandSender sender, String type) {
if (type.equalsIgnoreCase("sql") || type.equalsIgnoreCase("mysql")) {
return "sql";
}
if (type.equalsIgnoreCase("flatfile")) {
return "flatfile";
}
try {
Class<?> clazz = Class.forName(type);
if (!DatabaseManager.class.isAssignableFrom(clazz)) {
sender.sendMessage(LocaleLoader.getString("Commands.mmoupdate.InvalidType", type));
return null;
}
return type;
}
catch (Exception e) {
sender.sendMessage(LocaleLoader.getString("Commands.mmoupdate.InvalidType", type));
return null;
}
}
private String getCurrentDb() {
if (DatabaseManagerFactory.getCustomDatabaseManagerClass() != null) {
return DatabaseManagerFactory.getCustomDatabaseManagerClass().getSimpleName();
}
if (Config.getInstance().getUseMySQL()) {
return "sql";
}
else {
return "flatfile";
}
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
return ImmutableList.of();
if (sender instanceof Player) {
// What, you're trying to run this on a live server? No autocomplete for you! Do your research first!
return ImmutableList.of();
}
Class<?> clazz = DatabaseManagerFactory.getCustomDatabaseManagerClass();
if (clazz != null) {
return ImmutableList.of("confirm", "flatfile", "sql", clazz.getName());
}
return ImmutableList.of("confirm", "flatfile", "sql");
}
}

View File

@ -46,6 +46,10 @@ public class DatabaseManagerFactory {
customManager = clazz;
}
public static Class<? extends DatabaseManager> getCustomDatabaseManagerClass() {
return customManager;
}
// For data conversion purposes
public static FlatfileDatabaseManager createFlatfileDatabaseManager() {

View File

@ -0,0 +1,41 @@
package com.gmail.nossr50.runnables.database;
import java.util.logging.Level;
import org.bukkit.command.CommandSender;
import org.bukkit.scheduler.BukkitRunnable;
import com.gmail.nossr50.mcMMO;
import com.gmail.nossr50.database.DatabaseManager;
import com.gmail.nossr50.locale.LocaleLoader;
public class ConversionTask extends BukkitRunnable {
private final DatabaseManager sourceDb;
private final CommandSender sender;
private final String message;
public ConversionTask(DatabaseManager from, CommandSender sendback, String oldType, String newType) {
sourceDb = from;
sender = sendback;
message = LocaleLoader.getString("Commands.mmoupdate.Finish", oldType, newType);
}
@Override
public void run() {
sourceDb.convertUsers(mcMMO.getDatabaseManager());
// Announce completeness
mcMMO.p.getServer().getScheduler().runTask(mcMMO.p, new CompleteAnnouncement());
}
public class CompleteAnnouncement implements Runnable {
@Override
public void run() {
try {
sender.sendMessage(message);
} catch (Exception e) {
mcMMO.p.getLogger().log(Level.WARNING, "Exception sending database conversion completion message to " + sender.getName(), e);
}
}
}
}

View File

@ -1,46 +0,0 @@
package com.gmail.nossr50.runnables.database;
import java.io.BufferedReader;
import java.io.FileReader;
import org.bukkit.scheduler.BukkitRunnable;
import com.gmail.nossr50.mcMMO;
import com.gmail.nossr50.database.DatabaseManager;
import com.gmail.nossr50.database.DatabaseManagerFactory;
import com.gmail.nossr50.datatypes.player.PlayerProfile;
public class FromFlatfileConversionTask extends BukkitRunnable {
@Override
public void run() {
String location = mcMMO.getUsersFilePath();
try {
DatabaseManager from = DatabaseManagerFactory.createFlatfileDatabaseManager();
DatabaseManager to = mcMMO.getDatabaseManager();
BufferedReader in = new BufferedReader(new FileReader(location));
String line = "";
int converted = 0;
while ((line = in.readLine()) != null) {
// Find if the line contains the player we want.
String[] playerData = line.split(":");
String playerName = playerData[0];
PlayerProfile profile = from.loadPlayerProfile(playerName, false);
if (profile.isLoaded()) {
to.saveUser(profile);
converted++;
}
}
mcMMO.p.getLogger().info("Database updated from users file, " + converted + " items added/updated to DB");
in.close();
}
catch (Exception e) {
mcMMO.p.getLogger().severe("Exception while reading " + location + " (Are you sure you formatted it correctly?) " + e.toString());
}
}
}

View File

@ -19,6 +19,7 @@ import com.gmail.nossr50.commands.chat.AdminChatCommand;
import com.gmail.nossr50.commands.chat.PartyChatCommand;
import com.gmail.nossr50.commands.database.McpurgeCommand;
import com.gmail.nossr50.commands.database.McremoveCommand;
import com.gmail.nossr50.commands.database.MmoshowdbCommand;
import com.gmail.nossr50.commands.database.MmoupdateCommand;
import com.gmail.nossr50.commands.experience.AddlevelsCommand;
import com.gmail.nossr50.commands.experience.AddxpCommand;
@ -276,11 +277,20 @@ public final class CommandRegistrationManager {
PluginCommand command = mcMMO.p.getCommand("mmoupdate");
command.setDescription(LocaleLoader.getString("Commands.Description.mmoupdate"));
command.setPermission("mcmmo.commands.mmoupdate");
command.setPermissionMessage(permissionsMessage);
command.setUsage(LocaleLoader.getString("Commands.Usage.0", "mmoupdate"));
command.setPermissionMessage(LocaleLoader.getString("Commands.mmoupdate.OpOnly"));
command.setUsage(LocaleLoader.getString("Commands.Usage.1", "mmoupdate", "<confirm|flatfile|sql|" + LocaleLoader.getString("Commands.Usage.FullClassName") + ">"));
command.setExecutor(new MmoupdateCommand());
}
private static void registerMmoshowdbCommand() {
PluginCommand command = mcMMO.p.getCommand("mmoshowdb");
command.setDescription(LocaleLoader.getString("Commands.Description.mmoshowdb"));
command.setPermission("mcmmo.commands.mmoshowdb");
command.setPermissionMessage(permissionsMessage);
command.setUsage(LocaleLoader.getString("Commands.Usage.0", "mmoshowdb"));
command.setExecutor(new MmoshowdbCommand());
}
private static void registerAdminChatCommand() {
PluginCommand command = mcMMO.p.getCommand("adminchat");
command.setDescription(LocaleLoader.getString("Commands.Description.adminchat"));
@ -421,6 +431,7 @@ public final class CommandRegistrationManager {
registerMcpurgeCommand();
registerMcremoveCommand();
registerMmoupdateCommand();
registerMmoshowdbCommand();
// Experience Commands
registerAddlevelsCommand();

View File

@ -442,8 +442,11 @@ Commands.mmoedit=[player] <skill> <newvalue> [[RED]] - Modify target
Commands.mmoedit.AllSkills.1=[[GREEN]]Your level in all skills was set to {0}!
Commands.mmoedit.Modified.1=[[GREEN]]Your level in {0} was set to {1}!
Commands.mmoedit.Modified.2=[[RED]]{0} has been modified for {1}.
Commands.mmoupdate.Start=[[GRAY]]Starting conversion...
Commands.mmoupdate.Finish=[[GREEN]]Conversion finished!
Commands.mmoupdate.Same=[[RED]]You are already using the {0} database!
Commands.mmoupdate.InvalidType=[[RED]]{0} is not a valid database type.
Commands.mmoupdate.Start=[[GRAY]]Starting conversion from {0} to {1}...
Commands.mmoupdate.Finish=[[GRAY]]Database migration complete; the {1} database now has all data from the {0} database.
Commands.mmoshowdb=[[YELLOW]]The currently used database is [[GREEN]]{0}
Commands.ModDescription=[[RED]]- Read brief mod description
Commands.NoConsole=This command does not support console usage.
Commands.Notifications.Off=Ability notifications toggled [[RED]]off
@ -505,6 +508,7 @@ Commands.Usage.0=[[RED]]Proper usage is /{0}
Commands.Usage.1=[[RED]]Proper usage is /{0} {1}
Commands.Usage.2=[[RED]]Proper usage is /{0} {1} {2}
Commands.Usage.3=[[RED]]Proper usage is /{0} {1} {2} {3}
Commands.Usage.FullClassName=classname
Commands.Usage.Level=level
Commands.Usage.Message=message
Commands.Usage.Page=page
@ -751,7 +755,8 @@ Commands.Description.mcremove=Remove a user from the mcMMO database
Commands.Description.mcstats=Show your mcMMO levels and XP
Commands.Description.mctop=Show mcMMO leader boards
Commands.Description.mmoedit=Edit mcMMO levels for a user
Commands.Description.mmoupdate=Convert mcMMO database from Flatfile to MySQL
Commands.Description.mmoupdate=Migrate mcMMO database from an old database into the current one
Commands.Description.mmoshowdb=Show the name of the current database type (for later use with /mmoupdate)
Commands.Description.party=Control various mcMMO party settings
Commands.Description.partychat=Toggle mcMMO party chat on/off or send party chat messages
Commands.Description.ptp=Teleport to an mcMMO party member

View File

@ -58,7 +58,9 @@ commands:
inspect:
description: View detailed mcMMO info on another player
mmoupdate:
description: Convert from Flat File to MySQL
description: Migrate mcMMO database from an old database type to the current
mmoshowdb:
description: Show the name of the current database type (for later use with /mmoupdate)
partychat:
aliases: [pc, p]
description: Toggle Party chat or send party chat messages
@ -717,6 +719,7 @@ permissions:
mcmmo.commands.mmoedit: true
mcmmo.commands.mmoedit.others: true
mcmmo.commands.mmoupdate: true
mcmmo.commands.mmoshowdb: true
mcmmo.commands.ptp.world.all: true
mcmmo.commands.skillreset.all: true
mcmmo.commands.vampirism.all: true
@ -908,6 +911,8 @@ permissions:
description: Allows access to the mmoedit command for other players
mcmmo.commands.mmoupdate:
description: Allows access to the mmoupdate command
mcmmo.commands.mmoshowdb:
description: Allows access to the mmoshowdb command
mcmmo.commands.mobhealth:
default: true
description: Allows access to the mobhealth command