Bugfixes, Format fixes, Some Javadocs.

Following bugs have been fixed:
- Changed command links to say "Click me"
- Concurrent modification exception: Cachehandler 83, Cachehandler 208
- GMTimes on analysis page still shows 0 but graph works
- Page has to be refreshed multiple times to view (Faulty response)
- Data not saved to db on login
- Command usages upside down
- New Players set to 0 too easily (Wrong data was fetched)

Known bugs:
- Graph is wrong way around
- Graph is written to points with no data present
- (Player activity graph data might not be properly saved)
-> Graph uses players from a single point and draws a line
- Demographics data is not saved properly/detected

Other:
- (MySQL not tested)
- PlanLite features
This commit is contained in:
Rsl1122 2017-01-14 21:18:39 +02:00
parent f9df236c59
commit 3ab14a6dd5
43 changed files with 365 additions and 250 deletions

View File

@ -11,7 +11,7 @@ import com.djrapitops.plan.database.databases.SQLiteDB;
import com.djrapitops.plan.data.cache.DataCacheHandler;
import com.djrapitops.plan.data.cache.InspectCacheHandler;
import com.djrapitops.plan.data.listeners.*;
import com.djrapitops.plan.ui.WebSocketServer;
import main.java.com.djrapitops.plan.ui.webserver.WebSocketServer;
import org.bukkit.plugin.java.JavaPlugin;
import java.util.ArrayList;

View File

@ -1,8 +1,8 @@
package com.djrapitops.plan.api;
/**
* Old API Part.
*
* @author Rsl1122
* @deprecated Moved to PlanLite plugin
*/

View File

