77 lines
3.1 KiB
Java
77 lines
3.1 KiB
Java
package moe.oko.Kiafumi.command;
|
|
|
|
import com.google.common.reflect.ClassPath;
|
|
|
|
import java.lang.reflect.Constructor;
|
|
import java.lang.reflect.InvocationTargetException;
|
|
import java.util.ArrayList;
|
|
import java.util.List;
|
|
import java.util.Set;
|
|
import java.util.stream.Collectors;
|
|
|
|
import static moe.oko.Kiafumi.util.LoggingManager.error;
|
|
import static moe.oko.Kiafumi.util.LoggingManager.info;
|
|
import static moe.oko.Kiafumi.util.LoggingManager.debug;
|
|
|
|
/**
|
|
* CommandRegistrar Class
|
|
* Used for easy command package loading, we use this to avoid having 20 lines of list.add() methods.
|
|
* @author Kay
|
|
*/
|
|
public class CommandRegistrar {
|
|
|
|
/**
|
|
* Locates all classes that contain the package name provided. Use CAREFULLY.
|
|
* @param packageName - the name of the package to look for
|
|
* @return - A set of classes that contain that package name.
|
|
*/
|
|
public Set<Class> findAllClassesContaining(String packageName) {
|
|
try {
|
|
return ClassPath.from(ClassLoader.getSystemClassLoader())
|
|
.getAllClasses()
|
|
.stream()
|
|
.filter(clazz -> clazz.getPackageName()
|
|
.contains(packageName))
|
|
.map(clazz -> clazz.load())
|
|
.collect(Collectors.toSet());
|
|
} catch (Exception ex) {
|
|
error("Failed to load classes containing " + packageName + ", check stack.");
|
|
ex.printStackTrace();
|
|
return null;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Utilizes findAllClassesContaining() to find all command classes and return them in a simple manner.
|
|
* @return - The CommandClass's located.
|
|
*/
|
|
public List<CommandClass> getCommandClasses() {
|
|
try {
|
|
// TODO have this check the classpath that we're under and have it scan *that* instead of hard-coding it to only be moe.oko.Kiafumi path.
|
|
var classes = findAllClassesContaining("moe.oko.Kiafumi.command");
|
|
List<CommandClass> commands = new ArrayList<>();
|
|
debug("Discovered " + classes.size() + " classes containing moe.oko.Kiafumi.command in package class.");
|
|
for (Class clazz : classes) {
|
|
for (Constructor cnstr : clazz.getConstructors()) {
|
|
try {
|
|
var obj = cnstr.newInstance(); // making an attempt.
|
|
if (obj instanceof CommandClass) {
|
|
debug("Loading command class %green(" + cnstr.getName() + ").");
|
|
commands.add((CommandClass) obj);
|
|
}
|
|
} catch (InstantiationException ex) {
|
|
// Ignore, this is just us trying to load the CommandClass abstract class.
|
|
}
|
|
}
|
|
}
|
|
info("Loaded [" + commands.size() + "] command classes.");
|
|
return commands;
|
|
} catch (IllegalAccessException | InvocationTargetException exception) {
|
|
// Now we don't ignore, this is a core issue.
|
|
exception.printStackTrace();
|
|
error("Failure in command class loading.");
|
|
return null;
|
|
}
|
|
}
|
|
}
|