diff --git a/.classpath b/.classpath
index 6cf8f5a..30f7b88 100644
--- a/.classpath
+++ b/.classpath
@@ -27,5 +27,6 @@
+
diff --git a/assets/config.csv b/assets/config.csv
index 20f1aa9..7007008 100644
--- a/assets/config.csv
+++ b/assets/config.csv
@@ -50,7 +50,7 @@
"Localized Commands","stats",""
"Localized Commands","teey",""
"Localized Commands","tony, stark, dontfeelgood, dontfeelsogood","tony, stark, dontfeelgood, dontfeelsogood, snap"
-"Localized Commands","tradebeans",""
+"Localized Commands","tradebeans, trade",""
"Localized Commands","tweet",""
"Localized Commands","vote",""
"Localized Commands","wolfram",""
@@ -323,7 +323,7 @@
"Command Enabler","stats","1"
"Command Enabler","teey","1"
"Command Enabler","tony, stark, dontfeelgood, dontfeelsogood","1"
-"Command Enabler","tradebeans","1"
+"Command Enabler","tradebeans, trade","1"
"Command Enabler","tweet","1"
"Command Enabler","vote","1"
"Command Enabler","wolfram","1"
diff --git a/lib/nanohttpd-2.3.1.jar b/lib/nanohttpd-2.3.1.jar
new file mode 100644
index 0000000..ade9bbe
Binary files /dev/null and b/lib/nanohttpd-2.3.1.jar differ
diff --git a/src/commands/general/CommandTradeBeans.java b/src/commands/general/CommandTradeBeans.java
index 5829c0e..c3b17e1 100644
--- a/src/commands/general/CommandTradeBeans.java
+++ b/src/commands/general/CommandTradeBeans.java
@@ -27,13 +27,22 @@ public class CommandTradeBeans extends Command
}
int beans = 0;
- try {
+
+ try
+ {
beans = Integer.parseInt(input.args.split(" ")[0]);
}
catch (NumberFormatException e)
{
- res.send(LocStrings.stub("TradeBeansIntParseError"));
- return;
+ try
+ {
+ beans = Integer.parseInt(input.args.split(" ")[1]);
+ }
+ catch(Exception eInner)
+ {
+ res.send(LocStrings.stub("TradeBeansIntParseError"));
+ return;
+ }
}
if(user.getBeans() < beans)
diff --git a/src/core/CommandManager.java b/src/core/CommandManager.java
index d356519..fc4dd6b 100644
--- a/src/core/CommandManager.java
+++ b/src/core/CommandManager.java
@@ -1,235 +1,235 @@
-package core;
-
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.Map.Entry;
-
-import commands.characters.CommandCharacterMain;
-import commands.general.*;
-import commands.guildrole.CommandGuildRoleMain;
-import commands.mod.CommandModMain;
-import commands.music.CommandMusicMain;
-import commands.poll.CommandPollMain;
-import commands.raffle.CommandRaffleMain;
-import dataStructures.*;
-import utils.GlobalLog;
-import utils.LogFilter;
-
-public class CommandManager
-{
- // Variables
- private HashMap commands;
- private ArrayList threadAccumulator;
- private CommandEnabler commandEnabler;
- private long invokeCount;
-
- // Singleton
- public static CommandManager instance;
-
- // Default Constructor
- public CommandManager(CommandEnabler commandEnabler)
- {
- GlobalLog.log(LogFilter.Core, "Initializing " + this.getClass().getSimpleName());
-
- if(instance == null)
- {
- this.commands = new HashMap();
- this.threadAccumulator = new ArrayList();
- this.invokeCount = 0;
- this.commandEnabler = commandEnabler;
-
- registerAllCommands();
-
- instance = this;
- }
- else
- {
- GlobalLog.error(LogFilter.Core, "You can't have two of the following: " + this.getClass().getSimpleName());
- }
- }
-
- // Registers all the commands for the instance
- public void registerAllCommands()
- {
- this.commands.clear();
-
- // Dev
- this.register(LocCommands.stub("work"), new CommandDoWork(KittyRole.Dev, KittyRating.Safe));
- this.register(LocCommands.stub("shutdown"), new CommandShutdown(KittyRole.Dev, KittyRating.Safe));
- this.register(LocCommands.stub("stats"), new CommandStats(KittyRole.Dev, KittyRating.Safe));
- this.register(LocCommands.stub("invite"), new CommandInvite(KittyRole.Dev, KittyRating.Safe));
- this.register(LocCommands.stub("buildHelp"), new CommandHelpBuilder(KittyRole.Dev, KittyRating.Safe));
- this.register(LocCommands.stub("tweet"), new CommandTweet(KittyRole.Dev, KittyRating.Safe));
- this.register(LocCommands.stub("dbflush"), new CommandDBFlush(KittyRole.Dev, KittyRating.Safe));
- this.register(LocCommands.stub("dbstats"), new CommandDBStats(KittyRole.Dev, KittyRating.Safe));
-
- // Admin
- this.register(LocCommands.stub("rating"), new CommandRating(KittyRole.Admin, KittyRating.Safe));
- this.register(LocCommands.stub("indicator"), new CommandChangeIndicator(KittyRole.Admin, KittyRating.Safe));
-
- // Mod
- this.register(LocCommands.stub("givebeans"), new CommandGiveBeans(KittyRole.Mod, KittyRating.Safe));
- this.register(LocCommands.stub("mod"), new CommandModMain(KittyRole.Mod, KittyRating.Safe));
-
- // General
- this.register(LocCommands.stub("fetch"), new CommandFetch(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("teey"), new CommandTeey(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("perish, thenperish"), new CommandPerish(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("yeet"), new CommandYeet(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("ping"), new CommandPing(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("boop"), new CommandBoop(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("roll"), new CommandRoll(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("choose"), new CommandChoose(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("help"), new CommandHelp(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("info, about"), new CommandInfo(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("wolfram"), new CommandWolfram(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("c++, g++, cplus, cpp"), new CommandColiru(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("java, jdoodle"), new CommandJDoodle(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("beans"), new CommandBeansShow(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("kittyrole"), new CommandRole(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("bet"), new CommandBetBeans(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("map"), new CommandMap(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("rpstart"), new CommandRPStart(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("rpend"), new CommandRPEnd(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("tony, stark, dontfeelgood, dontfeelsogood"), new CommandStark(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("blur"), new CommandBlurry(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("eightball, 8ball"), new CommandEightBall(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("catch"), new CommandCatch(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("bethistory"), new CommandBetHistory(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("crouton"), new CommandCrouton(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("benchmark, bench"), new CommandBenchmark(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("leaderboard"), new CommandLeaderboard(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("color, colour"), new CommandColor(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("remind"), new CommandRemind(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("role"), new CommandGuildRoleMain(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("character"), new CommandCharacterMain(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("raffle"), new CommandRaffleMain(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("poll"), new CommandPollMain(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("music"), new CommandMusicMain(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("defaultdance"), new CommandDefaultDance(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("getsauce"), new CommandGetSauce(KittyRole.General, KittyRating.Safe));
- this.register(LocCommands.stub("tradebeans"), new CommandTradeBeans(KittyRole.General, KittyRating.Safe));
-
- this.register(LocCommands.stub("e6"), new CommandE6(KittyRole.General, KittyRating.Filtered));
- this.register(LocCommands.stub("derpi"), new CommandDerpi(KittyRole.General, KittyRating.Filtered));
- }
-
- // Allows the command manager to keep track of a command. Takes a pair (the un-localized and localzied commands)
- // and the command associated with the localized commands.
- public void register(Pair pair, Command command)
- {
- if(pair == null || pair.Second == null)
- return;
-
- String[] keys = pair.Second.split(",");
-
- for(int i = 0; i < keys.length; ++i)
- {
- String key = keys[i].trim().toLowerCase();
-
- command.registeredNames.add(key);
- Command old = commands.put(key, command);
-
- if(old != null)
- {
- GlobalLog.warn(LogFilter.Core, "Writing over a command with the key " + key);
- return;
- }
-
- GlobalLog.log(LogFilter.Core, "Command registered under key " + key);
- }
- }
-
- // Calls the command but on a whole new thread!
- public boolean invokeOnNewThread(KittyGuild guild, KittyChannel channel, KittyUser user, UserInput input, Response responseContext)
- {
- // This is here to prevent spinning up a thread if this wasn't even a command.
- if(input == null || !input.isValid())
- return false;
-
- // At this point, verify that the command is enabled. If we don't have any info
- // on if it's enabled or not, we assume it's enabled to prevent broken functionality due
- // to formatting or casing issues.
- if(input.key != null && !commandEnabler.isEnabled(input.key))
- return false;
-
- Command command = commands.get(input.key);
- if(command != null)
- {
- // Spin up a thread and begin it. The thread carries the info needed to invoke the command.
- CommandThread newThread = new CommandThread(this, input, guild, channel, user, responseContext);
- threadAccumulator.add(newThread);
- newThread.start();
- return true;
- }
- else
- {
- GlobalLog.warn(LogFilter.Command, "User " + user.name + " tried to invoke command that doesn't exist: " + input.key);
- return false;
- }
- }
-
- // Calls the command specified with the key, providing user information arguments, etc.
- void invoke(KittyGuild guild, KittyChannel channel, KittyUser user, UserInput input, Response responseContext)
- {
- if(input == null || !input.isValid())
- return;
-
- Command command = commands.get(input.key);
- if(command != null)
- {
- ++invokeCount;
- command.invoke(guild, channel, user, input, responseContext);
- }
- }
-
- // Looks up command by name. If it exists, dumps help text, otherwise returns null.
- public String getCommandHelpText(String key)
- {
- Command command = commands.get(key);
-
- if(command != null)
- return "`" + key + "`: " + command.getHelpText();
-
- return null;
- }
-
- // Returns the number of commands sent so far during this program run
- public long getInvokeCount()
- {
- return invokeCount;
- }
-
- // Returns all commands by name
- public ArrayList getAllRegisteredCommands()
- {
- ArrayList cmds = new ArrayList();
- for(Entry entry : commands.entrySet())
- cmds.add(entry.getValue());
-
- return cmds;
- }
-
- // Info about threads running packaged into an object
- public class ThreadData
- {
- public HashMap states = new HashMap();
- }
- public ThreadData dumpThreadData()
- {
- ThreadData data = new ThreadData();
-
- for(int i = 0; i < threadAccumulator.size(); ++i)
- {
- Thread.State state = threadAccumulator.get(i).getState();
- Integer num = data.states.get(state);
-
- if(num == null)
- num = 0;
-
- data.states.put(state, num + 1);
- }
-
- return data;
- }
-}
+package core;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.Map.Entry;
+
+import commands.characters.CommandCharacterMain;
+import commands.general.*;
+import commands.guildrole.CommandGuildRoleMain;
+import commands.mod.CommandModMain;
+import commands.music.CommandMusicMain;
+import commands.poll.CommandPollMain;
+import commands.raffle.CommandRaffleMain;
+import dataStructures.*;
+import utils.GlobalLog;
+import utils.LogFilter;
+
+public class CommandManager
+{
+ // Variables
+ private HashMap commands;
+ private ArrayList threadAccumulator;
+ private CommandEnabler commandEnabler;
+ private long invokeCount;
+
+ // Singleton
+ public static CommandManager instance;
+
+ // Default Constructor
+ public CommandManager(CommandEnabler commandEnabler)
+ {
+ GlobalLog.log(LogFilter.Core, "Initializing " + this.getClass().getSimpleName());
+
+ if(instance == null)
+ {
+ this.commands = new HashMap();
+ this.threadAccumulator = new ArrayList();
+ this.invokeCount = 0;
+ this.commandEnabler = commandEnabler;
+
+ registerAllCommands();
+
+ instance = this;
+ }
+ else
+ {
+ GlobalLog.error(LogFilter.Core, "You can't have two of the following: " + this.getClass().getSimpleName());
+ }
+ }
+
+ // Registers all the commands for the instance
+ public void registerAllCommands()
+ {
+ this.commands.clear();
+
+ // Dev
+ this.register(LocCommands.stub("work"), new CommandDoWork(KittyRole.Dev, KittyRating.Safe));
+ this.register(LocCommands.stub("shutdown"), new CommandShutdown(KittyRole.Dev, KittyRating.Safe));
+ this.register(LocCommands.stub("stats"), new CommandStats(KittyRole.Dev, KittyRating.Safe));
+ this.register(LocCommands.stub("invite"), new CommandInvite(KittyRole.Dev, KittyRating.Safe));
+ this.register(LocCommands.stub("buildHelp"), new CommandHelpBuilder(KittyRole.Dev, KittyRating.Safe));
+ this.register(LocCommands.stub("tweet"), new CommandTweet(KittyRole.Dev, KittyRating.Safe));
+ this.register(LocCommands.stub("dbflush"), new CommandDBFlush(KittyRole.Dev, KittyRating.Safe));
+ this.register(LocCommands.stub("dbstats"), new CommandDBStats(KittyRole.Dev, KittyRating.Safe));
+
+ // Admin
+ this.register(LocCommands.stub("rating"), new CommandRating(KittyRole.Admin, KittyRating.Safe));
+ this.register(LocCommands.stub("indicator"), new CommandChangeIndicator(KittyRole.Admin, KittyRating.Safe));
+
+ // Mod
+ this.register(LocCommands.stub("givebeans"), new CommandGiveBeans(KittyRole.Mod, KittyRating.Safe));
+ this.register(LocCommands.stub("mod"), new CommandModMain(KittyRole.Mod, KittyRating.Safe));
+
+ // General
+ this.register(LocCommands.stub("fetch"), new CommandFetch(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("teey"), new CommandTeey(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("perish, thenperish"), new CommandPerish(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("yeet"), new CommandYeet(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("ping"), new CommandPing(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("boop"), new CommandBoop(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("roll"), new CommandRoll(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("choose"), new CommandChoose(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("help"), new CommandHelp(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("info, about"), new CommandInfo(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("wolfram"), new CommandWolfram(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("c++, g++, cplus, cpp"), new CommandColiru(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("java, jdoodle"), new CommandJDoodle(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("beans"), new CommandBeansShow(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("kittyrole"), new CommandRole(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("bet"), new CommandBetBeans(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("map"), new CommandMap(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("rpstart"), new CommandRPStart(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("rpend"), new CommandRPEnd(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("tony, stark, dontfeelgood, dontfeelsogood"), new CommandStark(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("blur"), new CommandBlurry(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("eightball, 8ball"), new CommandEightBall(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("catch"), new CommandCatch(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("bethistory"), new CommandBetHistory(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("crouton"), new CommandCrouton(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("benchmark, bench"), new CommandBenchmark(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("leaderboard"), new CommandLeaderboard(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("color, colour"), new CommandColor(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("remind"), new CommandRemind(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("role"), new CommandGuildRoleMain(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("character"), new CommandCharacterMain(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("raffle"), new CommandRaffleMain(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("poll"), new CommandPollMain(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("music"), new CommandMusicMain(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("defaultdance"), new CommandDefaultDance(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("getsauce"), new CommandGetSauce(KittyRole.General, KittyRating.Safe));
+ this.register(LocCommands.stub("tradebeans, trade"), new CommandTradeBeans(KittyRole.General, KittyRating.Safe));
+
+ this.register(LocCommands.stub("e6"), new CommandE6(KittyRole.General, KittyRating.Filtered));
+ this.register(LocCommands.stub("derpi"), new CommandDerpi(KittyRole.General, KittyRating.Filtered));
+ }
+
+ // Allows the command manager to keep track of a command. Takes a pair (the un-localized and localzied commands)
+ // and the command associated with the localized commands.
+ public void register(Pair pair, Command command)
+ {
+ if(pair == null || pair.Second == null)
+ return;
+
+ String[] keys = pair.Second.split(",");
+
+ for(int i = 0; i < keys.length; ++i)
+ {
+ String key = keys[i].trim().toLowerCase();
+
+ command.registeredNames.add(key);
+ Command old = commands.put(key, command);
+
+ if(old != null)
+ {
+ GlobalLog.warn(LogFilter.Core, "Writing over a command with the key " + key);
+ return;
+ }
+
+ GlobalLog.log(LogFilter.Core, "Command registered under key " + key);
+ }
+ }
+
+ // Calls the command but on a whole new thread!
+ public boolean invokeOnNewThread(KittyGuild guild, KittyChannel channel, KittyUser user, UserInput input, Response responseContext)
+ {
+ // This is here to prevent spinning up a thread if this wasn't even a command.
+ if(input == null || !input.isValid())
+ return false;
+
+ // At this point, verify that the command is enabled. If we don't have any info
+ // on if it's enabled or not, we assume it's enabled to prevent broken functionality due
+ // to formatting or casing issues.
+ if(input.key != null && !commandEnabler.isEnabled(input.key))
+ return false;
+
+ Command command = commands.get(input.key);
+ if(command != null)
+ {
+ // Spin up a thread and begin it. The thread carries the info needed to invoke the command.
+ CommandThread newThread = new CommandThread(this, input, guild, channel, user, responseContext);
+ threadAccumulator.add(newThread);
+ newThread.start();
+ return true;
+ }
+ else
+ {
+ GlobalLog.warn(LogFilter.Command, "User " + user.name + " tried to invoke command that doesn't exist: " + input.key);
+ return false;
+ }
+ }
+
+ // Calls the command specified with the key, providing user information arguments, etc.
+ void invoke(KittyGuild guild, KittyChannel channel, KittyUser user, UserInput input, Response responseContext)
+ {
+ if(input == null || !input.isValid())
+ return;
+
+ Command command = commands.get(input.key);
+ if(command != null)
+ {
+ ++invokeCount;
+ command.invoke(guild, channel, user, input, responseContext);
+ }
+ }
+
+ // Looks up command by name. If it exists, dumps help text, otherwise returns null.
+ public String getCommandHelpText(String key)
+ {
+ Command command = commands.get(key);
+
+ if(command != null)
+ return "`" + key + "`: " + command.getHelpText();
+
+ return null;
+ }
+
+ // Returns the number of commands sent so far during this program run
+ public long getInvokeCount()
+ {
+ return invokeCount;
+ }
+
+ // Returns all commands by name
+ public ArrayList getAllRegisteredCommands()
+ {
+ ArrayList cmds = new ArrayList();
+ for(Entry entry : commands.entrySet())
+ cmds.add(entry.getValue());
+
+ return cmds;
+ }
+
+ // Info about threads running packaged into an object
+ public class ThreadData
+ {
+ public HashMap states = new HashMap();
+ }
+ public ThreadData dumpThreadData()
+ {
+ ThreadData data = new ThreadData();
+
+ for(int i = 0; i < threadAccumulator.size(); ++i)
+ {
+ Thread.State state = threadAccumulator.get(i).getState();
+ Integer num = data.states.get(state);
+
+ if(num == null)
+ num = 0;
+
+ data.states.put(state, num + 1);
+ }
+
+ return data;
+ }
+}
diff --git a/src/network/NetworkTheColorAPI.java b/src/network/NetworkTheColorAPI.java
index 5f2e2b2..07e9b35 100644
--- a/src/network/NetworkTheColorAPI.java
+++ b/src/network/NetworkTheColorAPI.java
@@ -75,7 +75,21 @@ public class NetworkTheColorAPI
{
try
{
- hex = hex.replace("#", "");
+ hex = hex.replace("#", "").trim();
+ String hexUpper = hex.toUpperCase();
+
+ // Verify the number is hex.
+ for(int i = 0; i < hexUpper.length(); ++i)
+ {
+ char current = hexUpper.charAt(i);
+ Boolean isValidNum = current >= '0' && current <= '9';
+ Boolean isValidChar = current >= 'A' && current <= 'F';
+
+ // If it's not a valid character or a valid number, return null/
+ if(!isValidNum && !isValidChar)
+ return null;
+ }
+
String response = HTTPUtils.sendGETRequest("https://www.thecolorapi.com/id?hex=" + hex);
ColorData data = jsonParser.fromJson(response, ColorData.class);