@ -1,4 +1,3 @@
package com.djrapitops.plan.api;
public enum Gender {

View File

@ -4,6 +4,7 @@ import java.util.HashMap;
/**
* Old API Part
*
* @author Rsl1122
* @deprecated
*/

View File

@ -1,7 +1,6 @@
package com.djrapitops.plan.command;
public enum CommandType
{
public enum CommandType {
CONSOLE,
PLAYER,
CONSOLE_WITH_ARGUMENTS

View File

@ -5,7 +5,6 @@ import com.djrapitops.plan.Plan;
import com.djrapitops.plan.command.CommandType;
import com.djrapitops.plan.command.SubCommand;
import com.djrapitops.plan.data.cache.AnalysisCacheHandler;
import com.djrapitops.plan.utilities.FormatUtils;
import java.util.Date;
import org.bukkit.Bukkit;
import org.bukkit.ChatColor;
@ -15,23 +14,44 @@ import org.bukkit.configuration.file.FileConfiguration;
import org.bukkit.entity.Player;
import org.bukkit.scheduler.BukkitRunnable;
/**
*
* @author Rsl1122
*/
public class AnalyzeCommand extends SubCommand {
private Plan plugin;
private AnalysisCacheHandler analysisCache;
/**
* Class Constructor.
*
* @param plugin Current instance of Plan
*/
public AnalyzeCommand(Plan plugin) {
super("analyze", "plan.analyze", "View the Server Analysis", CommandType.CONSOLE, "");
this.plugin = plugin;
analysisCache = plugin.getAnalysisCache();
}
/**
* Subcommand analyze.
*
* Updates AnalysisCache if last refresh was over 60 seconds ago and sends
* player the link that views cache.
*
* @param sender
* @param cmd
* @param commandLabel
* @param args
* @return true in all cases.
*/
@Override
public boolean onCommand(CommandSender sender, Command cmd, String commandLabel, String[] args) {
Date refresh = new Date();
if (!analysisCache.isCached()) {
analysisCache.updateCache();
} else if (new Date().getTime() - analysisCache.getData().getRefreshDate() > 60 * 5) {
} else if (new Date().getTime() - analysisCache.getData().getRefreshDate() > 60) {
analysisCache.updateCache();
}
ChatColor oColor = Phrase.COLOR_MAIN.color();
@ -60,7 +80,7 @@ public class AnalyzeCommand extends SubCommand {
Player player = (Player) sender;
Bukkit.getServer().dispatchCommand(
Bukkit.getConsoleSender(),
"tellraw " + player.getName() + " [\"\",{\"text\":\" Analysis Results\",\"underlined\":true,"
"tellraw " + player.getName() + " [\"\",{\"text\":\"Click Me\",\"underlined\":true,"
+ "\"clickEvent\":{\"action\":\"open_url\",\"value\":\"" + url + "\"}}]");
}
// Footer

View File

@ -10,7 +10,6 @@ import java.util.Date;
import com.djrapitops.plan.data.cache.InspectCacheHandler;
import com.djrapitops.plan.utilities.FormatUtils;
import com.djrapitops.plan.utilities.MiscUtils;
import static com.google.common.base.Predicates.instanceOf;
import java.util.UUID;
import org.bukkit.Bukkit;
@ -23,11 +22,20 @@ import org.bukkit.configuration.file.FileConfiguration;
import org.bukkit.entity.Player;
import org.bukkit.scheduler.BukkitRunnable;
/**
*
* @author Rsl1122
*/
public class InspectCommand extends SubCommand {
private Plan plugin;
private InspectCacheHandler inspectCache;
/**
* Class Constructor.
*
* @param plugin Current instance of Plan
*/
public InspectCommand(Plan plugin) {
super("inspect", "plan.inspect", "Inspect Player's Data", CommandType.CONSOLE_WITH_ARGUMENTS, "<player>");
@ -35,6 +43,19 @@ public class InspectCommand extends SubCommand {
inspectCache = plugin.getInspectCache();
}
/**
* Subcommand inspect.
*
* Adds player's data from DataCache/DB to the InspectCache for amount of
* time specified in the config, and clears the data from Cache with a timer
* task.
*
* @param sender
* @param cmd
* @param commandLabel
* @param args Player's name or nothing - if empty sender's name is used.
* @return true in all cases.
*/
@Override
public boolean onCommand(CommandSender sender, Command cmd, String commandLabel, String[] args) {
String playerName = MiscUtils.getPlayerDisplayname(args, sender);
@ -69,7 +90,11 @@ public class InspectCommand extends SubCommand {
final boolean useAlternativeIP = config.getBoolean("Settings.WebServer.ShowAlternativeServerIP");
final int port = config.getInt("Settings.WebServer.Port");
final String alternativeIP = config.getString("Settings.WebServer.AlternativeIP").replaceAll("%port%", "" + port);
final int available = config.getInt("Settings.Cache.InspectCache.ClearFromInspectCacheAfterXMinutes");
int configValue = config.getInt("Settings.Cache.InspectCache.ClearFromInspectCacheAfterXMinutes");
if (configValue <= 0) {
configValue = 4;
}
final int available = configValue;
(new BukkitRunnable() {
@Override
public void run() {
@ -90,7 +115,7 @@ public class InspectCommand extends SubCommand {
Player player = (Player) sender;
Bukkit.getServer().dispatchCommand(
Bukkit.getConsoleSender(),
"tellraw " + player.getName() + " [\"\",{\"text\":\" Inspect Results\",\"underlined\":true,"
"tellraw " + player.getName() + " [\"\",{\"text\":\"Click Me\",\"underlined\":true,"
+ "\"clickEvent\":{\"action\":\"open_url\",\"value\":\"" + url + "\"}}]");
}

View File

@ -18,17 +18,38 @@ import org.bukkit.command.CommandSender;
import org.bukkit.configuration.file.FileConfiguration;
import org.bukkit.entity.Player;
/**
*
* @author Rsl1122
*/
public class SearchCommand extends SubCommand {
private final Plan plugin;
private InspectCacheHandler inspectCache;
/**
* Class Constructor.
*
* @param plugin Current instance of Plan
*/
public SearchCommand(Plan plugin) {
super("search", "plan.search", "Search for player", CommandType.CONSOLE_WITH_ARGUMENTS, "<Part of Playername");
this.plugin = plugin;
inspectCache = plugin.getInspectCache();
}
/**
* Subcommand search.
*
* Searches database for matching playernames and caches matching PlayerData
* to InspectCache. Shows all links to matching players data.
*
* @param sender
* @param cmd
* @param commandLabel
* @param args Part of a Players name
* @return true in all cases.
*/
@Override
public boolean onCommand(CommandSender sender, Command cmd, String commandLabel, String[] args) {
if (args.length != 1) {
@ -53,7 +74,11 @@ public class SearchCommand extends SubCommand {
final boolean useAlternativeIP = config.getBoolean("Settings.WebServer.ShowAlternativeServerIP");
final int port = config.getInt("Settings.WebServer.Port");
final String alternativeIP = config.getString("Settings.WebServer.AlternativeIP").replaceAll("%port%", "" + port);
final int available = config.getInt("Settings.Cache.InspectCache.ClearFromInspectCacheAfterXMinutes");
int configValue = config.getInt("Settings.Cache.InspectCache.ClearFromInspectCacheAfterXMinutes");
if (configValue <= 0) {
configValue = 4;
}
final int available = configValue;
// Header
sender.sendMessage(hColor + Phrase.ARROWS_RIGHT.toString() + oColor + " Player Analytics - Search results for: " + args[0]);
@ -79,7 +104,7 @@ public class SearchCommand extends SubCommand {
Player player = (Player) sender;
Bukkit.getServer().dispatchCommand(
Bukkit.getConsoleSender(),
"tellraw "+player.getName()+ " [\"\",{\"text\":\" Search Result\",\"underlined\":true,"
"tellraw " + player.getName() + " [\"\",{\"text\":\"Click Me\",\"underlined\":true,"
+ "\"clickEvent\":{\"action\":\"open_url\",\"value\":\"" + url + "\"}}]");
}
}

View File

@ -36,7 +36,6 @@ public class AnalysisData {
}
// Getters and setters v---------------------------------v
public String getPlayersChartImgHtmlMonth() {
return playersChartImgHtmlMonth;
}
@ -133,8 +132,6 @@ public class AnalysisData {
this.gm3Perc = gm3Perc;
}
public int getTotalPlayers() {
return totalPlayers;
}
@ -167,7 +164,6 @@ public class AnalysisData {
return gmTimesChartImgHtml;
}
public String getActivityChartImgHtml() {
return activityChartImgHtml;
}
@ -196,7 +192,6 @@ public class AnalysisData {
this.gmTimesChartImgHtml = gmTimesChartImgHtml;
}
public void setActivityChartImgHtml(String activityChartImgHtml) {
this.activityChartImgHtml = activityChartImgHtml;
}

View File

@ -1,9 +1,9 @@
package com.djrapitops.plan.data;
import com.djrapitops.plan.api.Gender;
public class DemographicsData {
private int age;
private Gender gender;
private String geoLocation;
@ -19,7 +19,6 @@ public class DemographicsData {
}
// Getters
public int getAge() {
return age;
}
@ -33,7 +32,6 @@ public class DemographicsData {
}
// Setters
public void setAge(int age) {
this.age = age;
}
@ -46,5 +44,4 @@ public class DemographicsData {
this.geoLocation = geoLocation;
}
}

View File

@ -1,10 +1,10 @@
package com.djrapitops.plan.data;
import java.util.HashMap;
import org.bukkit.Bukkit;
public class ServerData {
private final HashMap<String, Integer> commandUsage;
private int playersOnline;
private int newPlayers;

View File

@ -1,4 +1,3 @@
package com.djrapitops.plan.data.cache;
import com.djrapitops.plan.Plan;
@ -10,6 +9,7 @@ import com.djrapitops.plan.utilities.Analysis;
* @author Rsl1122
*/
public class AnalysisCacheHandler {
private Plan plugin;
private AnalysisData cache;
private Analysis analysis;

View File

@ -5,10 +5,10 @@ import com.djrapitops.plan.database.Database;
import com.djrapitops.plan.data.*;
import com.djrapitops.plan.data.handlers.*;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Set;
import java.util.UUID;
import org.bukkit.Bukkit;
import static org.bukkit.Bukkit.getPlayer;
import org.bukkit.entity.Player;
import org.bukkit.scheduler.BukkitRunnable;
import static org.bukkit.Bukkit.getPlayer;
@ -205,8 +205,9 @@ public class DataCacheHandler {
*/
public void clearCache() {
Set<UUID> uuidSet = dataCache.keySet();
for (UUID uuid : uuidSet) {
clearFromCache(uuid);
Iterator<UUID> uuidIterator = uuidSet.iterator();
while (uuidIterator.hasNext()) {
clearFromCache(uuidIterator.next());
}
}

View File

@ -73,8 +73,7 @@ public class ActivityHandler {
/**
* Updates UserData about activity related things on Logout.
*
* Saves PlayTime, Set's LastPlayed
* value to long matching current Date
* Saves PlayTime, Set's LastPlayed value to long matching current Date
*
* @param event QuitEvent from Listener
* @param data UserData matching the Player

View File

@ -16,6 +16,7 @@ public class BasicInfoHandler {
/**
* Class Constructor
*
* @param plugin Current instance of Plan
* @param h Current instance of DataCacheHandler
*/
@ -25,6 +26,7 @@ public class BasicInfoHandler {
/**
* Adds new nicknames and IPs to UserData
*
* @param event JoinEvent to get the Player
* @param data UserData matching the Player
*/
@ -36,6 +38,7 @@ public class BasicInfoHandler {
/**
* Adds new nicknames and IPs to UserData in case of /reload
*
* @param player A player that is online when /reload is run
* @param data UserData matching the Player
*/

View File

@ -20,6 +20,7 @@ public class LocationHandler {
/**
* Class Constructor.
*
* @param plugin Current instance of Plan
* @param h Current instance of DataCacheHandler
*/
@ -29,6 +30,7 @@ public class LocationHandler {
/**
* Adds location to the UserData if it is not being saved.
*
* @param uuid UUID of the matching Player
* @param loc Location from the MoveEvent listener.
*/
@ -43,6 +45,7 @@ public class LocationHandler {
/**
* Adds multiple locaitons to the UserData.
*
* @param uuid UUID of the matching Player
* @param locs The Locations that are added.
*/
@ -54,6 +57,7 @@ public class LocationHandler {
* Handles QuitEvent by updating BedLocation.
*
* Uses OfflinePlayer to prevent null bedlocation.
*
* @param event QuitEvent from Listener.
* @param data UserData matching Player.
*/

View File

@ -1,10 +1,10 @@
package com.djrapitops.plan.data.handlers;
import com.djrapitops.plan.Plan;
import com.djrapitops.plan.PlanLiteHook;
public class PlanLiteHandler {
private Plan plugin;
private PlanLiteHook hook;

View File

@ -1,9 +1,9 @@
package com.djrapitops.plan.data.handlers;
import com.djrapitops.plan.data.ServerData;
public class ServerDataHandler {
private ServerData serverData;
public ServerDataHandler(ServerData serverData) {

View File

@ -33,6 +33,7 @@ public class PlanChatListener implements Listener {
/**
* ChatEvent listener.
*
* @param event Fired Event
*/
@EventHandler(priority = EventPriority.MONITOR)
@ -46,4 +47,3 @@ public class PlanChatListener implements Listener {
demographicsHandler.handleChatEvent(event, data);
}
}

View File

@ -32,4 +32,3 @@ public class PlanGamemodeChangeListener implements Listener {
gmTimesH.handleChangeEvent(event, data);
}
}

View File

@ -12,6 +12,8 @@ import org.bukkit.event.Listener;
import org.bukkit.event.player.PlayerJoinEvent;
import org.bukkit.event.player.PlayerKickEvent;
import org.bukkit.event.player.PlayerQuitEvent;
import static org.bukkit.plugin.java.JavaPlugin.getPlugin;
import org.bukkit.scheduler.BukkitRunnable;
/**
*
@ -19,6 +21,7 @@ import org.bukkit.event.player.PlayerQuitEvent;
*/
public class PlanPlayerListener implements Listener {
private final Plan plugin;
private final DataCacheHandler handler;
private final ActivityHandler activityH;
private final BasicInfoHandler basicInfoH;
@ -37,6 +40,7 @@ public class PlanPlayerListener implements Listener {
* @param plugin Current instance of Plan
*/
public PlanPlayerListener(Plan plugin) {
this.plugin = plugin;
handler = plugin.getHandler();
activityH = handler.getActivityHandler();
basicInfoH = handler.getBasicInfoHandler();
@ -69,8 +73,13 @@ public class PlanPlayerListener implements Listener {
basicInfoH.handleLogin(event, data);
gmTimesH.handleLogin(event, data);
demographicH.handleLogin(event, data);
(new BukkitRunnable() {
@Override
public void run() {
handler.saveCachedData(uuid);
}
}).runTaskLater(plugin, 15 * 20);
}
/**
* PlayerQuitEvent Listener.

View File

@ -22,6 +22,7 @@ public class PlanPlayerMoveListener implements Listener {
/**
* Class Consturctor.
*
* @param plugin Current instance of Plan
*/
public PlanPlayerMoveListener(Plan plugin) {

View File

@ -144,7 +144,6 @@ public abstract class SQLDB extends Database {
public boolean init() {
super.init();
return checkConnection();
}
public boolean checkConnection() {
@ -230,10 +229,8 @@ public abstract class SQLDB extends Database {
}
} catch (SQLException e) {
e.printStackTrace();
return false;
}
return true;
}
@ -420,7 +417,7 @@ public abstract class SQLDB extends Database {
HashMap<Long, ServerData> rawServerData = new HashMap<>();
try {
PreparedStatement statement = connection.prepareStatement("SELECT * FROM " + serverdataName
+ " ORDER BY " + serverdataColumnDate + " ASC");
+ " ORDER BY " + serverdataColumnDate + " DESC");
ResultSet set = statement.executeQuery();
while (set.next()) {
@ -443,7 +440,7 @@ public abstract class SQLDB extends Database {
Date startOfToday = new Date(now.getTime() - (now.getTime() % 86400000));
try {
PreparedStatement statement = connection.prepareStatement("SELECT * FROM " + serverdataName
+ " ORDER BY " + serverdataColumnDate + " ASC LIMIT 1");
+ " ORDER BY " + serverdataColumnDate + " DESC LIMIT 1");
ResultSet set = statement.executeQuery();
while (set.next()) {

View File

@ -1,4 +1,3 @@
package com.djrapitops.plan.ui;
import com.djrapitops.plan.Plan;
@ -15,6 +14,7 @@ import java.util.UUID;
* @author Rsl1122
*/
public class DataRequestHandler {
private Plan plugin;
private InspectCacheHandler inspectCache;
private AnalysisCacheHandler analysisCache;

View File

@ -11,6 +11,14 @@ import com.googlecode.charts4j.Slice;
*/
public class ActivityPieChartCreator {
/**
* Creates a image link to Activity Chart.
*
* @param totalBanned Number of Banned Players
* @param active Number of Active Players
* @param inactive Number of Inactive Players
* @return Url to Image link.
*/
public static String createChart(int totalBanned, int active, int inactive) {
int total = totalBanned + active + inactive;
@ -35,5 +43,4 @@ public class ActivityPieChartCreator {
String refURL = refChart.toURLString();
return refURL;
}
}

View File

@ -13,6 +13,15 @@ import org.bukkit.GameMode;
*/
public class GMTimesPieChartCreator {
/**
* Creates a link to New image of the Gamemode usage chart without total.
*
* Calculated total is not required.
*
* @param gmTimes Map with all 4 Gamemodes and responding times spent in
* them
* @return Url of charts4j image link.
*/
public static String createChart(HashMap<GameMode, Long> gmTimes) {
long total = gmTimes.get(GameMode.SURVIVAL) + gmTimes.get(GameMode.CREATIVE)
+ gmTimes.get(GameMode.ADVENTURE) + gmTimes.get(GameMode.SPECTATOR);
@ -20,6 +29,14 @@ public class GMTimesPieChartCreator {
return createChart(gmTimes, total);
}
/**
* Creates a link to New image of the Gamemode usage chart.
*
* @param gmTimes Map with all 4 Gamemodes and responding times spent in
* them
* @param total Time spent in all 4 gamemodes.
* @return Url of charts4j image link.
*/
public static String createChart(HashMap<GameMode, Long> gmTimes, long total) {
long gmZero = gmTimes.get(GameMode.SURVIVAL);
long gmOne = gmTimes.get(GameMode.CREATIVE);

View File

@ -17,11 +17,22 @@ public class Response {
private DataRequestHandler requestHandler;
/**
* Class Constructor.
*
* @param output Website outputstream to write the response to.
* @param h Current Instance of DataRequestHandler
*/
public Response(OutputStream output, DataRequestHandler h) {
this.output = output;
requestHandler = h;
}
/**
* Wrties the HTML to the Outputstream according to the requested page.
*
* @throws IOException
*/
public void sendStaticResource() throws IOException {
try {
if (request == null) {
@ -55,7 +66,7 @@ public class Response {
}
if (requestHandler.checkIfCached(uuid)) {
String dataHtml = requestHandler.getDataHtml(uuid);
String htmlDef = "HTTP/1.1 Inspect\r\n"
String htmlDef = "HTTP/1.1 OK\r\n"
+ "Content-Type: text/html\r\n"
+ "Content-Length: " + dataHtml.length() + "\r\n"
+ "\r\n";
@ -66,7 +77,7 @@ public class Response {
} else if (command.equals("server")) {
if (requestHandler.checkIfAnalysisIsCached()) {
String analysisHtml = requestHandler.getAnalysisHtml();
String htmlDef = "HTTP/1.1 Analysis\r\n"
String htmlDef = "HTTP/1.1 OK\r\n"
+ "Content-Type: text/html\r\n"
+ "Content-Length: " + analysisHtml.length() + "\r\n"
+ "\r\n";
@ -86,6 +97,11 @@ public class Response {
}
}
/**
* Sets the HTML Request to get response for.
*
* @param request Request.
*/
public void setRequest(Request request) {
this.request = request;
}

View File

@ -1,8 +1,9 @@
package com.djrapitops.plan.ui;
package main.java.com.djrapitops.plan.ui.webserver;
import com.djrapitops.plan.Plan;
import com.djrapitops.plan.data.cache.AnalysisCacheHandler;
import com.djrapitops.plan.data.cache.InspectCacheHandler;
import com.djrapitops.plan.ui.DataRequestHandler;
import com.djrapitops.plan.ui.webserver.Request;
import com.djrapitops.plan.ui.webserver.Response;
import java.io.IOException;
@ -30,6 +31,13 @@ public class WebSocketServer {
private boolean shutdown;
/**
* Class Constructor.
*
* Initializes DataRequestHandler
*
* @param plugin Current instance of Plan
*/
public WebSocketServer(Plan plugin) {
this.plugin = plugin;
this.inspectHandler = plugin.getInspectCache();
@ -38,6 +46,9 @@ public class WebSocketServer {
dataReqHandler = new DataRequestHandler(plugin);
}
/**
* Starts up the Webserver in a Asyncronous thread.
*/
public void initServer() {
//Server is already enabled stop code
if (ENABLED) {
@ -84,6 +95,9 @@ public class WebSocketServer {
}
}
/**
* Shuts down the server - Async thread is closed with shutdown boolean.
*/
public void stop() {
plugin.log("Shutting down Webserver..");
shutdown = true;

View File

@ -5,6 +5,7 @@ import com.djrapitops.plan.data.AnalysisData;
import com.djrapitops.plan.data.ServerData;
import com.djrapitops.plan.data.UserData;
import com.djrapitops.plan.ui.graphs.GMTimesPieChartCreator;
import java.util.Collections;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
@ -74,10 +75,10 @@ public class AnalysisUtils {
HashMap<String, String> replaceMap = new HashMap<>();
replaceMap.put("%activitypiechart%", data.getActivityChartImgHtml());
replaceMap.put("%gmpiechart%", data.getGmTimesChartImgHtml());
replaceMap.put("%gm0%", (int) data.getGm0Perc() * 100 + "%");
replaceMap.put("%gm1%", (int) data.getGm1Perc() * 100 + "%");
replaceMap.put("%gm2%", (int) data.getGm2Perc() * 100 + "%");
replaceMap.put("%gm3%", (int) data.getGm3Perc() * 100 + "%");
replaceMap.put("%gm0%", (int) (data.getGm0Perc() * 100) + "%");
replaceMap.put("%gm1%", (int) (data.getGm1Perc() * 100) + "%");
replaceMap.put("%gm2%", (int) (data.getGm2Perc() * 100) + "%");
replaceMap.put("%gm3%", (int) (data.getGm3Perc() * 100) + "%");
replaceMap.put("%active%", "" + data.getActive());
replaceMap.put("%banned%", "" + data.getBanned());
replaceMap.put("%inactive%", "" + data.getInactive());
@ -121,6 +122,7 @@ public class AnalysisUtils {
html = "<p>Error Calcuclating Command usages</p>";
return html;
}
Collections.reverse(sorted);
int i = 1;
for (String[] values : sorted) {
if (i >= 50) {

View File

@ -1,4 +1,3 @@
package com.djrapitops.plan.utilities;
import java.util.ArrayList;

View File

@ -34,63 +34,55 @@ import java.nio.ByteBuffer;
import java.util.*;
import java.util.concurrent.Callable;
public class UUIDFetcher implements Callable<Map<String, UUID>>
{
public class UUIDFetcher implements Callable<Map<String, UUID>> {
private static final double PROFILES_PER_REQUEST = 100;
private static final String PROFILE_URL = "https://api.mojang.com/profiles/minecraft";
private final JSONParser jsonParser = new JSONParser();
private final List<String> names;
private final boolean rateLimiting;
public UUIDFetcher( List<String> names, boolean rateLimiting )
{
public UUIDFetcher(List<String> names, boolean rateLimiting) {
this.names = ImmutableList.copyOf(names);
this.rateLimiting = rateLimiting;
}
public UUIDFetcher( List<String> names )
{
public UUIDFetcher(List<String> names) {
this(names, true);
}
public Map<String, UUID> call() throws Exception
{
public Map<String, UUID> call() throws Exception {
Map<String, UUID> uuidMap = new HashMap<String, UUID>();
int requests = (int) Math.ceil(names.size() / PROFILES_PER_REQUEST);
for( int i = 0; i < requests; i++ )
{
for (int i = 0; i < requests; i++) {
HttpURLConnection connection = createConnection();
String body = JSONArray.toJSONString(names.subList(i * 100, Math.min((i + 1) * 100, names.size())));
writeBody(connection, body);
JSONArray array = (JSONArray) jsonParser.parse(new InputStreamReader(connection.getInputStream()));
for( Object profile : array )
{
for (Object profile : array) {
JSONObject jsonProfile = (JSONObject) profile;
String id = (String) jsonProfile.get("id");
String name = (String) jsonProfile.get("name");
UUID uuid = UUIDFetcher.getUUID(id);
uuidMap.put(name, uuid);
}
if( rateLimiting && i != requests - 1 )
{
if (rateLimiting && i != requests - 1) {
Thread.sleep(100L);
}
}
return uuidMap;
}
private static void writeBody( HttpURLConnection connection, String body ) throws Exception
{
private static void writeBody(HttpURLConnection connection, String body) throws Exception {
OutputStream stream = connection.getOutputStream();
stream.write(body.getBytes());
stream.flush();
stream.close();
}
private static HttpURLConnection createConnection() throws Exception
{
private static HttpURLConnection createConnection() throws Exception {
URL url = new URL(PROFILE_URL);
HttpURLConnection connection = (HttpURLConnection) url.openConnection();
connection.setRequestMethod("POST");
@ -101,23 +93,19 @@ public class UUIDFetcher implements Callable<Map<String, UUID>>
return connection;
}
private static UUID getUUID( String id )
{
private static UUID getUUID(String id) {
return UUID.fromString(id.substring(0, 8) + "-" + id.substring(8, 12) + "-" + id.substring(12, 16) + "-" + id.substring(16, 20) + "-" + id.substring(20, 32));
}
public static byte[] toBytes( UUID uuid )
{
public static byte[] toBytes(UUID uuid) {
ByteBuffer byteBuffer = ByteBuffer.wrap(new byte[16]);
byteBuffer.putLong(uuid.getMostSignificantBits());
byteBuffer.putLong(uuid.getLeastSignificantBits());
return byteBuffer.array();
}
public static UUID fromBytes( byte[] array )
{
if( array.length != 16 )
{
public static UUID fromBytes(byte[] array) {
if (array.length != 16) {
throw new IllegalArgumentException("Illegal byte array length: " + array.length);
}
ByteBuffer byteBuffer = ByteBuffer.wrap(array);
@ -126,8 +114,7 @@ public class UUIDFetcher implements Callable<Map<String, UUID>>
return new UUID(mostSignificant, leastSignificant);
}
public static UUID getUUIDOf( String name ) throws Exception
{
public static UUID getUUIDOf(String name) throws Exception {
return new UUIDFetcher(Arrays.asList(name)).call().get(name);
}
}

View File

@ -16,5 +16,4 @@ public class MapComparator {
return sortedList;
}
}