From 2647a1f0b4b7708f88f3cc2d50ca88026250e5fd Mon Sep 17 00:00:00 2001 From: tueem Date: Wed, 26 Mar 2025 19:26:57 +0100 Subject: [PATCH 01/18] refactor(registry): outsource entry discovery to seperate method --- .../marinara/registry/InteractionEntry.java | 24 ++++++++++++++++--- .../registry/InteractionRegistry.java | 13 ++-------- 2 files changed, 23 insertions(+), 14 deletions(-) diff --git a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionEntry.java b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionEntry.java index 2d2868a..ec7a674 100644 --- a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionEntry.java +++ b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionEntry.java @@ -1,6 +1,8 @@ package net.tomatentum.marinara.registry; +import java.util.Arrays; import java.util.HashSet; +import java.util.Optional; import java.util.Set; import org.slf4j.Logger; @@ -11,6 +13,17 @@ import net.tomatentum.marinara.interaction.methods.InteractionMethod; import net.tomatentum.marinara.util.LoggerUtil; public class InteractionEntry { + + public static InteractionEntry findEntry(Set entries, InteractionIdentifier identifier) { + Optional oentry = entries.stream() + .filter(i -> i.identifier().equals(identifier)) + .findFirst(); + + InteractionEntry entry = oentry.orElse(new InteractionEntry(identifier)); + if (oentry.isEmpty()) entries.add(entry); + return entry; + } + private InteractionIdentifier identifier; private Set methods; @@ -22,11 +35,16 @@ public class InteractionEntry { } public InteractionEntry addMethod(InteractionMethod method) { - if (!method.identifier().equals(this.identifier)) - throw new IllegalArgumentException("Method's identifier did not match the entry's identifier"); + Optional methodId = Arrays.stream(method.identifier()) + .filter(x -> x.name().equals(identifier().name())) + .findFirst(); + + if (methodId.isEmpty()) + throw new IllegalArgumentException("Method's identifiers did not contain the entry's identifier"); this.methods.add(method); - InteractionIdentifier.tryAddDescriptions(identifier, method.identifier()); + InteractionIdentifier.tryAddDescriptions(identifier, methodId.get()); + logger.debug("Added method {} to entry {}", method.method().getName(), this.identifier); return this; } diff --git a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java index be5678d..d1791dc 100644 --- a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java +++ b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java @@ -4,7 +4,6 @@ import java.lang.reflect.Method; import java.util.Arrays; import java.util.HashSet; import java.util.List; -import java.util.Optional; import java.util.Set; import org.slf4j.Logger; @@ -32,20 +31,12 @@ public class InteractionRegistry { this.identifierProvider = marinara.getWrapper().createIdentifierProvider(); marinara.getWrapper().subscribeInteractions(this::handle); } - - /* - * TODO: Maybe relocate InteractionEntry checking to another class with description merging. - */ + public void addInteractions(InteractionHandler interactionHandler) { for (Method method : interactionHandler.getClass().getMethods()) { InteractionMethod iMethod = InteractionMethod.create(method, interactionHandler, marinara); if (iMethod != null) { - Optional oentry = this.interactions.stream() - .filter(i -> i.identifier().equals(iMethod.identifier())) - .findFirst(); - - InteractionEntry entry = oentry.orElse(new InteractionEntry(iMethod.identifier())).addMethod(iMethod); - if (oentry.isEmpty()) this.interactions.add(entry); + InteractionEntry.findEntry(interactions, iMethod.identifier()).addMethod(iMethod); logger.debug("Added {} method from {}", iMethod.method().getName(), interactionHandler.getClass().getSimpleName()); } } -- 2.47.2 From 0590789359fd6b820411842dc1693e98b11066ca Mon Sep 17 00:00:00 2001 From: tueem Date: Wed, 26 Mar 2025 19:46:44 +0100 Subject: [PATCH 02/18] fix: compile error --- .../marinara/registry/InteractionEntry.java | 11 ++++------- 1 file changed, 4 insertions(+), 7 deletions(-) diff --git a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionEntry.java b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionEntry.java index ec7a674..d0e56db 100644 --- a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionEntry.java +++ b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionEntry.java @@ -1,6 +1,5 @@ package net.tomatentum.marinara.registry; -import java.util.Arrays; import java.util.HashSet; import java.util.Optional; import java.util.Set; @@ -35,15 +34,13 @@ public class InteractionEntry { } public InteractionEntry addMethod(InteractionMethod method) { - Optional methodId = Arrays.stream(method.identifier()) - .filter(x -> x.name().equals(identifier().name())) - .findFirst(); + InteractionIdentifier identifier = method.identifier(); - if (methodId.isEmpty()) - throw new IllegalArgumentException("Method's identifiers did not contain the entry's identifier"); + if (this.identifier().equals(identifier)) + throw new IllegalArgumentException("Method's identifier did not equal the entry's identifier"); this.methods.add(method); - InteractionIdentifier.tryAddDescriptions(identifier, methodId.get()); + InteractionIdentifier.tryAddDescriptions(identifier, identifier); logger.debug("Added method {} to entry {}", method.method().getName(), this.identifier); return this; } -- 2.47.2 From 0973016a74f2095ac1e7708ef66b2df75363adf2 Mon Sep 17 00:00:00 2001 From: tueem Date: Wed, 26 Mar 2025 22:22:39 +0100 Subject: [PATCH 03/18] refactor(interaction): seperate InteractionMethod to ReflectedMethod --- .../methods/ButtonInteractionMethod.java | 9 ++- .../AutoCompleteInteractionMethod.java | 4 +- .../methods/InteractionMethod.java | 74 +++++------------- .../SlashCommandInteractionMethod.java | 4 +- .../marinara/util/ReflectedMethod.java | 75 +++++++++++++++++++ 5 files changed, 102 insertions(+), 64 deletions(-) rename lib/src/main/java/net/tomatentum/marinara/interaction/{ => components}/methods/ButtonInteractionMethod.java (75%) create mode 100644 lib/src/main/java/net/tomatentum/marinara/util/ReflectedMethod.java diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/ButtonInteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/components/methods/ButtonInteractionMethod.java similarity index 75% rename from lib/src/main/java/net/tomatentum/marinara/interaction/methods/ButtonInteractionMethod.java rename to lib/src/main/java/net/tomatentum/marinara/interaction/components/methods/ButtonInteractionMethod.java index ec011a4..08cfaa8 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/ButtonInteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/components/methods/ButtonInteractionMethod.java @@ -1,4 +1,4 @@ -package net.tomatentum.marinara.interaction.methods; +package net.tomatentum.marinara.interaction.components.methods; import java.lang.reflect.Method; @@ -6,6 +6,7 @@ import net.tomatentum.marinara.Marinara; import net.tomatentum.marinara.interaction.InteractionHandler; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; +import net.tomatentum.marinara.interaction.methods.InteractionMethod; import net.tomatentum.marinara.parser.AnnotationParser; import net.tomatentum.marinara.parser.ButtonParser; @@ -13,14 +14,14 @@ public class ButtonInteractionMethod extends InteractionMethod { private String customId; - ButtonInteractionMethod(Method method, InteractionHandler handler, Marinara marinara) { + public ButtonInteractionMethod(Method method, InteractionHandler handler, Marinara marinara) { super(method, handler, marinara); } @Override - public AnnotationParser[] parsers() { + public AnnotationParser[] provideParsers() { return new AnnotationParser[] { - new ButtonParser(method, (x) -> { this.customId = x; } ) + new ButtonParser(method(), (x) -> { this.customId = x; } ) }; } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java index a5d53b4..356d9b5 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java @@ -20,9 +20,9 @@ public class AutoCompleteInteractionMethod extends InteractionMethod { } @Override - public AnnotationParser[] parsers() { + public AnnotationParser[] provideParsers() { return new AnnotationParser[] { - new SlashCommandParser(method, true, (x) -> { this.interactionIdentifier = x; } ) + new SlashCommandParser(method(), true, (x) -> { this.interactionIdentifier = x; } ) }; } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/InteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/InteractionMethod.java index 9fdda56..d68d513 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/InteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/InteractionMethod.java @@ -1,14 +1,9 @@ package net.tomatentum.marinara.interaction.methods; -import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; -import java.security.InvalidParameterException; import java.util.ArrayList; -import java.util.Arrays; import java.util.List; -import org.slf4j.Logger; - import net.tomatentum.marinara.Marinara; import net.tomatentum.marinara.checks.AppliedCheck; import net.tomatentum.marinara.interaction.InteractionHandler; @@ -16,13 +11,13 @@ import net.tomatentum.marinara.interaction.annotation.AutoComplete; import net.tomatentum.marinara.interaction.annotation.Button; import net.tomatentum.marinara.interaction.commands.annotation.SlashCommand; import net.tomatentum.marinara.interaction.commands.annotation.SubCommand; +import net.tomatentum.marinara.interaction.components.methods.ButtonInteractionMethod; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; import net.tomatentum.marinara.parser.AnnotationParser; import net.tomatentum.marinara.parser.InteractionCheckParser; -import net.tomatentum.marinara.util.LoggerUtil; -import net.tomatentum.marinara.util.ReflectionUtil; +import net.tomatentum.marinara.util.ReflectedMethod; -public abstract class InteractionMethod { +public abstract class InteractionMethod extends ReflectedMethod { public static InteractionMethod create(Method method, InteractionHandler handler, Marinara marinara) { if (method.isAnnotationPresent(AutoComplete.class)) @@ -34,72 +29,39 @@ public abstract class InteractionMethod { return null; } - protected Method method; - protected InteractionHandler handler; protected Marinara marinara; - protected List parsers; protected List appliedChecks; - private Logger logger = LoggerUtil.getLogger(getClass()); - protected InteractionMethod( Method method, InteractionHandler handler, Marinara marinara ) { - if (!Arrays.asList(handler.getClass().getMethods()).contains(method)) - throw new InvalidParameterException("Method does not apply to specified handler"); - - this.method = method; - this.handler = handler; + super(method, handler); this.marinara = marinara; - this.parsers = new ArrayList<>(Arrays.asList(parsers())); this.appliedChecks = new ArrayList<>(); - - parsers.add(new InteractionCheckParser(method, appliedChecks::add, marinara.getCheckRegistry())); - - parsers.stream().forEach(AnnotationParser::parse); } - public void run(Object context) { + @Override + public AnnotationParser[] provideParsers() { + return new AnnotationParser[] { + new InteractionCheckParser(method(), appliedChecks::add, marinara.getCheckRegistry()) + }; + } + + @Override + public Object run(Object context) { + Object result = null; if (this.appliedChecks.stream().filter(x -> !x.pre(context)).count() > 0) - return; + return null; - method.setAccessible(true); - try { - method.invoke(handler, getParameters(context)); - }catch (IllegalAccessException | InvocationTargetException ex) { - logger.error("InteractionMethod failed to run", ex); - } + result = super.run(context); this.appliedChecks.forEach(x -> x.post(context)); + + return result; } - public abstract AnnotationParser[] parsers(); - - public abstract Object getParameter(Object context, int index); - public abstract InteractionIdentifier identifier(); - public Method method() { - return method; - } - - private Object[] getParameters(Object context) { - int parameterCount = method.getParameterCount(); - List parameters = new ArrayList<>(); - - for (int i = 0; i < parameterCount; i++) { - Object parameter; - if (i == 0) { - parameter = context; - }else - parameter = getParameter(context, i-1); - - logger.trace("Found parameter {}={} for method {}", parameter != null ? parameter.getClass().toString() : " ", parameter, ReflectionUtil.getFullMethodName(method)); - parameters.add(parameter); - } - return parameters.toArray(); - } - } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java index d89d709..c7edd47 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java @@ -18,9 +18,9 @@ public class SlashCommandInteractionMethod extends InteractionMethod { } @Override - public AnnotationParser[] parsers() { + public AnnotationParser[] provideParsers() { return new AnnotationParser[] { - new SlashCommandParser(method, false, (x) -> { this.interactionIdentifier = x; } ) + new SlashCommandParser(method(), false, (x) -> { this.interactionIdentifier = x; } ) }; } diff --git a/lib/src/main/java/net/tomatentum/marinara/util/ReflectedMethod.java b/lib/src/main/java/net/tomatentum/marinara/util/ReflectedMethod.java new file mode 100644 index 0000000..af5df50 --- /dev/null +++ b/lib/src/main/java/net/tomatentum/marinara/util/ReflectedMethod.java @@ -0,0 +1,75 @@ +package net.tomatentum.marinara.util; + +import java.lang.reflect.InvocationTargetException; +import java.lang.reflect.Method; +import java.security.InvalidParameterException; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.List; + +import org.slf4j.Logger; + +import net.tomatentum.marinara.parser.AnnotationParser; + +public abstract class ReflectedMethod { + + private Logger logger = LoggerUtil.getLogger(getClass()); + + private Method method; + private Object containingObject; + protected List parsers; + + public ReflectedMethod(Method method, Object containingObject) { + if (!Arrays.asList(containingObject.getClass().getMethods()).contains(method)) + throw new InvalidParameterException("Method does not apply to specified handler"); + this.method = method; + this.containingObject = containingObject; + this.parsers = new ArrayList<>(Arrays.asList(provideParsers())); + + this.parsers.stream().forEach(AnnotationParser::parse); + } + + public abstract Object getParameter(Object context, int index); + + public abstract AnnotationParser[] provideParsers(); + + public Object run(Object context) { + method.setAccessible(true); + try { + return method.invoke(containingObject, getParameters(context)); + }catch (IllegalAccessException | InvocationTargetException ex) { + logger.error("ReflectedMethod failed to run", ex); + return null; + } + } + + public Method method() { + return this.method; + } + + public Object containingObject() { + return this.containingObject; + } + + public List parsers() { + return this.parsers; + } + + private Object[] getParameters(Object context) { + int parameterCount = method.getParameterCount(); + List parameters = new ArrayList<>(); + + for (int i = 0; i < parameterCount; i++) { + Object parameter; + if (i == 0) { + parameter = context; + }else + parameter = getParameter(context, i-1); + + logger.trace("Found parameter {}={} for method {}", parameter != null ? parameter.getClass().toString() : " ", parameter, ReflectionUtil.getFullMethodName(method)); + parameters.add(parameter); + } + return parameters.toArray(); + } + +} -- 2.47.2 From 8495659364e188a0d8c8a874c30a44cea70ba50b Mon Sep 17 00:00:00 2001 From: tueem Date: Sat, 29 Mar 2025 18:37:51 +0100 Subject: [PATCH 04/18] fix(registry): fix logic error in InteractionEntry identifier checking and fix InteractionIdentifier#equals to actually recursively check parent identifiers --- .../marinara/interaction/ident/InteractionIdentifier.java | 2 +- .../java/net/tomatentum/marinara/registry/InteractionEntry.java | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/ident/InteractionIdentifier.java b/lib/src/main/java/net/tomatentum/marinara/interaction/ident/InteractionIdentifier.java index 7207738..9ef1298 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/ident/InteractionIdentifier.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/ident/InteractionIdentifier.java @@ -80,7 +80,7 @@ public class InteractionIdentifier { return false; if (!name().equals(ident.name())) return false; - return Objects.equals(ident, obj); + return Objects.equals(parent(), ident.parent()); } @Override diff --git a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionEntry.java b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionEntry.java index d0e56db..310aa8b 100644 --- a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionEntry.java +++ b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionEntry.java @@ -36,7 +36,7 @@ public class InteractionEntry { public InteractionEntry addMethod(InteractionMethod method) { InteractionIdentifier identifier = method.identifier(); - if (this.identifier().equals(identifier)) + if (!this.identifier().equals(identifier)) throw new IllegalArgumentException("Method's identifier did not equal the entry's identifier"); this.methods.add(method); -- 2.47.2 From 8a3cde52fd9dc4da95d190888e81bbe8d44ea615 Mon Sep 17 00:00:00 2001 From: tueem Date: Sat, 29 Mar 2025 18:49:26 +0100 Subject: [PATCH 05/18] refactor(interaction): implement Factory pattern for all Interaction- and ReflectedMethods --- .../net/tomatentum/marinara/Marinara.java | 18 ++++-- .../methods/ButtonInteractionMethod.java | 36 ++++++++--- .../AutoCompleteInteractionMethod.java | 36 ++++++++--- .../methods/InteractionMethod.java | 45 +++++++------ .../SlashCommandInteractionMethod.java | 38 ++++++++--- .../{util => reflection}/ReflectedMethod.java | 15 +---- .../reflection/ReflectedMethodFactory.java | 19 ++++++ .../ReflectedMethodFactoryImpl.java | 63 +++++++++++++++++++ .../registry/InteractionRegistry.java | 16 ++++- 9 files changed, 219 insertions(+), 67 deletions(-) rename lib/src/main/java/net/tomatentum/marinara/{util => reflection}/ReflectedMethod.java (82%) create mode 100644 lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactory.java create mode 100644 lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactoryImpl.java diff --git a/lib/src/main/java/net/tomatentum/marinara/Marinara.java b/lib/src/main/java/net/tomatentum/marinara/Marinara.java index f53a7ae..31b0786 100644 --- a/lib/src/main/java/net/tomatentum/marinara/Marinara.java +++ b/lib/src/main/java/net/tomatentum/marinara/Marinara.java @@ -2,6 +2,8 @@ package net.tomatentum.marinara; import org.slf4j.Logger; +import net.tomatentum.marinara.reflection.ReflectedMethodFactory; +import net.tomatentum.marinara.reflection.ReflectedMethodFactoryImpl; import net.tomatentum.marinara.registry.InteractionCheckRegistry; import net.tomatentum.marinara.registry.InteractionRegistry; import net.tomatentum.marinara.util.LoggerUtil; @@ -15,26 +17,32 @@ public class Marinara { return new Marinara(wrapper); } + private LibraryWrapper wrapper; + private ReflectedMethodFactory reflectedMethodFactory; private InteractionRegistry registry; private InteractionCheckRegistry checkRegistry; - private LibraryWrapper wrapper; private Marinara(LibraryWrapper wrapper) { this.wrapper = wrapper; + this.reflectedMethodFactory = new ReflectedMethodFactoryImpl(this); this.registry = new InteractionRegistry(this); this.checkRegistry = new InteractionCheckRegistry(); logger.info("Marinara loaded successfully!"); } + public LibraryWrapper getWrapper() { + return this.wrapper; + } + public InteractionRegistry getRegistry() { - return registry; + return this.registry; } public InteractionCheckRegistry getCheckRegistry() { - return checkRegistry; + return this.checkRegistry; } - public LibraryWrapper getWrapper() { - return wrapper; + public ReflectedMethodFactory getReflectedMethodFactory() { + return this.reflectedMethodFactory; } } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/components/methods/ButtonInteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/components/methods/ButtonInteractionMethod.java index 08cfaa8..82e25a6 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/components/methods/ButtonInteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/components/methods/ButtonInteractionMethod.java @@ -1,30 +1,26 @@ package net.tomatentum.marinara.interaction.components.methods; import java.lang.reflect.Method; +import java.util.List; import net.tomatentum.marinara.Marinara; import net.tomatentum.marinara.interaction.InteractionHandler; import net.tomatentum.marinara.interaction.InteractionType; +import net.tomatentum.marinara.interaction.annotation.Button; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; import net.tomatentum.marinara.interaction.methods.InteractionMethod; import net.tomatentum.marinara.parser.AnnotationParser; import net.tomatentum.marinara.parser.ButtonParser; +import net.tomatentum.marinara.reflection.ReflectedMethod; public class ButtonInteractionMethod extends InteractionMethod { private String customId; - public ButtonInteractionMethod(Method method, InteractionHandler handler, Marinara marinara) { + private ButtonInteractionMethod(Method method, InteractionHandler handler, Marinara marinara) { super(method, handler, marinara); } - @Override - public AnnotationParser[] provideParsers() { - return new AnnotationParser[] { - new ButtonParser(method(), (x) -> { this.customId = x; } ) - }; - } - @Override public Object getParameter(Object context, int index) { Class type = method().getParameterTypes()[index+1]; @@ -40,4 +36,28 @@ public class ButtonInteractionMethod extends InteractionMethod { .build(); } + public static class Factory extends InteractionMethod.Factory { + + @Override + public ReflectedMethod produce(Marinara marinara, Method method, Object containingObject) { + if (!method.isAnnotationPresent(Button.class) || + !(containingObject instanceof InteractionHandler) + ) + return null; + + return new ButtonInteractionMethod(method, (InteractionHandler) containingObject, marinara); + } + + @Override + public void addParser(ReflectedMethod method, List parser) { + super.addParser(method, parser); + + ButtonInteractionMethod imethod = (ButtonInteractionMethod) method; + parser.add( + new ButtonParser(method.method(), x -> imethod.customId = x) + ); + } + + } + } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java index 356d9b5..c1b6477 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java @@ -1,31 +1,27 @@ package net.tomatentum.marinara.interaction.methods; import java.lang.reflect.Method; +import java.util.List; import net.tomatentum.marinara.Marinara; import net.tomatentum.marinara.interaction.InteractionHandler; +import net.tomatentum.marinara.interaction.annotation.AutoComplete; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; import net.tomatentum.marinara.parser.AnnotationParser; import net.tomatentum.marinara.parser.SlashCommandParser; +import net.tomatentum.marinara.reflection.ReflectedMethod; public class AutoCompleteInteractionMethod extends InteractionMethod { private InteractionIdentifier interactionIdentifier; - public AutoCompleteInteractionMethod(Method method, + private AutoCompleteInteractionMethod(Method method, InteractionHandler handler, Marinara marinara ) { super(method, handler, marinara); } - @Override - public AnnotationParser[] provideParsers() { - return new AnnotationParser[] { - new SlashCommandParser(method(), true, (x) -> { this.interactionIdentifier = x; } ) - }; - } - @Override public Object getParameter(Object context, int index) { Class type = method().getParameterTypes()[index+1]; @@ -40,5 +36,29 @@ public class AutoCompleteInteractionMethod extends InteractionMethod { public InteractionIdentifier identifier() { return interactionIdentifier; } + + public static class Factory extends InteractionMethod.Factory { + + @Override + public ReflectedMethod produce(Marinara marinara, Method method, Object containingObject) { + if (!method.isAnnotationPresent(AutoComplete.class) || + !(containingObject instanceof InteractionHandler) + ) + return null; + + return new AutoCompleteInteractionMethod(method, (InteractionHandler) containingObject, marinara); + } + + @Override + public void addParser(ReflectedMethod method, List parser) { + super.addParser(method, parser); + + AutoCompleteInteractionMethod imethod = (AutoCompleteInteractionMethod) method; + parser.add( + new SlashCommandParser(method.method(), true, x -> imethod.interactionIdentifier = x) + ); + } + + } } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/InteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/InteractionMethod.java index d68d513..2e56a7e 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/InteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/InteractionMethod.java @@ -7,28 +7,14 @@ import java.util.List; import net.tomatentum.marinara.Marinara; import net.tomatentum.marinara.checks.AppliedCheck; import net.tomatentum.marinara.interaction.InteractionHandler; -import net.tomatentum.marinara.interaction.annotation.AutoComplete; -import net.tomatentum.marinara.interaction.annotation.Button; -import net.tomatentum.marinara.interaction.commands.annotation.SlashCommand; -import net.tomatentum.marinara.interaction.commands.annotation.SubCommand; -import net.tomatentum.marinara.interaction.components.methods.ButtonInteractionMethod; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; import net.tomatentum.marinara.parser.AnnotationParser; import net.tomatentum.marinara.parser.InteractionCheckParser; -import net.tomatentum.marinara.util.ReflectedMethod; +import net.tomatentum.marinara.reflection.ReflectedMethod; +import net.tomatentum.marinara.reflection.ReflectedMethodFactory; public abstract class InteractionMethod extends ReflectedMethod { - public static InteractionMethod create(Method method, InteractionHandler handler, Marinara marinara) { - if (method.isAnnotationPresent(AutoComplete.class)) - return new AutoCompleteInteractionMethod(method, handler, marinara); - if (method.isAnnotationPresent(SlashCommand.class) || method.isAnnotationPresent(SubCommand.class)) - return new SlashCommandInteractionMethod(method, handler, marinara); - if (method.isAnnotationPresent(Button.class)) - return new ButtonInteractionMethod(method, handler, marinara); - return null; - } - protected Marinara marinara; protected List appliedChecks; @@ -41,13 +27,6 @@ public abstract class InteractionMethod extends ReflectedMethod { this.marinara = marinara; this.appliedChecks = new ArrayList<>(); } - - @Override - public AnnotationParser[] provideParsers() { - return new AnnotationParser[] { - new InteractionCheckParser(method(), appliedChecks::add, marinara.getCheckRegistry()) - }; - } @Override public Object run(Object context) { @@ -64,4 +43,24 @@ public abstract class InteractionMethod extends ReflectedMethod { public abstract InteractionIdentifier identifier(); + public Marinara marinara() { + return this.marinara; + } + + public List appliedChecks() { + return this.appliedChecks; + } + + public static abstract class Factory implements ReflectedMethodFactory.Factory { + + @Override + public void addParser(ReflectedMethod method, List parser) { + InteractionMethod imethod = (InteractionMethod) method; + parser.add( + new InteractionCheckParser(method.method(), imethod.appliedChecks::add, imethod.marinara().getCheckRegistry()) + ); + } + + } + } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java index c7edd47..a0adb74 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java @@ -1,29 +1,26 @@ package net.tomatentum.marinara.interaction.methods; import java.lang.reflect.Method; +import java.util.List; import net.tomatentum.marinara.Marinara; import net.tomatentum.marinara.interaction.InteractionHandler; +import net.tomatentum.marinara.interaction.commands.annotation.SlashCommand; +import net.tomatentum.marinara.interaction.commands.annotation.SubCommand; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; import net.tomatentum.marinara.interaction.ident.SlashCommandIdentifier; import net.tomatentum.marinara.parser.AnnotationParser; import net.tomatentum.marinara.parser.SlashCommandParser; +import net.tomatentum.marinara.reflection.ReflectedMethod; public class SlashCommandInteractionMethod extends InteractionMethod { private SlashCommandIdentifier interactionIdentifier; - SlashCommandInteractionMethod(Method method, InteractionHandler handler, Marinara marinara) { + private SlashCommandInteractionMethod(Method method, InteractionHandler handler, Marinara marinara) { super(method, handler, marinara); } - @Override - public AnnotationParser[] provideParsers() { - return new AnnotationParser[] { - new SlashCommandParser(method(), false, (x) -> { this.interactionIdentifier = x; } ) - }; - } - @Override public Object getParameter(Object context, int index) { return marinara.getWrapper().getContextObjectProvider().convertCommandOption(context, interactionIdentifier.options()[index].name()); @@ -34,4 +31,29 @@ public class SlashCommandInteractionMethod extends InteractionMethod { return interactionIdentifier; } + public static class Factory extends InteractionMethod.Factory { + + @Override + public ReflectedMethod produce(Marinara marinara, Method method, Object containingObject) { + if (!(method.isAnnotationPresent(SlashCommand.class) || + method.isAnnotationPresent(SubCommand.class)) || + !(containingObject instanceof InteractionHandler) + ) + return null; + + return new SlashCommandInteractionMethod(method, (InteractionHandler) containingObject, marinara); + } + + @Override + public void addParser(ReflectedMethod method, List parser) { + super.addParser(method, parser); + + SlashCommandInteractionMethod imethod = (SlashCommandInteractionMethod) method; + parser.add( + new SlashCommandParser(method.method(), false, x -> imethod.interactionIdentifier = x) + ); + } + + } + } diff --git a/lib/src/main/java/net/tomatentum/marinara/util/ReflectedMethod.java b/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethod.java similarity index 82% rename from lib/src/main/java/net/tomatentum/marinara/util/ReflectedMethod.java rename to lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethod.java index af5df50..fa0a1fd 100644 --- a/lib/src/main/java/net/tomatentum/marinara/util/ReflectedMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethod.java @@ -1,4 +1,4 @@ -package net.tomatentum.marinara.util; +package net.tomatentum.marinara.reflection; import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; @@ -9,7 +9,8 @@ import java.util.List; import org.slf4j.Logger; -import net.tomatentum.marinara.parser.AnnotationParser; +import net.tomatentum.marinara.util.LoggerUtil; +import net.tomatentum.marinara.util.ReflectionUtil; public abstract class ReflectedMethod { @@ -17,22 +18,16 @@ public abstract class ReflectedMethod { private Method method; private Object containingObject; - protected List parsers; public ReflectedMethod(Method method, Object containingObject) { if (!Arrays.asList(containingObject.getClass().getMethods()).contains(method)) throw new InvalidParameterException("Method does not apply to specified handler"); this.method = method; this.containingObject = containingObject; - this.parsers = new ArrayList<>(Arrays.asList(provideParsers())); - - this.parsers.stream().forEach(AnnotationParser::parse); } public abstract Object getParameter(Object context, int index); - public abstract AnnotationParser[] provideParsers(); - public Object run(Object context) { method.setAccessible(true); try { @@ -51,10 +46,6 @@ public abstract class ReflectedMethod { return this.containingObject; } - public List parsers() { - return this.parsers; - } - private Object[] getParameters(Object context) { int parameterCount = method.getParameterCount(); List parameters = new ArrayList<>(); diff --git a/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactory.java b/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactory.java new file mode 100644 index 0000000..134a975 --- /dev/null +++ b/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactory.java @@ -0,0 +1,19 @@ +package net.tomatentum.marinara.reflection; + +import java.lang.reflect.Method; +import java.util.List; + +import net.tomatentum.marinara.Marinara; +import net.tomatentum.marinara.parser.AnnotationParser; + +public interface ReflectedMethodFactory { + ReflectedMethod produce(Method method, Object containingClass); + ReflectedMethodFactory addFactory(Factory factory); + + public interface Factory { + + ReflectedMethod produce(Marinara marinara, Method method, Object containingObject); + void addParser(ReflectedMethod method, List parser); + + } +} \ No newline at end of file diff --git a/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactoryImpl.java b/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactoryImpl.java new file mode 100644 index 0000000..d04c59e --- /dev/null +++ b/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactoryImpl.java @@ -0,0 +1,63 @@ +package net.tomatentum.marinara.reflection; + +import java.lang.reflect.Method; +import java.util.ArrayList; +import java.util.List; +import java.util.Objects; +import java.util.Optional; + +import org.slf4j.Logger; + +import net.tomatentum.marinara.Marinara; +import net.tomatentum.marinara.parser.AnnotationParser; +import net.tomatentum.marinara.util.LoggerUtil; +import net.tomatentum.marinara.util.ReflectionUtil; + +public class ReflectedMethodFactoryImpl implements ReflectedMethodFactory { + + private Logger logger = LoggerUtil.getLogger(getClass()); + + private Marinara marinara; + private List factories; + + public ReflectedMethodFactoryImpl(Marinara marinara) { + this(marinara, new ArrayList<>()); + } + + public ReflectedMethodFactoryImpl(Marinara marinara, List factories) { + this.marinara = marinara; + this.factories = factories; + } + + @Override + public ReflectedMethod produce(Method method, Object containingClass) { + Optional imethod = this.factories.stream() + .map(f -> factoryProduce(f, method, containingClass)) + .filter(Objects::nonNull) + .findFirst(); + + if (imethod.isEmpty()) { + logger.debug("Could not produce a ReflectedMethod for Method {}", ReflectionUtil.getFullMethodName(method)); + return null; + } + + return imethod.get(); + } + + @Override + public ReflectedMethodFactory addFactory(Factory factory) { + this.factories.add(factory); + return this; + } + + private ReflectedMethod factoryProduce(Factory factory, Method method, Object containingClass) { + List parser = new ArrayList<>(); + ReflectedMethod m = factory.produce(this.marinara, method, containingClass); + if (m != null) { + factory.addParser(m, parser); + parser.forEach(AnnotationParser::parse); + } + return m; + } + +} diff --git a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java index d1791dc..5eae605 100644 --- a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java +++ b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java @@ -12,12 +12,16 @@ import net.tomatentum.marinara.Marinara; import net.tomatentum.marinara.interaction.InteractionHandler; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.commands.SlashCommandDefinition; +import net.tomatentum.marinara.interaction.components.methods.ButtonInteractionMethod; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; import net.tomatentum.marinara.interaction.ident.RootCommandIdentifier; import net.tomatentum.marinara.util.LoggerUtil; import net.tomatentum.marinara.util.ObjectAggregator; import net.tomatentum.marinara.wrapper.IdentifierProvider; +import net.tomatentum.marinara.interaction.methods.AutoCompleteInteractionMethod; import net.tomatentum.marinara.interaction.methods.InteractionMethod; +import net.tomatentum.marinara.interaction.methods.SlashCommandInteractionMethod; +import net.tomatentum.marinara.reflection.ReflectedMethod; public class InteractionRegistry { private Logger logger = LoggerUtil.getLogger(getClass()); @@ -30,12 +34,18 @@ public class InteractionRegistry { this.marinara = marinara; this.identifierProvider = marinara.getWrapper().createIdentifierProvider(); marinara.getWrapper().subscribeInteractions(this::handle); + marinara.getReflectedMethodFactory() + .addFactory(new AutoCompleteInteractionMethod.Factory()) + .addFactory(new SlashCommandInteractionMethod.Factory()) + .addFactory(new ButtonInteractionMethod.Factory()); + } public void addInteractions(InteractionHandler interactionHandler) { - for (Method method : interactionHandler.getClass().getMethods()) { - InteractionMethod iMethod = InteractionMethod.create(method, interactionHandler, marinara); - if (iMethod != null) { + for (Method method : interactionHandler.getClass().getDeclaredMethods()) { + ReflectedMethod rMethod = this.marinara.getReflectedMethodFactory().produce(method, interactionHandler); + if (rMethod != null && rMethod instanceof InteractionMethod) { + InteractionMethod iMethod = (InteractionMethod) rMethod; InteractionEntry.findEntry(interactions, iMethod.identifier()).addMethod(iMethod); logger.debug("Added {} method from {}", iMethod.method().getName(), interactionHandler.getClass().getSimpleName()); } -- 2.47.2 From 92540576df61fe9418c9337ce1daac9358d22259 Mon Sep 17 00:00:00 2001 From: tueem Date: Mon, 31 Mar 2025 10:30:24 +0200 Subject: [PATCH 06/18] fix(registry): add null check to InteractionIdentifier#equals --- .../marinara/interaction/ident/InteractionIdentifier.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/ident/InteractionIdentifier.java b/lib/src/main/java/net/tomatentum/marinara/interaction/ident/InteractionIdentifier.java index 9ef1298..6e87068 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/ident/InteractionIdentifier.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/ident/InteractionIdentifier.java @@ -73,7 +73,7 @@ public class InteractionIdentifier { @Override public boolean equals(Object obj) { - if (!(obj instanceof InteractionIdentifier)) + if (obj == null || !(obj instanceof InteractionIdentifier)) return false; InteractionIdentifier ident = (InteractionIdentifier) obj; if (!type().equals(ident.type())) -- 2.47.2 From 450f1fdaa1cefb574af7f2f80ea2c4f356a33dfd Mon Sep 17 00:00:00 2001 From: tueem Date: Mon, 31 Mar 2025 10:36:49 +0200 Subject: [PATCH 07/18] refactor(autocomplete): implement autocompleteRefs and remove SlashCommand annotation on Autocomplete Method --- .../interaction/annotation/AutoComplete.java | 2 +- .../ident/RootCommandIdentifier.java | 23 +++++++++---- .../ident/SlashCommandIdentifier.java | 30 ++++++++++++++--- .../AutoCompleteInteractionMethod.java | 22 +++++++++---- .../SlashCommandInteractionMethod.java | 13 +++++--- .../marinara/parser/AutocompleteParser.java | 33 +++++++++++++++++++ .../marinara/parser/SlashCommandParser.java | 10 +++--- .../registry/InteractionRegistry.java | 9 ++++- .../marinara/wrapper/IdentifierProvider.java | 11 ++++--- .../AutocompleteIdentifierConverter.java | 29 ++++++++++++---- .../ButtonIdentifierConverter.java | 3 +- .../SlashCommandIdentifierConverter.java | 3 +- .../test/discord4j/TestAutocomplete.java | 10 ++++-- .../AutocompleteIdentifierConverter.java | 30 +++++++++++++---- .../ButtonIdentifierConverter.java | 3 +- .../SlashCommandIdentifierConverter.java | 3 +- .../test/javacord/TestAutocomplete.java | 8 ++++- 17 files changed, 186 insertions(+), 56 deletions(-) create mode 100644 lib/src/main/java/net/tomatentum/marinara/parser/AutocompleteParser.java diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/annotation/AutoComplete.java b/lib/src/main/java/net/tomatentum/marinara/interaction/annotation/AutoComplete.java index 46aa6aa..01dc483 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/annotation/AutoComplete.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/annotation/AutoComplete.java @@ -8,5 +8,5 @@ import java.lang.annotation.Target; @Target({ElementType.METHOD}) @Retention(RetentionPolicy.RUNTIME) public @interface AutoComplete { - + public String value(); } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/ident/RootCommandIdentifier.java b/lib/src/main/java/net/tomatentum/marinara/interaction/ident/RootCommandIdentifier.java index ae0e6d4..5563718 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/ident/RootCommandIdentifier.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/ident/RootCommandIdentifier.java @@ -13,8 +13,9 @@ public class RootCommandIdentifier extends SlashCommandIdentifier { String description, InteractionType type, SlashCommandOption[] options, - long[] serverIds) { - super(parent, name, description, type, options); + long[] serverIds, + String[] autocompleteRef) { + super(parent, name, description, type, options, autocompleteRef); this.serverIds = serverIds; } @@ -28,7 +29,7 @@ public class RootCommandIdentifier extends SlashCommandIdentifier { private String description; private SlashCommandOption[] options; private long[] serverIds; - + private String[] autocompleteRef; public InteractionIdentifier parent() { return parent; @@ -75,14 +76,24 @@ public class RootCommandIdentifier extends SlashCommandIdentifier { return this; } - public SlashCommandIdentifier build(boolean autocomplete) { + public String[] autocompleteRef() { + return this.autocompleteRef; + } + + public Builder autocompleteRef(String[] autocompleteRef) { + this.autocompleteRef = autocompleteRef; + return this; + } + + public SlashCommandIdentifier build() { return new RootCommandIdentifier( parent, name, description, - autocomplete ? InteractionType.AUTOCOMPLETE : InteractionType.COMMAND, + InteractionType.COMMAND, options, - serverIds); + serverIds, + autocompleteRef); } } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/ident/SlashCommandIdentifier.java b/lib/src/main/java/net/tomatentum/marinara/interaction/ident/SlashCommandIdentifier.java index 7284a2a..1e7ebf1 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/ident/SlashCommandIdentifier.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/ident/SlashCommandIdentifier.java @@ -6,27 +6,39 @@ import net.tomatentum.marinara.interaction.commands.annotation.SlashCommandOptio public class SlashCommandIdentifier extends InteractionIdentifier { private SlashCommandOption[] options; + private String[] autocompleteRef; protected SlashCommandIdentifier( InteractionIdentifier parent, String name, String description, InteractionType type, - SlashCommandOption[] options + SlashCommandOption[] options, + String[] autocompleteRef ) { super(parent, name, description, type); this.options = options; + this.autocompleteRef = autocompleteRef; } public SlashCommandOption[] options() { return this.options; } + public String[] autocompleteRef() { + return this.autocompleteRef; + } + public SlashCommandIdentifier autocompleteRef(String[] autocompleteRef) { + this.autocompleteRef = autocompleteRef; + return this; + } + public static class Builder { private InteractionIdentifier parent; private String name; private String description; private SlashCommandOption[] options; + private String[] autocompleteRef; public InteractionIdentifier parent() { return parent; @@ -64,13 +76,23 @@ public class SlashCommandIdentifier extends InteractionIdentifier { return this; } - public SlashCommandIdentifier build(boolean autocomplete) { + public String[] autocompleteRef() { + return this.autocompleteRef; + } + + public Builder autocompleteRef(String[] autocompleteRef) { + this.autocompleteRef = autocompleteRef; + return this; + } + + public SlashCommandIdentifier build() { return new SlashCommandIdentifier( parent, name, description, - autocomplete ? InteractionType.AUTOCOMPLETE : InteractionType.COMMAND, - options); + InteractionType.COMMAND, + options, + autocompleteRef); } } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java index c1b6477..1261445 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java @@ -5,15 +5,18 @@ import java.util.List; import net.tomatentum.marinara.Marinara; import net.tomatentum.marinara.interaction.InteractionHandler; +import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.annotation.AutoComplete; +import net.tomatentum.marinara.interaction.commands.annotation.SlashCommand; +import net.tomatentum.marinara.interaction.commands.annotation.SubCommand; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; import net.tomatentum.marinara.parser.AnnotationParser; -import net.tomatentum.marinara.parser.SlashCommandParser; +import net.tomatentum.marinara.parser.AutocompleteParser; import net.tomatentum.marinara.reflection.ReflectedMethod; public class AutoCompleteInteractionMethod extends InteractionMethod { - private InteractionIdentifier interactionIdentifier; + private String autocompleteRef; private AutoCompleteInteractionMethod(Method method, InteractionHandler handler, @@ -34,16 +37,21 @@ public class AutoCompleteInteractionMethod extends InteractionMethod { @Override public InteractionIdentifier identifier() { - return interactionIdentifier; + return InteractionIdentifier.builder() + .type(InteractionType.AUTOCOMPLETE) + .name(autocompleteRef) + .description("AUTOCOMPLETE") + .build(); } public static class Factory extends InteractionMethod.Factory { @Override public ReflectedMethod produce(Marinara marinara, Method method, Object containingObject) { - if (!method.isAnnotationPresent(AutoComplete.class) || - !(containingObject instanceof InteractionHandler) - ) + if (!(containingObject instanceof InteractionHandler) || + !method.isAnnotationPresent(AutoComplete.class) || + (method.isAnnotationPresent(SlashCommand.class) || + method.isAnnotationPresent(SubCommand.class))) return null; return new AutoCompleteInteractionMethod(method, (InteractionHandler) containingObject, marinara); @@ -55,7 +63,7 @@ public class AutoCompleteInteractionMethod extends InteractionMethod { AutoCompleteInteractionMethod imethod = (AutoCompleteInteractionMethod) method; parser.add( - new SlashCommandParser(method.method(), true, x -> imethod.interactionIdentifier = x) + new AutocompleteParser(method.method(), x -> imethod.autocompleteRef = x[0]) ); } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java index a0adb74..f4fd0fd 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java @@ -10,6 +10,7 @@ import net.tomatentum.marinara.interaction.commands.annotation.SubCommand; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; import net.tomatentum.marinara.interaction.ident.SlashCommandIdentifier; import net.tomatentum.marinara.parser.AnnotationParser; +import net.tomatentum.marinara.parser.AutocompleteParser; import net.tomatentum.marinara.parser.SlashCommandParser; import net.tomatentum.marinara.reflection.ReflectedMethod; @@ -35,10 +36,9 @@ public class SlashCommandInteractionMethod extends InteractionMethod { @Override public ReflectedMethod produce(Marinara marinara, Method method, Object containingObject) { - if (!(method.isAnnotationPresent(SlashCommand.class) || - method.isAnnotationPresent(SubCommand.class)) || - !(containingObject instanceof InteractionHandler) - ) + if (!(containingObject instanceof InteractionHandler) || + !(method.isAnnotationPresent(SlashCommand.class) || + method.isAnnotationPresent(SubCommand.class))) return null; return new SlashCommandInteractionMethod(method, (InteractionHandler) containingObject, marinara); @@ -50,7 +50,10 @@ public class SlashCommandInteractionMethod extends InteractionMethod { SlashCommandInteractionMethod imethod = (SlashCommandInteractionMethod) method; parser.add( - new SlashCommandParser(method.method(), false, x -> imethod.interactionIdentifier = x) + new SlashCommandParser(method.method(), x -> imethod.interactionIdentifier = x) + ); + parser.add( + new AutocompleteParser(method.method(), x -> imethod.interactionIdentifier.autocompleteRef(x)) ); } diff --git a/lib/src/main/java/net/tomatentum/marinara/parser/AutocompleteParser.java b/lib/src/main/java/net/tomatentum/marinara/parser/AutocompleteParser.java new file mode 100644 index 0000000..37ab8c8 --- /dev/null +++ b/lib/src/main/java/net/tomatentum/marinara/parser/AutocompleteParser.java @@ -0,0 +1,33 @@ +package net.tomatentum.marinara.parser; + +import java.lang.reflect.Method; +import java.util.Arrays; +import java.util.function.Consumer; + +import net.tomatentum.marinara.interaction.annotation.AutoComplete; + +public class AutocompleteParser implements AnnotationParser { + + private Method method; + private Consumer consumer; + + public AutocompleteParser(Method method, Consumer consumer) { + this.method = method; + this.consumer = consumer; + } + + @Override + public void parse() { + String[] autocompletes = Arrays.stream(this.method.getAnnotationsByType(AutoComplete.class)) + .map(AutoComplete::value) + .toArray(String[]::new); + this.consumer.accept(autocompletes); + + } + + @Override + public Method getMethod() { + return this.method; + } + +} diff --git a/lib/src/main/java/net/tomatentum/marinara/parser/SlashCommandParser.java b/lib/src/main/java/net/tomatentum/marinara/parser/SlashCommandParser.java index c598761..b13efa1 100644 --- a/lib/src/main/java/net/tomatentum/marinara/parser/SlashCommandParser.java +++ b/lib/src/main/java/net/tomatentum/marinara/parser/SlashCommandParser.java @@ -17,14 +17,12 @@ import net.tomatentum.marinara.util.ReflectionUtil; public class SlashCommandParser implements AnnotationParser { private Method method; - private boolean isAutoComplete; private Consumer consumer; private Logger logger = LoggerUtil.getLogger(getClass()); - public SlashCommandParser(Method method, boolean isAutoComplete, Consumer consumer) { + public SlashCommandParser(Method method, Consumer consumer) { this.method = method; - this.isAutoComplete = isAutoComplete; this.consumer = consumer; } @@ -38,14 +36,14 @@ public class SlashCommandParser implements AnnotationParser { .description(cmd.description()) .options(cmd.options()) .serverIds(cmd.serverIds()) - .build(isAutoComplete); + .build(); if (ReflectionUtil.isAnnotationPresent(method, SubCommandGroup.class)) { SubCommandGroup cmdGroup = ReflectionUtil.getAnnotation(method, SubCommandGroup.class); lastIdentifier = InteractionIdentifier.builder() .name(cmdGroup.name()) .description(cmdGroup.description()) - .type(isAutoComplete ? InteractionType.AUTOCOMPLETE : InteractionType.COMMAND) + .type(InteractionType.COMMAND) .parent(lastIdentifier) .build(); } @@ -56,7 +54,7 @@ public class SlashCommandParser implements AnnotationParser { .name(subCmd.name()) .description(subCmd.description()) .options(subCmd.options()) - .build(isAutoComplete); + .build(); } logger.trace("Parsed using SlashCommandParser for method {} with the result: {}", ReflectionUtil.getFullMethodName(method), lastIdentifier.toString()); diff --git a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java index 5eae605..f582b0b 100644 --- a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java +++ b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java @@ -4,6 +4,7 @@ import java.lang.reflect.Method; import java.util.Arrays; import java.util.HashSet; import java.util.List; +import java.util.Optional; import java.util.Set; import org.slf4j.Logger; @@ -72,10 +73,16 @@ public class InteractionRegistry { public void handle(Object context) { logger.debug("Received {} interaction ", context); interactions.forEach((e) -> { - if (this.identifierProvider.provide(context).equals(e.identifier())) { + if (e.identifier().equals(this.identifierProvider.provide(context, this))) { logger.info("Running {} interaction using {}\ncontext: {}", e.type(), e.toString(), context.toString()); e.runAll(context); } }); } + + public Optional findFor(InteractionIdentifier identifier) { + return this.interactions.stream() + .filter(x -> x.identifier().equals(identifier)) + .findFirst(); + } } diff --git a/lib/src/main/java/net/tomatentum/marinara/wrapper/IdentifierProvider.java b/lib/src/main/java/net/tomatentum/marinara/wrapper/IdentifierProvider.java index 1308222..1c5f544 100644 --- a/lib/src/main/java/net/tomatentum/marinara/wrapper/IdentifierProvider.java +++ b/lib/src/main/java/net/tomatentum/marinara/wrapper/IdentifierProvider.java @@ -11,6 +11,7 @@ import org.slf4j.Logger; import io.leangen.geantyref.GenericTypeReflector; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; +import net.tomatentum.marinara.registry.InteractionRegistry; import net.tomatentum.marinara.util.LoggerUtil; import net.tomatentum.marinara.util.ReflectionUtil; @@ -36,7 +37,7 @@ public class IdentifierProvider { } } - public InteractionIdentifier provide(Object context) { + public InteractionIdentifier provide(Object context, InteractionRegistry registry) { Type type = ReflectionUtil.getMostSpecificClass( converter.keySet().stream().filter(x -> x.isAssignableFrom(context.getClass())).toArray(Class[]::new), context.getClass()); @@ -47,12 +48,12 @@ public class IdentifierProvider { @SuppressWarnings("unchecked") Converter conv = (Converter) converter.get(type); - return conv.convert(context); + return conv.convert(context, registry); } @FunctionalInterface public interface Converter { - InteractionIdentifier convert(T context); + InteractionIdentifier convert(T context, InteractionRegistry registry); } public static class LambdaWrapper implements Converter { @@ -64,8 +65,8 @@ public class IdentifierProvider { } @Override - public InteractionIdentifier convert(T context) { - return this.converter.convert(context); + public InteractionIdentifier convert(T context, InteractionRegistry registry) { + return this.converter.convert(context, registry); } } diff --git a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/AutocompleteIdentifierConverter.java b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/AutocompleteIdentifierConverter.java index 49761d9..03f1bb1 100644 --- a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/AutocompleteIdentifierConverter.java +++ b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/AutocompleteIdentifierConverter.java @@ -1,38 +1,53 @@ package net.tomatentum.marinara.wrapper.discord4j.identifierconverter; import java.util.List; +import java.util.Optional; import discord4j.core.event.domain.interaction.ChatInputAutoCompleteEvent; import discord4j.core.object.command.ApplicationCommandInteractionOption; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; +import net.tomatentum.marinara.interaction.ident.SlashCommandIdentifier; +import net.tomatentum.marinara.registry.InteractionEntry; +import net.tomatentum.marinara.registry.InteractionRegistry; import net.tomatentum.marinara.wrapper.IdentifierProvider; import net.tomatentum.marinara.wrapper.discord4j.Discord4JWrapper; public class AutocompleteIdentifierConverter implements IdentifierProvider.Converter { @Override - public InteractionIdentifier convert(ChatInputAutoCompleteEvent context) { + public InteractionIdentifier convert(ChatInputAutoCompleteEvent context, InteractionRegistry registry) { List options = Discord4JWrapper.SUB_FILTER.apply(context.getOptions()); String commandName = context.getCommandName(); + InteractionIdentifier ident; if (!options.isEmpty()) { List sub_options = Discord4JWrapper.SUB_FILTER.apply(options.getFirst().getOptions()); if (!sub_options.isEmpty()) - return InteractionIdentifier.createHierarchy( - InteractionType.AUTOCOMPLETE, + ident = InteractionIdentifier.createHierarchy( + InteractionType.COMMAND, commandName, options.getFirst().getName(), sub_options.getFirst().getName()); else - return InteractionIdentifier.createHierarchy( - InteractionType.AUTOCOMPLETE, + ident = InteractionIdentifier.createHierarchy( + InteractionType.COMMAND, commandName, options.getFirst().getName()); }else - return InteractionIdentifier.createHierarchy( - InteractionType.AUTOCOMPLETE, + ident = InteractionIdentifier.createHierarchy( + InteractionType.COMMAND, commandName); + + Optional entry = registry.findFor(ident); + if (entry.isPresent() && entry.get().identifier() instanceof SlashCommandIdentifier) { + SlashCommandIdentifier sIdent = (SlashCommandIdentifier) entry.get().identifier(); + return InteractionIdentifier.builder() + .type(InteractionType.AUTOCOMPLETE) + .name(sIdent.autocompleteRef()[0]) + .build(); + } + return null; } } diff --git a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/ButtonIdentifierConverter.java b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/ButtonIdentifierConverter.java index 8751d4f..148452a 100644 --- a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/ButtonIdentifierConverter.java +++ b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/ButtonIdentifierConverter.java @@ -3,12 +3,13 @@ package net.tomatentum.marinara.wrapper.discord4j.identifierconverter; import discord4j.core.event.domain.interaction.ButtonInteractionEvent; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; +import net.tomatentum.marinara.registry.InteractionRegistry; import net.tomatentum.marinara.wrapper.IdentifierProvider; public class ButtonIdentifierConverter implements IdentifierProvider.Converter { @Override - public InteractionIdentifier convert(ButtonInteractionEvent context) { + public InteractionIdentifier convert(ButtonInteractionEvent context, InteractionRegistry registry) { return InteractionIdentifier.builder().name(context.getCustomId()).type(InteractionType.BUTTON).build(); } diff --git a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/SlashCommandIdentifierConverter.java b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/SlashCommandIdentifierConverter.java index 612cd0a..f82b016 100644 --- a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/SlashCommandIdentifierConverter.java +++ b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/SlashCommandIdentifierConverter.java @@ -6,13 +6,14 @@ import discord4j.core.event.domain.interaction.ChatInputInteractionEvent; import discord4j.core.object.command.ApplicationCommandInteractionOption; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; +import net.tomatentum.marinara.registry.InteractionRegistry; import net.tomatentum.marinara.wrapper.IdentifierProvider; import net.tomatentum.marinara.wrapper.discord4j.Discord4JWrapper; public class SlashCommandIdentifierConverter implements IdentifierProvider.Converter { @Override - public InteractionIdentifier convert(ChatInputInteractionEvent context) { + public InteractionIdentifier convert(ChatInputInteractionEvent context, InteractionRegistry registry) { List options = Discord4JWrapper.SUB_FILTER.apply(context.getOptions()); String commandName = context.getCommandName(); diff --git a/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/TestAutocomplete.java b/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/TestAutocomplete.java index d216805..c1b04a8 100644 --- a/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/TestAutocomplete.java +++ b/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/TestAutocomplete.java @@ -5,14 +5,20 @@ import static org.junit.jupiter.api.Assertions.assertEquals; import java.util.Collections; import discord4j.core.event.domain.interaction.ChatInputAutoCompleteEvent; +import discord4j.core.event.domain.interaction.ChatInputInteractionEvent; import net.tomatentum.marinara.interaction.InteractionHandler; import net.tomatentum.marinara.interaction.annotation.AutoComplete; import net.tomatentum.marinara.interaction.commands.annotation.SlashCommand; public class TestAutocomplete implements InteractionHandler { - + @SlashCommand(name = "test") - @AutoComplete + @AutoComplete("testAuto") + public void exec(ChatInputInteractionEvent context) { + + } + + @AutoComplete("testAuto") public void autocomplete(ChatInputAutoCompleteEvent context, String value) { System.out.println("Success!"); assertEquals(value, "test"); diff --git a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/AutocompleteIdentifierConverter.java b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/AutocompleteIdentifierConverter.java index 65fef44..3c1b7da 100644 --- a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/AutocompleteIdentifierConverter.java +++ b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/AutocompleteIdentifierConverter.java @@ -1,37 +1,53 @@ package net.tomatentum.marinara.wrapper.javacord.identifierconverter; import java.util.List; +import java.util.Optional; import org.javacord.api.interaction.AutocompleteInteraction; import org.javacord.api.interaction.SlashCommandInteractionOption; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; +import net.tomatentum.marinara.interaction.ident.SlashCommandIdentifier; +import net.tomatentum.marinara.registry.InteractionEntry; +import net.tomatentum.marinara.registry.InteractionRegistry; import net.tomatentum.marinara.wrapper.IdentifierProvider; public class AutocompleteIdentifierConverter implements IdentifierProvider.Converter { @Override - public InteractionIdentifier convert(AutocompleteInteraction context) { + public InteractionIdentifier convert(AutocompleteInteraction context, InteractionRegistry registry) { List options = context.getOptions(); String commandName = context.getCommandName(); + InteractionIdentifier ident; + if (!options.isEmpty()) { List sub_options = context.getOptions().getFirst().getOptions(); if (!sub_options.isEmpty()) - return InteractionIdentifier.createHierarchy( - InteractionType.AUTOCOMPLETE, + ident = InteractionIdentifier.createHierarchy( + InteractionType.COMMAND, commandName, options.getFirst().getName(), sub_options.getFirst().getName()); else - return InteractionIdentifier.createHierarchy( - InteractionType.AUTOCOMPLETE, + ident = InteractionIdentifier.createHierarchy( + InteractionType.COMMAND, commandName, options.getFirst().getName()); }else - return InteractionIdentifier.createHierarchy( - InteractionType.AUTOCOMPLETE, + ident = InteractionIdentifier.createHierarchy( + InteractionType.COMMAND, commandName); + + Optional entry = registry.findFor(ident); + if (entry.isPresent() && entry.get().identifier() instanceof SlashCommandIdentifier) { + SlashCommandIdentifier sIdent = (SlashCommandIdentifier) entry.get().identifier(); + return InteractionIdentifier.builder() + .type(InteractionType.AUTOCOMPLETE) + .name(sIdent.autocompleteRef()[0]) + .build(); + } + return null; } } diff --git a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/ButtonIdentifierConverter.java b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/ButtonIdentifierConverter.java index 209ce32..e9e7155 100644 --- a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/ButtonIdentifierConverter.java +++ b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/ButtonIdentifierConverter.java @@ -4,12 +4,13 @@ import org.javacord.api.interaction.ButtonInteraction; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; +import net.tomatentum.marinara.registry.InteractionRegistry; import net.tomatentum.marinara.wrapper.IdentifierProvider; public class ButtonIdentifierConverter implements IdentifierProvider.Converter { @Override - public InteractionIdentifier convert(ButtonInteraction context) { + public InteractionIdentifier convert(ButtonInteraction context, InteractionRegistry registry) { return InteractionIdentifier.builder().name(context.getCustomId()).type(InteractionType.BUTTON).build(); } diff --git a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/SlashCommandIdentifierConverter.java b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/SlashCommandIdentifierConverter.java index 4b90bd1..84ab246 100644 --- a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/SlashCommandIdentifierConverter.java +++ b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/SlashCommandIdentifierConverter.java @@ -7,12 +7,13 @@ import org.javacord.api.interaction.SlashCommandInteractionOption; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; +import net.tomatentum.marinara.registry.InteractionRegistry; import net.tomatentum.marinara.wrapper.IdentifierProvider; public class SlashCommandIdentifierConverter implements IdentifierProvider.Converter { @Override - public InteractionIdentifier convert(SlashCommandInteraction context) { + public InteractionIdentifier convert(SlashCommandInteraction context, InteractionRegistry registry) { List options = context.getOptions(); String commandName = context.getCommandName(); if (!options.isEmpty()) { diff --git a/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/TestAutocomplete.java b/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/TestAutocomplete.java index d9063bb..bb56c25 100644 --- a/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/TestAutocomplete.java +++ b/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/TestAutocomplete.java @@ -4,6 +4,7 @@ import static org.junit.jupiter.api.Assertions.assertEquals; import java.util.Collections; +import org.javacord.api.event.interaction.SlashCommandCreateEvent; import org.javacord.api.interaction.AutocompleteInteraction; import net.tomatentum.marinara.interaction.InteractionHandler; @@ -13,7 +14,12 @@ import net.tomatentum.marinara.interaction.commands.annotation.SlashCommand; public class TestAutocomplete implements InteractionHandler { @SlashCommand(name = "test") - @AutoComplete + @AutoComplete("testAuto") + public void exec(SlashCommandCreateEvent context) { + + } + + @AutoComplete("testAuto") public void autocomplete(AutocompleteInteraction context, String value) { System.out.println("Success!"); assertEquals(value, "test"); -- 2.47.2 From 0114cffcbd59eb0ea1f6a78b1d7ec9da8871f605 Mon Sep 17 00:00:00 2001 From: tueem Date: Mon, 31 Mar 2025 10:50:36 +0200 Subject: [PATCH 08/18] refactor(method): make use of optionals in ReflectedMethodFactory --- .../methods/ButtonInteractionMethod.java | 12 +++++++----- .../AutoCompleteInteractionMethod.java | 14 ++++++++------ .../SlashCommandInteractionMethod.java | 13 +++++++------ .../reflection/ReflectedMethodFactory.java | 5 +++-- .../ReflectedMethodFactoryImpl.java | 19 +++++++++---------- .../registry/InteractionRegistry.java | 14 ++++++++------ 6 files changed, 42 insertions(+), 35 deletions(-) diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/components/methods/ButtonInteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/components/methods/ButtonInteractionMethod.java index 82e25a6..81fe0d0 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/components/methods/ButtonInteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/components/methods/ButtonInteractionMethod.java @@ -2,6 +2,7 @@ package net.tomatentum.marinara.interaction.components.methods; import java.lang.reflect.Method; import java.util.List; +import java.util.Optional; import net.tomatentum.marinara.Marinara; import net.tomatentum.marinara.interaction.InteractionHandler; @@ -39,13 +40,14 @@ public class ButtonInteractionMethod extends InteractionMethod { public static class Factory extends InteractionMethod.Factory { @Override - public ReflectedMethod produce(Marinara marinara, Method method, Object containingObject) { - if (!method.isAnnotationPresent(Button.class) || - !(containingObject instanceof InteractionHandler) + public Optional produce(Marinara marinara, Method method, Object containingObject) { + ReflectedMethod rMethod = null; + if (method.isAnnotationPresent(Button.class) && + (containingObject instanceof InteractionHandler) ) - return null; + rMethod = new ButtonInteractionMethod(method, (InteractionHandler) containingObject, marinara); - return new ButtonInteractionMethod(method, (InteractionHandler) containingObject, marinara); + return Optional.ofNullable(rMethod); } @Override diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java index 1261445..82569a2 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java @@ -2,6 +2,7 @@ package net.tomatentum.marinara.interaction.methods; import java.lang.reflect.Method; import java.util.List; +import java.util.Optional; import net.tomatentum.marinara.Marinara; import net.tomatentum.marinara.interaction.InteractionHandler; @@ -47,14 +48,15 @@ public class AutoCompleteInteractionMethod extends InteractionMethod { public static class Factory extends InteractionMethod.Factory { @Override - public ReflectedMethod produce(Marinara marinara, Method method, Object containingObject) { - if (!(containingObject instanceof InteractionHandler) || - !method.isAnnotationPresent(AutoComplete.class) || - (method.isAnnotationPresent(SlashCommand.class) || + public Optional produce(Marinara marinara, Method method, Object containingObject) { + ReflectedMethod rMethod = null; + if ((containingObject instanceof InteractionHandler) && + method.isAnnotationPresent(AutoComplete.class) && + !(method.isAnnotationPresent(SlashCommand.class) || method.isAnnotationPresent(SubCommand.class))) - return null; + rMethod = new AutoCompleteInteractionMethod(method, (InteractionHandler) containingObject, marinara); - return new AutoCompleteInteractionMethod(method, (InteractionHandler) containingObject, marinara); + return Optional.ofNullable(rMethod); } @Override diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java index f4fd0fd..816308c 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java @@ -2,6 +2,7 @@ package net.tomatentum.marinara.interaction.methods; import java.lang.reflect.Method; import java.util.List; +import java.util.Optional; import net.tomatentum.marinara.Marinara; import net.tomatentum.marinara.interaction.InteractionHandler; @@ -35,13 +36,13 @@ public class SlashCommandInteractionMethod extends InteractionMethod { public static class Factory extends InteractionMethod.Factory { @Override - public ReflectedMethod produce(Marinara marinara, Method method, Object containingObject) { - if (!(containingObject instanceof InteractionHandler) || - !(method.isAnnotationPresent(SlashCommand.class) || + public Optional produce(Marinara marinara, Method method, Object containingObject) { + ReflectedMethod rMethod = null; + if ((containingObject instanceof InteractionHandler) && + (method.isAnnotationPresent(SlashCommand.class) || method.isAnnotationPresent(SubCommand.class))) - return null; - - return new SlashCommandInteractionMethod(method, (InteractionHandler) containingObject, marinara); + rMethod = new SlashCommandInteractionMethod(method, (InteractionHandler) containingObject, marinara); + return Optional.ofNullable(rMethod); } @Override diff --git a/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactory.java b/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactory.java index 134a975..e36da12 100644 --- a/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactory.java +++ b/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactory.java @@ -2,17 +2,18 @@ package net.tomatentum.marinara.reflection; import java.lang.reflect.Method; import java.util.List; +import java.util.Optional; import net.tomatentum.marinara.Marinara; import net.tomatentum.marinara.parser.AnnotationParser; public interface ReflectedMethodFactory { - ReflectedMethod produce(Method method, Object containingClass); + Optional produce(Method method, Object containingClass); ReflectedMethodFactory addFactory(Factory factory); public interface Factory { - ReflectedMethod produce(Marinara marinara, Method method, Object containingObject); + Optional produce(Marinara marinara, Method method, Object containingObject); void addParser(ReflectedMethod method, List parser); } diff --git a/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactoryImpl.java b/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactoryImpl.java index d04c59e..485ea0c 100644 --- a/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactoryImpl.java +++ b/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactoryImpl.java @@ -3,7 +3,6 @@ package net.tomatentum.marinara.reflection; import java.lang.reflect.Method; import java.util.ArrayList; import java.util.List; -import java.util.Objects; import java.util.Optional; import org.slf4j.Logger; @@ -30,18 +29,18 @@ public class ReflectedMethodFactoryImpl implements ReflectedMethodFactory { } @Override - public ReflectedMethod produce(Method method, Object containingClass) { + public Optional produce(Method method, Object containingClass) { Optional imethod = this.factories.stream() .map(f -> factoryProduce(f, method, containingClass)) - .filter(Objects::nonNull) + .filter(Optional::isPresent) + .map(Optional::get) .findFirst(); if (imethod.isEmpty()) { logger.debug("Could not produce a ReflectedMethod for Method {}", ReflectionUtil.getFullMethodName(method)); - return null; } - return imethod.get(); + return imethod; } @Override @@ -50,13 +49,13 @@ public class ReflectedMethodFactoryImpl implements ReflectedMethodFactory { return this; } - private ReflectedMethod factoryProduce(Factory factory, Method method, Object containingClass) { + private Optional factoryProduce(Factory factory, Method method, Object containingClass) { List parser = new ArrayList<>(); - ReflectedMethod m = factory.produce(this.marinara, method, containingClass); - if (m != null) { - factory.addParser(m, parser); + Optional m = factory.produce(this.marinara, method, containingClass); + m.ifPresent(x -> { + factory.addParser(x, parser); parser.forEach(AnnotationParser::parse); - } + }); return m; } diff --git a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java index f582b0b..e9acd40 100644 --- a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java +++ b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java @@ -44,12 +44,14 @@ public class InteractionRegistry { public void addInteractions(InteractionHandler interactionHandler) { for (Method method : interactionHandler.getClass().getDeclaredMethods()) { - ReflectedMethod rMethod = this.marinara.getReflectedMethodFactory().produce(method, interactionHandler); - if (rMethod != null && rMethod instanceof InteractionMethod) { - InteractionMethod iMethod = (InteractionMethod) rMethod; - InteractionEntry.findEntry(interactions, iMethod.identifier()).addMethod(iMethod); - logger.debug("Added {} method from {}", iMethod.method().getName(), interactionHandler.getClass().getSimpleName()); - } + Optional rMethod = this.marinara.getReflectedMethodFactory().produce(method, interactionHandler); + rMethod.ifPresent(x -> { + if (x instanceof InteractionMethod) { + InteractionMethod iMethod = (InteractionMethod) x; + InteractionEntry.findEntry(interactions, iMethod.identifier()).addMethod(iMethod); + logger.debug("Added {} method from {}", iMethod.method().getName(), interactionHandler.getClass().getSimpleName()); + } + }); } logger.info("Added all Interactions from {}", interactionHandler.getClass().getSimpleName()); } -- 2.47.2 From ec1795237506e5d9887eb867220bd8f5e97a2923 Mon Sep 17 00:00:00 2001 From: tueem Date: Tue, 1 Apr 2025 10:18:37 +0200 Subject: [PATCH 09/18] feat(build): add prefix to archive jar --- build.gradle.kts | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/build.gradle.kts b/build.gradle.kts index c821828..f32cd94 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -8,7 +8,11 @@ allprojects { group = "net.tomatentum.Marinara" version = "1.0.0-RC1" + (if (!project.hasProperty("release")) ("-" + getGitHash()) else "") description = "A simple but powerful, library-agnostic Discord Interaction Wrapper." - + plugins.withType { + tasks.withType().configureEach { + archiveBaseName.set("marinara-" + archiveBaseName.get()) + } + } } subprojects { -- 2.47.2 From 991d1c047b6539fe2bffa83c45f38cf5f41d6262 Mon Sep 17 00:00:00 2001 From: tueem Date: Sun, 6 Apr 2025 00:04:17 +0200 Subject: [PATCH 10/18] feat(core): add InteractionProcessors and InteractionExecutors and improve Autocomplete Interaction --- .../net/tomatentum/marinara/Marinara.java | 17 ++++++- .../annotation/SlashCommandOption.java | 5 +- .../option/AutocompleteOptionData.java | 16 +++++++ .../ident/InteractionIdentifier.java | 9 +++- .../ident/RootCommandIdentifier.java | 8 ++-- .../ident/SlashCommandIdentifier.java | 17 +------ .../AutoCompleteInteractionMethod.java | 17 ++++--- .../methods/InteractionMethod.java | 2 +- .../SlashCommandInteractionMethod.java | 11 ++--- .../AutocompleteInteractionProcessor.java | 46 +++++++++++++++++++ .../processor/DirectInteractionProcessor.java | 32 +++++++++++++ .../processor/InteractionProcessor.java | 10 ++++ .../marinara/registry/InteractionEntry.java | 26 +++++++---- .../registry/InteractionExecutor.java | 7 +++ .../registry/InteractionRegistry.java | 18 ++------ .../ProcessorInteractionExecutor.java | 41 +++++++++++++++++ .../wrapper/ContextObjectProvider.java | 4 +- .../marinara/wrapper/IdentifierProvider.java | 15 +++--- .../marinara/wrapper/LibraryWrapper.java | 3 +- .../Discord4JContextObjectProvider.java | 21 +++++---- .../discord4j/Discord4JConverterSpec.java | 6 +-- .../wrapper/discord4j/Discord4JWrapper.java | 20 ++++++-- .../AutocompleteIdentifierConverter.java | 34 ++++---------- .../ButtonIdentifierConverter.java | 3 +- .../SlashCommandIdentifierConverter.java | 3 +- .../test/discord4j/AutoCompleteTest.java | 4 +- .../test/discord4j/TestAutocomplete.java | 20 ++++++-- .../JavacordContextObjectProvider.java | 14 +++--- .../javacord/JavacordConverterSpec.java | 6 +-- .../wrapper/javacord/JavacordWrapper.java | 17 ++++++- .../AutocompleteIdentifierConverter.java | 34 ++++---------- .../ButtonIdentifierConverter.java | 3 +- .../SlashCommandIdentifierConverter.java | 3 +- .../test/javacord/TestAutocomplete.java | 16 +++++-- 34 files changed, 344 insertions(+), 164 deletions(-) create mode 100644 lib/src/main/java/net/tomatentum/marinara/interaction/commands/option/AutocompleteOptionData.java create mode 100644 lib/src/main/java/net/tomatentum/marinara/interaction/processor/AutocompleteInteractionProcessor.java create mode 100644 lib/src/main/java/net/tomatentum/marinara/interaction/processor/DirectInteractionProcessor.java create mode 100644 lib/src/main/java/net/tomatentum/marinara/interaction/processor/InteractionProcessor.java create mode 100644 lib/src/main/java/net/tomatentum/marinara/registry/InteractionExecutor.java create mode 100644 lib/src/main/java/net/tomatentum/marinara/registry/ProcessorInteractionExecutor.java diff --git a/lib/src/main/java/net/tomatentum/marinara/Marinara.java b/lib/src/main/java/net/tomatentum/marinara/Marinara.java index 31b0786..19ac092 100644 --- a/lib/src/main/java/net/tomatentum/marinara/Marinara.java +++ b/lib/src/main/java/net/tomatentum/marinara/Marinara.java @@ -2,10 +2,15 @@ package net.tomatentum.marinara; import org.slf4j.Logger; +import net.tomatentum.marinara.interaction.InteractionType; +import net.tomatentum.marinara.interaction.processor.AutocompleteInteractionProcessor; +import net.tomatentum.marinara.interaction.processor.DirectInteractionProcessor; import net.tomatentum.marinara.reflection.ReflectedMethodFactory; import net.tomatentum.marinara.reflection.ReflectedMethodFactoryImpl; import net.tomatentum.marinara.registry.InteractionCheckRegistry; +import net.tomatentum.marinara.registry.InteractionExecutor; import net.tomatentum.marinara.registry.InteractionRegistry; +import net.tomatentum.marinara.registry.ProcessorInteractionExecutor; import net.tomatentum.marinara.util.LoggerUtil; import net.tomatentum.marinara.wrapper.LibraryWrapper; @@ -13,7 +18,7 @@ public class Marinara { private Logger logger = LoggerUtil.getLogger(getClass()); - public static Marinara load(LibraryWrapper wrapper) { + public static Marinara load(LibraryWrapper wrapper) { return new Marinara(wrapper); } @@ -21,12 +26,17 @@ public class Marinara { private ReflectedMethodFactory reflectedMethodFactory; private InteractionRegistry registry; private InteractionCheckRegistry checkRegistry; + private InteractionExecutor interactionExecutor; private Marinara(LibraryWrapper wrapper) { this.wrapper = wrapper; this.reflectedMethodFactory = new ReflectedMethodFactoryImpl(this); this.registry = new InteractionRegistry(this); this.checkRegistry = new InteractionCheckRegistry(); + this.interactionExecutor = new ProcessorInteractionExecutor(wrapper.createIdentifierProvider(), this) + .addProcessor(new DirectInteractionProcessor(InteractionType.COMMAND, InteractionType.BUTTON)) + .addProcessor(new AutocompleteInteractionProcessor()); + wrapper.subscribeInteractions(this.interactionExecutor::handle); logger.info("Marinara loaded successfully!"); } @@ -45,4 +55,9 @@ public class Marinara { public ReflectedMethodFactory getReflectedMethodFactory() { return this.reflectedMethodFactory; } + + public InteractionExecutor getInteractionExecutor() { + return interactionExecutor; + } + } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/commands/annotation/SlashCommandOption.java b/lib/src/main/java/net/tomatentum/marinara/interaction/commands/annotation/SlashCommandOption.java index e29c361..e4aff31 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/commands/annotation/SlashCommandOption.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/commands/annotation/SlashCommandOption.java @@ -5,6 +5,7 @@ import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; +import net.tomatentum.marinara.interaction.annotation.AutoComplete; import net.tomatentum.marinara.interaction.commands.option.SlashCommandOptionType; @Target({ElementType.ANNOTATION_TYPE}) @@ -14,11 +15,11 @@ public @interface SlashCommandOption { public String description() default ""; public SlashCommandOptionType type() default SlashCommandOptionType.STRING; public boolean required() default false; - public boolean autocomplete() default false; + public AutoComplete[] autocompletes() default {}; public Range range() default @Range; public CommandChoices choices() default @CommandChoices; - public static enum PlaceHolderEnum { + public enum PlaceHolderEnum { } } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/commands/option/AutocompleteOptionData.java b/lib/src/main/java/net/tomatentum/marinara/interaction/commands/option/AutocompleteOptionData.java new file mode 100644 index 0000000..9f3afc6 --- /dev/null +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/commands/option/AutocompleteOptionData.java @@ -0,0 +1,16 @@ +package net.tomatentum.marinara.interaction.commands.option; + +import java.util.Arrays; + +import net.tomatentum.marinara.interaction.commands.annotation.SlashCommandOption; + +public record AutocompleteOptionData(String name, Object input) { + + public String[] getAutocompleteRefs(SlashCommandOption[] options) { + return Arrays.stream(options) + .filter(o -> o.name().equals(this.name())) + .flatMap(o -> Arrays.stream(o.autocompletes())) + .map(a -> a.value()) + .toArray(String[]::new); + } +} diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/ident/InteractionIdentifier.java b/lib/src/main/java/net/tomatentum/marinara/interaction/ident/InteractionIdentifier.java index 6e87068..5f4e090 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/ident/InteractionIdentifier.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/ident/InteractionIdentifier.java @@ -73,7 +73,7 @@ public class InteractionIdentifier { @Override public boolean equals(Object obj) { - if (obj == null || !(obj instanceof InteractionIdentifier)) + if (!(obj instanceof InteractionIdentifier)) return false; InteractionIdentifier ident = (InteractionIdentifier) obj; if (!type().equals(ident.type())) @@ -83,11 +83,16 @@ public class InteractionIdentifier { return Objects.equals(parent(), ident.parent()); } + @Override + public int hashCode() { + return Objects.hash(type(), name(), parent()); + } + @Override public String toString() { if (parent() == null) return name(); - return "{}.{}".formatted(name(), parent().toString()); + return "%s.%s".formatted(name(), parent().toString()); } public static class Builder { diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/ident/RootCommandIdentifier.java b/lib/src/main/java/net/tomatentum/marinara/interaction/ident/RootCommandIdentifier.java index 5563718..af82d3c 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/ident/RootCommandIdentifier.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/ident/RootCommandIdentifier.java @@ -13,9 +13,8 @@ public class RootCommandIdentifier extends SlashCommandIdentifier { String description, InteractionType type, SlashCommandOption[] options, - long[] serverIds, - String[] autocompleteRef) { - super(parent, name, description, type, options, autocompleteRef); + long[] serverIds) { + super(parent, name, description, type, options); this.serverIds = serverIds; } @@ -92,8 +91,7 @@ public class RootCommandIdentifier extends SlashCommandIdentifier { description, InteractionType.COMMAND, options, - serverIds, - autocompleteRef); + serverIds); } } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/ident/SlashCommandIdentifier.java b/lib/src/main/java/net/tomatentum/marinara/interaction/ident/SlashCommandIdentifier.java index 1e7ebf1..1e6b54e 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/ident/SlashCommandIdentifier.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/ident/SlashCommandIdentifier.java @@ -6,33 +6,21 @@ import net.tomatentum.marinara.interaction.commands.annotation.SlashCommandOptio public class SlashCommandIdentifier extends InteractionIdentifier { private SlashCommandOption[] options; - private String[] autocompleteRef; protected SlashCommandIdentifier( InteractionIdentifier parent, String name, String description, InteractionType type, - SlashCommandOption[] options, - String[] autocompleteRef - ) { + SlashCommandOption[] options) { super(parent, name, description, type); this.options = options; - this.autocompleteRef = autocompleteRef; } public SlashCommandOption[] options() { return this.options; } - public String[] autocompleteRef() { - return this.autocompleteRef; - } - public SlashCommandIdentifier autocompleteRef(String[] autocompleteRef) { - this.autocompleteRef = autocompleteRef; - return this; - } - public static class Builder { private InteractionIdentifier parent; private String name; @@ -91,8 +79,7 @@ public class SlashCommandIdentifier extends InteractionIdentifier { name, description, InteractionType.COMMAND, - options, - autocompleteRef); + options); } } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java index 82569a2..af100e5 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java @@ -29,11 +29,15 @@ public class AutoCompleteInteractionMethod extends InteractionMethod { @Override public Object getParameter(Object context, int index) { Class type = method().getParameterTypes()[index+1]; - Object autocompleteOptionValue = marinara.getWrapper().getContextObjectProvider().getAutocompleteFocusedOption(context); - if (autocompleteOptionValue != null) + Object contextObject = marinara.getWrapper().getContextObjectProvider().getInteractionContextObject(context, type); + if (contextObject != null) + return contextObject; + + Object autocompleteOptionValue = marinara.getWrapper().getContextObjectProvider().getAutocompleteFocusedOption(context).input(); + if (type.isInstance(autocompleteOptionValue)) return autocompleteOptionValue; - return marinara.getWrapper().getContextObjectProvider().getInteractionContextObject(context, type); + return null; } @Override @@ -50,11 +54,11 @@ public class AutoCompleteInteractionMethod extends InteractionMethod { @Override public Optional produce(Marinara marinara, Method method, Object containingObject) { ReflectedMethod rMethod = null; - if ((containingObject instanceof InteractionHandler) && + if ((containingObject instanceof InteractionHandler iHandler) && method.isAnnotationPresent(AutoComplete.class) && !(method.isAnnotationPresent(SlashCommand.class) || method.isAnnotationPresent(SubCommand.class))) - rMethod = new AutoCompleteInteractionMethod(method, (InteractionHandler) containingObject, marinara); + rMethod = new AutoCompleteInteractionMethod(method, iHandler, marinara); return Optional.ofNullable(rMethod); } @@ -63,9 +67,8 @@ public class AutoCompleteInteractionMethod extends InteractionMethod { public void addParser(ReflectedMethod method, List parser) { super.addParser(method, parser); - AutoCompleteInteractionMethod imethod = (AutoCompleteInteractionMethod) method; parser.add( - new AutocompleteParser(method.method(), x -> imethod.autocompleteRef = x[0]) + new AutocompleteParser(method.method(), x -> ((AutoCompleteInteractionMethod) method).autocompleteRef = x[0]) ); } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/InteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/InteractionMethod.java index 2e56a7e..caaa884 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/InteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/InteractionMethod.java @@ -51,7 +51,7 @@ public abstract class InteractionMethod extends ReflectedMethod { return this.appliedChecks; } - public static abstract class Factory implements ReflectedMethodFactory.Factory { + public abstract static class Factory implements ReflectedMethodFactory.Factory { @Override public void addParser(ReflectedMethod method, List parser) { diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java index 816308c..a6bd130 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java @@ -11,7 +11,6 @@ import net.tomatentum.marinara.interaction.commands.annotation.SubCommand; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; import net.tomatentum.marinara.interaction.ident.SlashCommandIdentifier; import net.tomatentum.marinara.parser.AnnotationParser; -import net.tomatentum.marinara.parser.AutocompleteParser; import net.tomatentum.marinara.parser.SlashCommandParser; import net.tomatentum.marinara.reflection.ReflectedMethod; @@ -38,10 +37,10 @@ public class SlashCommandInteractionMethod extends InteractionMethod { @Override public Optional produce(Marinara marinara, Method method, Object containingObject) { ReflectedMethod rMethod = null; - if ((containingObject instanceof InteractionHandler) && + if ((containingObject instanceof InteractionHandler iHandler) && (method.isAnnotationPresent(SlashCommand.class) || method.isAnnotationPresent(SubCommand.class))) - rMethod = new SlashCommandInteractionMethod(method, (InteractionHandler) containingObject, marinara); + rMethod = new SlashCommandInteractionMethod(method, iHandler, marinara); return Optional.ofNullable(rMethod); } @@ -49,12 +48,8 @@ public class SlashCommandInteractionMethod extends InteractionMethod { public void addParser(ReflectedMethod method, List parser) { super.addParser(method, parser); - SlashCommandInteractionMethod imethod = (SlashCommandInteractionMethod) method; parser.add( - new SlashCommandParser(method.method(), x -> imethod.interactionIdentifier = x) - ); - parser.add( - new AutocompleteParser(method.method(), x -> imethod.interactionIdentifier.autocompleteRef(x)) + new SlashCommandParser(method.method(), x -> ((SlashCommandInteractionMethod) method).interactionIdentifier = x) ); } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/processor/AutocompleteInteractionProcessor.java b/lib/src/main/java/net/tomatentum/marinara/interaction/processor/AutocompleteInteractionProcessor.java new file mode 100644 index 0000000..4483659 --- /dev/null +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/processor/AutocompleteInteractionProcessor.java @@ -0,0 +1,46 @@ +package net.tomatentum.marinara.interaction.processor; + +import java.util.Arrays; +import java.util.List; +import java.util.Objects; +import java.util.Optional; + +import net.tomatentum.marinara.Marinara; +import net.tomatentum.marinara.interaction.InteractionType; +import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; +import net.tomatentum.marinara.interaction.ident.SlashCommandIdentifier; +import net.tomatentum.marinara.registry.InteractionEntry; + +public class AutocompleteInteractionProcessor implements InteractionProcessor { + + @Override + public void process(Object context, InteractionIdentifier identifier, Marinara marinara) { + if (!identifier.type().equals(InteractionType.AUTOCOMPLETE)) + return; + Optional entry = marinara.getRegistry().findFor(convertToCommandIdentifier(identifier)); + if (entry.isPresent() && entry.get().identifier() instanceof SlashCommandIdentifier sIdent) { + List autocompleteRefs = Arrays.asList(marinara.getWrapper().getContextObjectProvider() + .getAutocompleteFocusedOption(context).getAutocompleteRefs(sIdent.options())); + List results = marinara.getRegistry().interactions().stream() + .filter(e -> e.type().equals(InteractionType.AUTOCOMPLETE)) + .filter(e -> autocompleteRefs.contains(e.identifier().name())) + .map(e -> e.runAll(context)) + .flatMap(Arrays::stream) + .filter(Objects::nonNull) + .toList(); + if (!results.isEmpty()) + marinara.getWrapper().respondAutocomplete(context, results); + } + } + + private InteractionIdentifier convertToCommandIdentifier(InteractionIdentifier identifier) { + if (Objects.isNull(identifier)) + return null; + return InteractionIdentifier.builder() + .type(InteractionType.COMMAND) + .name(identifier.name()) + .parent(convertToCommandIdentifier(identifier.parent())) + .build(); + } + +} diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/processor/DirectInteractionProcessor.java b/lib/src/main/java/net/tomatentum/marinara/interaction/processor/DirectInteractionProcessor.java new file mode 100644 index 0000000..b2d2296 --- /dev/null +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/processor/DirectInteractionProcessor.java @@ -0,0 +1,32 @@ +package net.tomatentum.marinara.interaction.processor; + +import java.util.Set; + +import org.slf4j.Logger; + +import net.tomatentum.marinara.Marinara; +import net.tomatentum.marinara.interaction.InteractionType; +import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; +import net.tomatentum.marinara.util.LoggerUtil; + +public class DirectInteractionProcessor implements InteractionProcessor { + + private Logger logger = LoggerUtil.getLogger(getClass()); + private Set types; + + public DirectInteractionProcessor(InteractionType... types) { + this.types = Set.of(types); + } + + @Override + public void process(Object context, InteractionIdentifier identifier, Marinara marinara) { + if (!types.contains(identifier.type())) + return; + logger.debug("Processing {} : {} with context {}", identifier, identifier.type(), context); + marinara.getRegistry().interactions().stream() + .filter(e -> e.identifier().equals(identifier)) + .findFirst() + .ifPresent(e -> e.runAll(context)); + } + +} diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/processor/InteractionProcessor.java b/lib/src/main/java/net/tomatentum/marinara/interaction/processor/InteractionProcessor.java new file mode 100644 index 0000000..24f0bbc --- /dev/null +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/processor/InteractionProcessor.java @@ -0,0 +1,10 @@ +package net.tomatentum.marinara.interaction.processor; + +import net.tomatentum.marinara.Marinara; +import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; + +public interface InteractionProcessor { + + void process(Object context, InteractionIdentifier identifier, Marinara marinara); + +} diff --git a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionEntry.java b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionEntry.java index 310aa8b..5f0828e 100644 --- a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionEntry.java +++ b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionEntry.java @@ -1,8 +1,10 @@ package net.tomatentum.marinara.registry; +import java.util.Arrays; import java.util.HashSet; import java.util.Optional; import java.util.Set; +import java.util.stream.Stream; import org.slf4j.Logger; @@ -34,22 +36,25 @@ public class InteractionEntry { } public InteractionEntry addMethod(InteractionMethod method) { - InteractionIdentifier identifier = method.identifier(); + InteractionIdentifier midentifier = method.identifier(); - if (!this.identifier().equals(identifier)) + if (!this.identifier().equals(midentifier)) throw new IllegalArgumentException("Method's identifier did not equal the entry's identifier"); this.methods.add(method); - InteractionIdentifier.tryAddDescriptions(identifier, identifier); + InteractionIdentifier.tryAddDescriptions(midentifier, midentifier); logger.debug("Added method {} to entry {}", method.method().getName(), this.identifier); return this; } - public void runAll(Object context) { - this.methods.stream().forEach(x -> { - logger.debug("Running Method {} from {} with context {}", x.toString(), this.toString(), context.toString()); - x.run(context); - }); + public Object[] runAll(Object context) { + return this.methods.stream() + .map(x -> { + logger.debug("Running Method {} from {} with context {}", x, this, context); + return x.run(context); + }) + .flatMap(o -> o instanceof Object[] oArray ? Arrays.stream(oArray) : Stream.of(o)) + .toArray(); } @Override @@ -60,6 +65,11 @@ public class InteractionEntry { return other.identifier().equals(identifier()); } + @Override + public int hashCode() { + return this.identifier().hashCode(); + } + @Override public String toString() { return "InteractionEntry(%s)".formatted(identifier().toString()); diff --git a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionExecutor.java b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionExecutor.java new file mode 100644 index 0000000..02d52bc --- /dev/null +++ b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionExecutor.java @@ -0,0 +1,7 @@ +package net.tomatentum.marinara.registry; + +public interface InteractionExecutor { + + void handle(Object context); + +} diff --git a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java index e9acd40..0c7b244 100644 --- a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java +++ b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java @@ -18,7 +18,6 @@ import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; import net.tomatentum.marinara.interaction.ident.RootCommandIdentifier; import net.tomatentum.marinara.util.LoggerUtil; import net.tomatentum.marinara.util.ObjectAggregator; -import net.tomatentum.marinara.wrapper.IdentifierProvider; import net.tomatentum.marinara.interaction.methods.AutoCompleteInteractionMethod; import net.tomatentum.marinara.interaction.methods.InteractionMethod; import net.tomatentum.marinara.interaction.methods.SlashCommandInteractionMethod; @@ -28,13 +27,10 @@ public class InteractionRegistry { private Logger logger = LoggerUtil.getLogger(getClass()); private Set interactions; private Marinara marinara; - private IdentifierProvider identifierProvider; public InteractionRegistry(Marinara marinara) { this.interactions = new HashSet<>(); this.marinara = marinara; - this.identifierProvider = marinara.getWrapper().createIdentifierProvider(); - marinara.getWrapper().subscribeInteractions(this::handle); marinara.getReflectedMethodFactory() .addFactory(new AutoCompleteInteractionMethod.Factory()) .addFactory(new SlashCommandInteractionMethod.Factory()) @@ -72,19 +68,13 @@ public class InteractionRegistry { marinara.getWrapper().getRegisterer().register(defs); } - public void handle(Object context) { - logger.debug("Received {} interaction ", context); - interactions.forEach((e) -> { - if (e.identifier().equals(this.identifierProvider.provide(context, this))) { - logger.info("Running {} interaction using {}\ncontext: {}", e.type(), e.toString(), context.toString()); - e.runAll(context); - } - }); - } - public Optional findFor(InteractionIdentifier identifier) { return this.interactions.stream() .filter(x -> x.identifier().equals(identifier)) .findFirst(); } + + public Set interactions() { + return this.interactions; + } } diff --git a/lib/src/main/java/net/tomatentum/marinara/registry/ProcessorInteractionExecutor.java b/lib/src/main/java/net/tomatentum/marinara/registry/ProcessorInteractionExecutor.java new file mode 100644 index 0000000..03c2785 --- /dev/null +++ b/lib/src/main/java/net/tomatentum/marinara/registry/ProcessorInteractionExecutor.java @@ -0,0 +1,41 @@ +package net.tomatentum.marinara.registry; + +import java.util.HashSet; +import java.util.Set; + +import org.slf4j.Logger; + +import net.tomatentum.marinara.Marinara; +import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; +import net.tomatentum.marinara.interaction.processor.InteractionProcessor; +import net.tomatentum.marinara.util.LoggerUtil; +import net.tomatentum.marinara.wrapper.IdentifierProvider; + +public class ProcessorInteractionExecutor implements InteractionExecutor { + + private Logger logger = LoggerUtil.getLogger(getClass()); + + private Set processors; + private IdentifierProvider identifierProvider; + private Marinara marinara; + + public ProcessorInteractionExecutor(IdentifierProvider identifierProvider, Marinara marinara) { + this.processors = new HashSet<>(); + this.identifierProvider = identifierProvider; + this.marinara = marinara; + } + + public ProcessorInteractionExecutor addProcessor(InteractionProcessor processor) { + this.processors.add(processor); + return this; + } + + @Override + public void handle(Object context) { + logger.debug("Received {} interaction ", context); + InteractionIdentifier identifier = this.identifierProvider.provide(context); + logger.debug("Processing {} : {} interaction ", identifier, identifier.type()); + processors.forEach(x -> x.process(context, identifier, this.marinara)); + } + +} diff --git a/lib/src/main/java/net/tomatentum/marinara/wrapper/ContextObjectProvider.java b/lib/src/main/java/net/tomatentum/marinara/wrapper/ContextObjectProvider.java index 27cbaa4..05afcc8 100644 --- a/lib/src/main/java/net/tomatentum/marinara/wrapper/ContextObjectProvider.java +++ b/lib/src/main/java/net/tomatentum/marinara/wrapper/ContextObjectProvider.java @@ -1,5 +1,7 @@ package net.tomatentum.marinara.wrapper; +import net.tomatentum.marinara.interaction.commands.option.AutocompleteOptionData; + public interface ContextObjectProvider { public Object convertCommandOption(Object context, String optionName); @@ -7,5 +9,5 @@ public interface ContextObjectProvider { public Object getComponentContextObject(Object context, Class type); public Object getInteractionContextObject(Object context, Class type); - public Object getAutocompleteFocusedOption(Object context); + public AutocompleteOptionData getAutocompleteFocusedOption(Object context); } diff --git a/lib/src/main/java/net/tomatentum/marinara/wrapper/IdentifierProvider.java b/lib/src/main/java/net/tomatentum/marinara/wrapper/IdentifierProvider.java index 1c5f544..0adbee9 100644 --- a/lib/src/main/java/net/tomatentum/marinara/wrapper/IdentifierProvider.java +++ b/lib/src/main/java/net/tomatentum/marinara/wrapper/IdentifierProvider.java @@ -11,7 +11,6 @@ import org.slf4j.Logger; import io.leangen.geantyref.GenericTypeReflector; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; -import net.tomatentum.marinara.registry.InteractionRegistry; import net.tomatentum.marinara.util.LoggerUtil; import net.tomatentum.marinara.util.ReflectionUtil; @@ -30,30 +29,30 @@ public class IdentifierProvider { if (conv.getClass().getName().contains("$$Lambda")) throw new IllegalArgumentException("Lambdas cannot be used for IdentifierConverter because of Type erasure."); Type type = GenericTypeReflector.getExactSuperType(conv.getClass(), Converter.class); - Type parameterType = (Class) ((ParameterizedType) type).getActualTypeArguments()[0]; + Type parameterType = ((ParameterizedType) type).getActualTypeArguments()[0]; if (!(parameterType instanceof Class)) throw new IllegalArgumentException("Only full Class types are supported by IdentiferConverters"); this.converter.put((Class) parameterType, conv); } } - public InteractionIdentifier provide(Object context, InteractionRegistry registry) { + public InteractionIdentifier provide(Object context) { Type type = ReflectionUtil.getMostSpecificClass( converter.keySet().stream().filter(x -> x.isAssignableFrom(context.getClass())).toArray(Class[]::new), context.getClass()); if (type == null) - logger.debug("No Identifier converter found for context {}", context.getClass().toString()); + logger.debug("No Identifier converter found for context {}", context.getClass()); @SuppressWarnings("unchecked") Converter conv = (Converter) converter.get(type); - return conv.convert(context, registry); + return conv.convert(context); } @FunctionalInterface public interface Converter { - InteractionIdentifier convert(T context, InteractionRegistry registry); + InteractionIdentifier convert(T context); } public static class LambdaWrapper implements Converter { @@ -65,8 +64,8 @@ public class IdentifierProvider { } @Override - public InteractionIdentifier convert(T context, InteractionRegistry registry) { - return this.converter.convert(context, registry); + public InteractionIdentifier convert(T context) { + return this.converter.convert(context); } } diff --git a/lib/src/main/java/net/tomatentum/marinara/wrapper/LibraryWrapper.java b/lib/src/main/java/net/tomatentum/marinara/wrapper/LibraryWrapper.java index 5b3ba04..f5459da 100644 --- a/lib/src/main/java/net/tomatentum/marinara/wrapper/LibraryWrapper.java +++ b/lib/src/main/java/net/tomatentum/marinara/wrapper/LibraryWrapper.java @@ -12,7 +12,7 @@ public abstract class LibraryWrapper { } public void handleInteraction(Object context) { - interactionSubscriber.forEach((o) -> o.accept(context)); + interactionSubscriber.forEach(o -> o.accept(context)); } public void subscribeInteractions(Consumer consumer) { @@ -25,5 +25,6 @@ public abstract class LibraryWrapper { public abstract CommandRegisterer getRegisterer(); public abstract IdentifierProvider createIdentifierProvider(); public abstract ContextObjectProvider getContextObjectProvider(); + public abstract void respondAutocomplete(Object context, List options); } \ No newline at end of file diff --git a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/Discord4JContextObjectProvider.java b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/Discord4JContextObjectProvider.java index d16f789..081d1fa 100644 --- a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/Discord4JContextObjectProvider.java +++ b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/Discord4JContextObjectProvider.java @@ -5,7 +5,9 @@ import java.util.List; import discord4j.core.event.domain.interaction.ChatInputAutoCompleteEvent; import discord4j.core.event.domain.interaction.ChatInputInteractionEvent; import discord4j.core.event.domain.interaction.ComponentInteractionEvent; +import discord4j.core.event.domain.interaction.InteractionCreateEvent; import discord4j.core.object.command.ApplicationCommandInteractionOption; +import net.tomatentum.marinara.interaction.commands.option.AutocompleteOptionData; import net.tomatentum.marinara.interaction.commands.option.SlashCommandOptionType; import net.tomatentum.marinara.wrapper.ContextObjectProvider; @@ -79,24 +81,25 @@ public class Discord4JContextObjectProvider implements ContextObjectProvider { @Override public Object getInteractionContextObject(Object context, Class type) { - ComponentInteractionEvent componentInteractionEvent = (ComponentInteractionEvent) context; + InteractionCreateEvent interactionEvent = (InteractionCreateEvent) context; switch (type.getName()) { case "discord4j.core.object.entity.channel.MessageChannel": - return componentInteractionEvent.getInteraction().getChannel().block(); + return interactionEvent.getInteraction().getChannel().block(); case "discord4j.core.object.entity.Guild": - return componentInteractionEvent.getInteraction().getGuild().block(); + return interactionEvent.getInteraction().getGuild().block(); case "discord4j.core.object.entity.Member": - return componentInteractionEvent.getInteraction().getMember().orElse(null); + return interactionEvent.getInteraction().getMember().orElse(null); case "discord4j.core.object.entity.User": - return componentInteractionEvent.getInteraction().getUser(); + return interactionEvent.getInteraction().getUser(); + default: + return null; } - return null; } @Override - public Object getAutocompleteFocusedOption(Object context) { - ChatInputAutoCompleteEvent interaction = (ChatInputAutoCompleteEvent) context; - return getOptionValue(interaction.getFocusedOption()); + public AutocompleteOptionData getAutocompleteFocusedOption(Object context) { + ApplicationCommandInteractionOption option = ((ChatInputAutoCompleteEvent) context).getFocusedOption(); + return new AutocompleteOptionData(option.getName(), getOptionValue(option)); } } diff --git a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/Discord4JConverterSpec.java b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/Discord4JConverterSpec.java index 57a8d2e..33458e3 100644 --- a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/Discord4JConverterSpec.java +++ b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/Discord4JConverterSpec.java @@ -55,10 +55,10 @@ public class Discord4JConverterSpec implements CommandConverter.Spec 0) + .minLength((int) option.range().min()) .minValue(option.range().min()) - .maxLength(Double.valueOf(option.range().max()).intValue()) + .maxLength((int)option.range().max()) .maxValue(option.range().max()) .choices(choices) .build(); diff --git a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/Discord4JWrapper.java b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/Discord4JWrapper.java index d77dc3e..a4d1569 100644 --- a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/Discord4JWrapper.java +++ b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/Discord4JWrapper.java @@ -1,14 +1,16 @@ package net.tomatentum.marinara.wrapper.discord4j; import java.util.List; -import java.util.function.Function; +import java.util.function.UnaryOperator; import org.slf4j.Logger; import discord4j.core.GatewayDiscordClient; +import discord4j.core.event.domain.interaction.ChatInputAutoCompleteEvent; import discord4j.core.event.domain.interaction.InteractionCreateEvent; import discord4j.core.object.command.ApplicationCommandInteractionOption; import discord4j.core.object.command.ApplicationCommandOption.Type; +import discord4j.discordjson.json.ApplicationCommandOptionChoiceData; import discord4j.discordjson.json.ApplicationCommandRequest; import net.tomatentum.marinara.util.LoggerUtil; @@ -22,13 +24,12 @@ import net.tomatentum.marinara.wrapper.discord4j.identifierconverter.ButtonIdent import net.tomatentum.marinara.wrapper.discord4j.identifierconverter.SlashCommandIdentifierConverter; public class Discord4JWrapper extends LibraryWrapper { - - public static final Function, List> SUB_FILTER = (i) -> + public static final UnaryOperator> SUB_FILTER = i -> i.stream() .filter(o -> o.getType().equals(Type.SUB_COMMAND) || o.getType().equals(Type.SUB_COMMAND_GROUP)) .toList(); - public static final Function, List> ARG_FILTER = (i) -> + public static final UnaryOperator> ARG_FILTER = i -> i.stream() .filter(o -> !o.getType().equals(Type.SUB_COMMAND) && !o.getType().equals(Type.SUB_COMMAND_GROUP)) .toList(); @@ -71,4 +72,15 @@ public class Discord4JWrapper extends LibraryWrapper { return this.contextObjectProvider; } + @Override + public void respondAutocomplete(Object context, List options) { + if (context instanceof ChatInputAutoCompleteEvent event) { + List choices = options.stream() + .filter(ApplicationCommandOptionChoiceData.class::isInstance) + .map(o -> (ApplicationCommandOptionChoiceData)o) + .toList(); + event.respondWithSuggestions(choices); + } + } + } diff --git a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/AutocompleteIdentifierConverter.java b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/AutocompleteIdentifierConverter.java index 03f1bb1..f2bf8cc 100644 --- a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/AutocompleteIdentifierConverter.java +++ b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/AutocompleteIdentifierConverter.java @@ -1,53 +1,39 @@ package net.tomatentum.marinara.wrapper.discord4j.identifierconverter; import java.util.List; -import java.util.Optional; import discord4j.core.event.domain.interaction.ChatInputAutoCompleteEvent; import discord4j.core.object.command.ApplicationCommandInteractionOption; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; -import net.tomatentum.marinara.interaction.ident.SlashCommandIdentifier; -import net.tomatentum.marinara.registry.InteractionEntry; -import net.tomatentum.marinara.registry.InteractionRegistry; import net.tomatentum.marinara.wrapper.IdentifierProvider; import net.tomatentum.marinara.wrapper.discord4j.Discord4JWrapper; public class AutocompleteIdentifierConverter implements IdentifierProvider.Converter { @Override - public InteractionIdentifier convert(ChatInputAutoCompleteEvent context, InteractionRegistry registry) { + public InteractionIdentifier convert(ChatInputAutoCompleteEvent context) { List options = Discord4JWrapper.SUB_FILTER.apply(context.getOptions()); String commandName = context.getCommandName(); - InteractionIdentifier ident; if (!options.isEmpty()) { - List sub_options = Discord4JWrapper.SUB_FILTER.apply(options.getFirst().getOptions()); - if (!sub_options.isEmpty()) - ident = InteractionIdentifier.createHierarchy( - InteractionType.COMMAND, + List subOptions = Discord4JWrapper.SUB_FILTER.apply(options.getFirst().getOptions()); + if (!subOptions.isEmpty()) + return InteractionIdentifier.createHierarchy( + InteractionType.AUTOCOMPLETE, commandName, options.getFirst().getName(), - sub_options.getFirst().getName()); + subOptions.getFirst().getName()); else - ident = InteractionIdentifier.createHierarchy( - InteractionType.COMMAND, + return InteractionIdentifier.createHierarchy( + InteractionType.AUTOCOMPLETE, commandName, options.getFirst().getName()); }else - ident = InteractionIdentifier.createHierarchy( - InteractionType.COMMAND, + return InteractionIdentifier.createHierarchy( + InteractionType.AUTOCOMPLETE, commandName); - Optional entry = registry.findFor(ident); - if (entry.isPresent() && entry.get().identifier() instanceof SlashCommandIdentifier) { - SlashCommandIdentifier sIdent = (SlashCommandIdentifier) entry.get().identifier(); - return InteractionIdentifier.builder() - .type(InteractionType.AUTOCOMPLETE) - .name(sIdent.autocompleteRef()[0]) - .build(); - } - return null; } } diff --git a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/ButtonIdentifierConverter.java b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/ButtonIdentifierConverter.java index 148452a..8751d4f 100644 --- a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/ButtonIdentifierConverter.java +++ b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/ButtonIdentifierConverter.java @@ -3,13 +3,12 @@ package net.tomatentum.marinara.wrapper.discord4j.identifierconverter; import discord4j.core.event.domain.interaction.ButtonInteractionEvent; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; -import net.tomatentum.marinara.registry.InteractionRegistry; import net.tomatentum.marinara.wrapper.IdentifierProvider; public class ButtonIdentifierConverter implements IdentifierProvider.Converter { @Override - public InteractionIdentifier convert(ButtonInteractionEvent context, InteractionRegistry registry) { + public InteractionIdentifier convert(ButtonInteractionEvent context) { return InteractionIdentifier.builder().name(context.getCustomId()).type(InteractionType.BUTTON).build(); } diff --git a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/SlashCommandIdentifierConverter.java b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/SlashCommandIdentifierConverter.java index f82b016..612cd0a 100644 --- a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/SlashCommandIdentifierConverter.java +++ b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/SlashCommandIdentifierConverter.java @@ -6,14 +6,13 @@ import discord4j.core.event.domain.interaction.ChatInputInteractionEvent; import discord4j.core.object.command.ApplicationCommandInteractionOption; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; -import net.tomatentum.marinara.registry.InteractionRegistry; import net.tomatentum.marinara.wrapper.IdentifierProvider; import net.tomatentum.marinara.wrapper.discord4j.Discord4JWrapper; public class SlashCommandIdentifierConverter implements IdentifierProvider.Converter { @Override - public InteractionIdentifier convert(ChatInputInteractionEvent context, InteractionRegistry registry) { + public InteractionIdentifier convert(ChatInputInteractionEvent context) { List options = Discord4JWrapper.SUB_FILTER.apply(context.getOptions()); String commandName = context.getCommandName(); diff --git a/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/AutoCompleteTest.java b/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/AutoCompleteTest.java index 62a9259..2c20695 100644 --- a/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/AutoCompleteTest.java +++ b/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/AutoCompleteTest.java @@ -18,10 +18,10 @@ import net.tomatentum.marinara.Marinara; import net.tomatentum.marinara.wrapper.LibraryWrapper; import net.tomatentum.marinara.wrapper.discord4j.Discord4JWrapper; -public class AutoCompleteTest { +class AutoCompleteTest { @Test - public void testAutocomplete() { + void testAutocomplete() { ApplicationCommandInteractionOption optionMock = mock(); ChatInputAutoCompleteEvent autoCompleteEventMock = mock(); diff --git a/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/TestAutocomplete.java b/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/TestAutocomplete.java index c1b04a8..18c0965 100644 --- a/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/TestAutocomplete.java +++ b/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/TestAutocomplete.java @@ -6,23 +6,35 @@ import java.util.Collections; import discord4j.core.event.domain.interaction.ChatInputAutoCompleteEvent; import discord4j.core.event.domain.interaction.ChatInputInteractionEvent; +import discord4j.discordjson.json.ApplicationCommandOptionChoiceData; import net.tomatentum.marinara.interaction.InteractionHandler; import net.tomatentum.marinara.interaction.annotation.AutoComplete; import net.tomatentum.marinara.interaction.commands.annotation.SlashCommand; +import net.tomatentum.marinara.interaction.commands.annotation.SlashCommandOption; +import net.tomatentum.marinara.interaction.commands.option.SlashCommandOptionType; public class TestAutocomplete implements InteractionHandler { - @SlashCommand(name = "test") + @SlashCommand( + name = "test", + options = @SlashCommandOption( + name = "foo", + type = SlashCommandOptionType.STRING, + autocompletes = @AutoComplete("testAuto") + ) + ) @AutoComplete("testAuto") public void exec(ChatInputInteractionEvent context) { } @AutoComplete("testAuto") - public void autocomplete(ChatInputAutoCompleteEvent context, String value) { + public ApplicationCommandOptionChoiceData[] autocomplete(ChatInputAutoCompleteEvent context, String value) { System.out.println("Success!"); - assertEquals(value, "test"); - context.respondWithSuggestions(Collections.emptyList()); + assertEquals("test", value); + return new ApplicationCommandOptionChoiceData[]{ + ApplicationCommandOptionChoiceData.builder().name("TestValue").value("test").build() + }; } } diff --git a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/JavacordContextObjectProvider.java b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/JavacordContextObjectProvider.java index 0812f0c..c17a901 100644 --- a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/JavacordContextObjectProvider.java +++ b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/JavacordContextObjectProvider.java @@ -2,10 +2,12 @@ package net.tomatentum.marinara.wrapper.javacord; import org.javacord.api.interaction.AutocompleteInteraction; import org.javacord.api.interaction.ButtonInteraction; +import org.javacord.api.interaction.InteractionBase; import org.javacord.api.interaction.SlashCommandInteraction; import org.javacord.api.interaction.SlashCommandInteractionOption; import org.javacord.api.interaction.SlashCommandOptionType; +import net.tomatentum.marinara.interaction.commands.option.AutocompleteOptionData; import net.tomatentum.marinara.wrapper.ContextObjectProvider; public class JavacordContextObjectProvider implements ContextObjectProvider { @@ -16,14 +18,14 @@ public class JavacordContextObjectProvider implements ContextObjectProvider { return null; SlashCommandInteraction interaction = (SlashCommandInteraction) context; if (!interaction.getArguments().isEmpty()) - return getOptionValue(interaction.getOptionByName(optionName).get()); + return getOptionValue(interaction.getOptionByName(optionName).orElse(null)); SlashCommandInteractionOption subCommandOption = interaction.getOptions().getFirst(); if (!subCommandOption.getOptions().isEmpty()) subCommandOption = subCommandOption.getOptions().getFirst(); - return getOptionValue(subCommandOption.getOptionByName(optionName).get()); + return getOptionValue(subCommandOption.getOptionByName(optionName).orElse(null)); } private Object getOptionValue(SlashCommandInteractionOption option) { @@ -89,7 +91,7 @@ public class JavacordContextObjectProvider implements ContextObjectProvider { @Override public Object getInteractionContextObject(Object context, Class type) { - ButtonInteraction button = (ButtonInteraction) context; + InteractionBase button = (InteractionBase) context; switch (type.getName()) { case "org.javacord.api.entity.channel.TextChannel": return button.getChannel().orElse(null); @@ -102,9 +104,9 @@ public class JavacordContextObjectProvider implements ContextObjectProvider { } @Override - public Object getAutocompleteFocusedOption(Object context) { - AutocompleteInteraction interaction = (AutocompleteInteraction) context; - return getOptionValue(interaction.getFocusedOption()); + public AutocompleteOptionData getAutocompleteFocusedOption(Object context) { + SlashCommandInteractionOption option = ((AutocompleteInteraction) context).getFocusedOption(); + return new AutocompleteOptionData(option.getName(), getOptionValue(option)); } } diff --git a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/JavacordConverterSpec.java b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/JavacordConverterSpec.java index 0fe16f5..76f1d25 100644 --- a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/JavacordConverterSpec.java +++ b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/JavacordConverterSpec.java @@ -50,10 +50,10 @@ public class JavacordConverterSpec implements CommandConverter.Spec 0) + .setMinLength((long) option.range().min()) .setDecimalMinValue(option.range().min()) - .setMaxLength(Double.valueOf(option.range().max()).longValue()) + .setMaxLength((long) option.range().max()) .setDecimalMaxValue(option.range().max()) .setChoices(choices) .build(); diff --git a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/JavacordWrapper.java b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/JavacordWrapper.java index fa7a3f5..0bf1718 100644 --- a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/JavacordWrapper.java +++ b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/JavacordWrapper.java @@ -1,7 +1,11 @@ package net.tomatentum.marinara.wrapper.javacord; +import java.util.List; + import org.javacord.api.DiscordApi; +import org.javacord.api.interaction.AutocompleteInteraction; import org.javacord.api.interaction.SlashCommandBuilder; +import org.javacord.api.interaction.SlashCommandOptionChoice; import org.slf4j.Logger; import net.tomatentum.marinara.wrapper.CommandConverter; @@ -27,7 +31,7 @@ public class JavacordWrapper extends LibraryWrapper { if (api != null) { this.commandRegisterer = CommandRegisterer.of(new JavacordRegistererStrategy(api), converter); - api.addInteractionCreateListener((e) -> handleInteraction(e.getInteraction())); + api.addInteractionCreateListener(e -> handleInteraction(e.getInteraction())); }else logger.warn("DiscordApi was null so no Events were subscribed to."); logger.info("Javacord wrapper loaded!"); @@ -52,4 +56,15 @@ public class JavacordWrapper extends LibraryWrapper { return contextObjectProvider; } + @Override + public void respondAutocomplete(Object context, List options) { + if (context instanceof AutocompleteInteraction interaction) { + List choices = options.stream() + .filter(SlashCommandOptionChoice.class::isInstance) + .map(o -> (SlashCommandOptionChoice)o) + .toList(); + interaction.respondWithChoices(choices); + } + } + } diff --git a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/AutocompleteIdentifierConverter.java b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/AutocompleteIdentifierConverter.java index 3c1b7da..38da7ca 100644 --- a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/AutocompleteIdentifierConverter.java +++ b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/AutocompleteIdentifierConverter.java @@ -1,53 +1,39 @@ package net.tomatentum.marinara.wrapper.javacord.identifierconverter; import java.util.List; -import java.util.Optional; import org.javacord.api.interaction.AutocompleteInteraction; import org.javacord.api.interaction.SlashCommandInteractionOption; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; -import net.tomatentum.marinara.interaction.ident.SlashCommandIdentifier; -import net.tomatentum.marinara.registry.InteractionEntry; -import net.tomatentum.marinara.registry.InteractionRegistry; import net.tomatentum.marinara.wrapper.IdentifierProvider; public class AutocompleteIdentifierConverter implements IdentifierProvider.Converter { @Override - public InteractionIdentifier convert(AutocompleteInteraction context, InteractionRegistry registry) { + public InteractionIdentifier convert(AutocompleteInteraction context) { List options = context.getOptions(); String commandName = context.getCommandName(); - InteractionIdentifier ident; if (!options.isEmpty()) { - List sub_options = context.getOptions().getFirst().getOptions(); - if (!sub_options.isEmpty()) - ident = InteractionIdentifier.createHierarchy( - InteractionType.COMMAND, + List subOptions = context.getOptions().getFirst().getOptions(); + if (!subOptions.isEmpty()) + return InteractionIdentifier.createHierarchy( + InteractionType.AUTOCOMPLETE, commandName, options.getFirst().getName(), - sub_options.getFirst().getName()); + subOptions.getFirst().getName()); else - ident = InteractionIdentifier.createHierarchy( - InteractionType.COMMAND, + return InteractionIdentifier.createHierarchy( + InteractionType.AUTOCOMPLETE, commandName, options.getFirst().getName()); }else - ident = InteractionIdentifier.createHierarchy( - InteractionType.COMMAND, + return InteractionIdentifier.createHierarchy( + InteractionType.AUTOCOMPLETE, commandName); - Optional entry = registry.findFor(ident); - if (entry.isPresent() && entry.get().identifier() instanceof SlashCommandIdentifier) { - SlashCommandIdentifier sIdent = (SlashCommandIdentifier) entry.get().identifier(); - return InteractionIdentifier.builder() - .type(InteractionType.AUTOCOMPLETE) - .name(sIdent.autocompleteRef()[0]) - .build(); - } - return null; } } diff --git a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/ButtonIdentifierConverter.java b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/ButtonIdentifierConverter.java index e9e7155..209ce32 100644 --- a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/ButtonIdentifierConverter.java +++ b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/ButtonIdentifierConverter.java @@ -4,13 +4,12 @@ import org.javacord.api.interaction.ButtonInteraction; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; -import net.tomatentum.marinara.registry.InteractionRegistry; import net.tomatentum.marinara.wrapper.IdentifierProvider; public class ButtonIdentifierConverter implements IdentifierProvider.Converter { @Override - public InteractionIdentifier convert(ButtonInteraction context, InteractionRegistry registry) { + public InteractionIdentifier convert(ButtonInteraction context) { return InteractionIdentifier.builder().name(context.getCustomId()).type(InteractionType.BUTTON).build(); } diff --git a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/SlashCommandIdentifierConverter.java b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/SlashCommandIdentifierConverter.java index 84ab246..4b90bd1 100644 --- a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/SlashCommandIdentifierConverter.java +++ b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/SlashCommandIdentifierConverter.java @@ -7,13 +7,12 @@ import org.javacord.api.interaction.SlashCommandInteractionOption; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; -import net.tomatentum.marinara.registry.InteractionRegistry; import net.tomatentum.marinara.wrapper.IdentifierProvider; public class SlashCommandIdentifierConverter implements IdentifierProvider.Converter { @Override - public InteractionIdentifier convert(SlashCommandInteraction context, InteractionRegistry registry) { + public InteractionIdentifier convert(SlashCommandInteraction context) { List options = context.getOptions(); String commandName = context.getCommandName(); if (!options.isEmpty()) { diff --git a/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/TestAutocomplete.java b/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/TestAutocomplete.java index bb56c25..da37684 100644 --- a/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/TestAutocomplete.java +++ b/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/TestAutocomplete.java @@ -6,17 +6,27 @@ import java.util.Collections; import org.javacord.api.event.interaction.SlashCommandCreateEvent; import org.javacord.api.interaction.AutocompleteInteraction; +import org.javacord.api.interaction.SlashCommandInteraction; import net.tomatentum.marinara.interaction.InteractionHandler; import net.tomatentum.marinara.interaction.annotation.AutoComplete; import net.tomatentum.marinara.interaction.commands.annotation.SlashCommand; +import net.tomatentum.marinara.interaction.commands.annotation.SlashCommandOption; +import net.tomatentum.marinara.interaction.commands.option.SlashCommandOptionType; public class TestAutocomplete implements InteractionHandler { - @SlashCommand(name = "test") + @SlashCommand( + name = "test", + options = @SlashCommandOption( + name = "foo", + type = SlashCommandOptionType.STRING, + autocompletes = @AutoComplete("testAuto") + ) + ) @AutoComplete("testAuto") - public void exec(SlashCommandCreateEvent context) { - + public void exec(SlashCommandInteraction context) { + } @AutoComplete("testAuto") -- 2.47.2 From 0b7b607a23e7b93320c40875dacf20a204a0259f Mon Sep 17 00:00:00 2001 From: tueem Date: Sun, 6 Apr 2025 13:14:22 +0200 Subject: [PATCH 11/18] refactor(wrapper): improve Converter structure --- .../AutocompleteIdentifierConverter.java | 35 ++++++++-------- .../SlashCommandIdentifierConverter.java | 37 ++++++++--------- .../AutocompleteIdentifierConverter.java | 35 ++++++++-------- .../SlashCommandIdentifierConverter.java | 40 ++++++++++--------- 4 files changed, 76 insertions(+), 71 deletions(-) diff --git a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/AutocompleteIdentifierConverter.java b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/AutocompleteIdentifierConverter.java index f2bf8cc..34892a8 100644 --- a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/AutocompleteIdentifierConverter.java +++ b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/AutocompleteIdentifierConverter.java @@ -13,27 +13,28 @@ public class AutocompleteIdentifierConverter implements IdentifierProvider.Conve @Override public InteractionIdentifier convert(ChatInputAutoCompleteEvent context) { - List options = Discord4JWrapper.SUB_FILTER.apply(context.getOptions()); - String commandName = context.getCommandName(); + InteractionIdentifier last = InteractionIdentifier.builder() + .type(InteractionType.AUTOCOMPLETE) + .name(context.getCommandName()) + .build(); + List options = Discord4JWrapper.SUB_FILTER.apply(context.getOptions()); if (!options.isEmpty()) { + last = InteractionIdentifier.builder() + .type(InteractionType.AUTOCOMPLETE) + .name(options.getFirst().getName()) + .parent(last) + .build(); + List subOptions = Discord4JWrapper.SUB_FILTER.apply(options.getFirst().getOptions()); if (!subOptions.isEmpty()) - return InteractionIdentifier.createHierarchy( - InteractionType.AUTOCOMPLETE, - commandName, - options.getFirst().getName(), - subOptions.getFirst().getName()); - else - return InteractionIdentifier.createHierarchy( - InteractionType.AUTOCOMPLETE, - commandName, - options.getFirst().getName()); - }else - return InteractionIdentifier.createHierarchy( - InteractionType.AUTOCOMPLETE, - commandName); - + last = InteractionIdentifier.builder() + .type(InteractionType.AUTOCOMPLETE) + .name(subOptions.getFirst().getName()) + .parent(last) + .build(); + } + return last; } } diff --git a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/SlashCommandIdentifierConverter.java b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/SlashCommandIdentifierConverter.java index 612cd0a..b3fc627 100644 --- a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/SlashCommandIdentifierConverter.java +++ b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/identifierconverter/SlashCommandIdentifierConverter.java @@ -13,27 +13,28 @@ public class SlashCommandIdentifierConverter implements IdentifierProvider.Conve @Override public InteractionIdentifier convert(ChatInputInteractionEvent context) { + InteractionIdentifier last = InteractionIdentifier.builder() + .type(InteractionType.COMMAND) + .name(context.getCommandName()) + .build(); + List options = Discord4JWrapper.SUB_FILTER.apply(context.getOptions()); - String commandName = context.getCommandName(); - if (!options.isEmpty()) { - List sub_options = Discord4JWrapper.SUB_FILTER.apply(options.getFirst().getOptions()); - if (!sub_options.isEmpty()) - return InteractionIdentifier.createHierarchy( - InteractionType.COMMAND, - commandName, - options.getFirst().getName(), - sub_options.getFirst().getName()); - else - return InteractionIdentifier.createHierarchy( - InteractionType.COMMAND, - commandName, - options.getFirst().getName()); - }else - return InteractionIdentifier.createHierarchy( - InteractionType.COMMAND, - commandName); + last = InteractionIdentifier.builder() + .type(InteractionType.COMMAND) + .name(options.getFirst().getName()) + .parent(last) + .build(); + List subOptions = Discord4JWrapper.SUB_FILTER.apply(options.getFirst().getOptions()); + if (!subOptions.isEmpty()) + last = InteractionIdentifier.builder() + .type(InteractionType.COMMAND) + .name(subOptions.getFirst().getName()) + .parent(last) + .build(); + } + return last; } } diff --git a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/AutocompleteIdentifierConverter.java b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/AutocompleteIdentifierConverter.java index 38da7ca..4e6195e 100644 --- a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/AutocompleteIdentifierConverter.java +++ b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/AutocompleteIdentifierConverter.java @@ -13,27 +13,28 @@ public class AutocompleteIdentifierConverter implements IdentifierProvider.Conve @Override public InteractionIdentifier convert(AutocompleteInteraction context) { - List options = context.getOptions(); - String commandName = context.getCommandName(); + InteractionIdentifier last = InteractionIdentifier.builder() + .type(InteractionType.AUTOCOMPLETE) + .name(context.getCommandName()) + .build(); + List options = context.getOptions(); if (!options.isEmpty()) { + last = InteractionIdentifier.builder() + .type(InteractionType.AUTOCOMPLETE) + .name(options.getFirst().getName()) + .parent(last) + .build(); + List subOptions = context.getOptions().getFirst().getOptions(); if (!subOptions.isEmpty()) - return InteractionIdentifier.createHierarchy( - InteractionType.AUTOCOMPLETE, - commandName, - options.getFirst().getName(), - subOptions.getFirst().getName()); - else - return InteractionIdentifier.createHierarchy( - InteractionType.AUTOCOMPLETE, - commandName, - options.getFirst().getName()); - }else - return InteractionIdentifier.createHierarchy( - InteractionType.AUTOCOMPLETE, - commandName); - + last = InteractionIdentifier.builder() + .type(InteractionType.AUTOCOMPLETE) + .name(subOptions.getFirst().getName()) + .parent(last) + .build(); + } + return last; } } diff --git a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/SlashCommandIdentifierConverter.java b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/SlashCommandIdentifierConverter.java index 4b90bd1..a6f7d5b 100644 --- a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/SlashCommandIdentifierConverter.java +++ b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/identifierconverter/SlashCommandIdentifierConverter.java @@ -13,26 +13,28 @@ public class SlashCommandIdentifierConverter implements IdentifierProvider.Conve @Override public InteractionIdentifier convert(SlashCommandInteraction context) { - List options = context.getOptions(); - String commandName = context.getCommandName(); - if (!options.isEmpty()) { - List sub_options = context.getOptions().getFirst().getOptions(); - if (!sub_options.isEmpty()) - return InteractionIdentifier.createHierarchy( - InteractionType.COMMAND, - commandName, - options.getFirst().getName(), - sub_options.getFirst().getName()); - else - return InteractionIdentifier.createHierarchy( - InteractionType.COMMAND, - commandName, - options.getFirst().getName()); - }else - return InteractionIdentifier.createHierarchy( - InteractionType.COMMAND, - commandName); + InteractionIdentifier last = InteractionIdentifier.builder() + .type(InteractionType.COMMAND) + .name(context.getCommandName()) + .build(); + List options = context.getOptions(); + if (!options.isEmpty()) { + last = InteractionIdentifier.builder() + .type(InteractionType.COMMAND) + .name(options.getFirst().getName()) + .parent(last) + .build(); + + List subOptions = context.getOptions().getFirst().getOptions(); + if (!subOptions.isEmpty()) + last = InteractionIdentifier.builder() + .type(InteractionType.COMMAND) + .name(subOptions.getFirst().getName()) + .parent(last) + .build(); + } + return last; } } -- 2.47.2 From 60ead419e28788c6951336024560fee3e0828e4a Mon Sep 17 00:00:00 2001 From: tueem Date: Sun, 6 Apr 2025 13:31:31 +0200 Subject: [PATCH 12/18] refactor(core): consistency --- .../components/methods/ButtonInteractionMethod.java | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/components/methods/ButtonInteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/components/methods/ButtonInteractionMethod.java index 81fe0d0..7fd45a5 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/components/methods/ButtonInteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/components/methods/ButtonInteractionMethod.java @@ -43,9 +43,9 @@ public class ButtonInteractionMethod extends InteractionMethod { public Optional produce(Marinara marinara, Method method, Object containingObject) { ReflectedMethod rMethod = null; if (method.isAnnotationPresent(Button.class) && - (containingObject instanceof InteractionHandler) + (containingObject instanceof InteractionHandler iHandler) ) - rMethod = new ButtonInteractionMethod(method, (InteractionHandler) containingObject, marinara); + rMethod = new ButtonInteractionMethod(method, iHandler, marinara); return Optional.ofNullable(rMethod); } @@ -54,9 +54,8 @@ public class ButtonInteractionMethod extends InteractionMethod { public void addParser(ReflectedMethod method, List parser) { super.addParser(method, parser); - ButtonInteractionMethod imethod = (ButtonInteractionMethod) method; parser.add( - new ButtonParser(method.method(), x -> imethod.customId = x) + new ButtonParser(method.method(), x -> ((ButtonInteractionMethod) method).customId = x) ); } -- 2.47.2 From 070319853aff34a1d72286a6b842a7390755c95b Mon Sep 17 00:00:00 2001 From: tueem Date: Mon, 7 Apr 2025 00:35:06 +0200 Subject: [PATCH 13/18] refactor(core): restructure MethodProcessors --- .../net/tomatentum/marinara/Marinara.java | 16 ++++---- .../AutocompleteInteractionProcessor.java | 21 ++++++---- .../processor/DirectInteractionProcessor.java | 23 ++++------- .../processor/InteractionMethodProcessor.java | 35 ++++++++++++++++ .../processor/InteractionProcessor.java | 10 ----- .../marinara/reflection/MethodExecutor.java | 7 ++++ .../marinara/reflection/MethodProcessor.java | 7 ++++ .../reflection/ProcessorContainer.java | 7 ++++ .../reflection/ProcessorMethodExecutor.java | 32 +++++++++++++++ .../registry/InteractionExecutor.java | 7 ---- .../ProcessorInteractionExecutor.java | 41 ------------------- 11 files changed, 120 insertions(+), 86 deletions(-) create mode 100644 lib/src/main/java/net/tomatentum/marinara/interaction/processor/InteractionMethodProcessor.java delete mode 100644 lib/src/main/java/net/tomatentum/marinara/interaction/processor/InteractionProcessor.java create mode 100644 lib/src/main/java/net/tomatentum/marinara/reflection/MethodExecutor.java create mode 100644 lib/src/main/java/net/tomatentum/marinara/reflection/MethodProcessor.java create mode 100644 lib/src/main/java/net/tomatentum/marinara/reflection/ProcessorContainer.java create mode 100644 lib/src/main/java/net/tomatentum/marinara/reflection/ProcessorMethodExecutor.java delete mode 100644 lib/src/main/java/net/tomatentum/marinara/registry/InteractionExecutor.java delete mode 100644 lib/src/main/java/net/tomatentum/marinara/registry/ProcessorInteractionExecutor.java diff --git a/lib/src/main/java/net/tomatentum/marinara/Marinara.java b/lib/src/main/java/net/tomatentum/marinara/Marinara.java index 19ac092..77c57d7 100644 --- a/lib/src/main/java/net/tomatentum/marinara/Marinara.java +++ b/lib/src/main/java/net/tomatentum/marinara/Marinara.java @@ -5,13 +5,14 @@ import org.slf4j.Logger; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.processor.AutocompleteInteractionProcessor; import net.tomatentum.marinara.interaction.processor.DirectInteractionProcessor; +import net.tomatentum.marinara.reflection.MethodExecutor; +import net.tomatentum.marinara.reflection.ProcessorMethodExecutor; import net.tomatentum.marinara.reflection.ReflectedMethodFactory; import net.tomatentum.marinara.reflection.ReflectedMethodFactoryImpl; import net.tomatentum.marinara.registry.InteractionCheckRegistry; -import net.tomatentum.marinara.registry.InteractionExecutor; import net.tomatentum.marinara.registry.InteractionRegistry; -import net.tomatentum.marinara.registry.ProcessorInteractionExecutor; import net.tomatentum.marinara.util.LoggerUtil; +import net.tomatentum.marinara.wrapper.IdentifierProvider; import net.tomatentum.marinara.wrapper.LibraryWrapper; public class Marinara { @@ -26,16 +27,17 @@ public class Marinara { private ReflectedMethodFactory reflectedMethodFactory; private InteractionRegistry registry; private InteractionCheckRegistry checkRegistry; - private InteractionExecutor interactionExecutor; + private MethodExecutor interactionExecutor; private Marinara(LibraryWrapper wrapper) { this.wrapper = wrapper; this.reflectedMethodFactory = new ReflectedMethodFactoryImpl(this); this.registry = new InteractionRegistry(this); this.checkRegistry = new InteractionCheckRegistry(); - this.interactionExecutor = new ProcessorInteractionExecutor(wrapper.createIdentifierProvider(), this) - .addProcessor(new DirectInteractionProcessor(InteractionType.COMMAND, InteractionType.BUTTON)) - .addProcessor(new AutocompleteInteractionProcessor()); + IdentifierProvider provider = wrapper.createIdentifierProvider(); + this.interactionExecutor = (MethodExecutor) new ProcessorMethodExecutor() + .addProcessor(new DirectInteractionProcessor(getRegistry(), provider, InteractionType.COMMAND, InteractionType.BUTTON)) + .addProcessor(new AutocompleteInteractionProcessor(this, provider)); wrapper.subscribeInteractions(this.interactionExecutor::handle); logger.info("Marinara loaded successfully!"); } @@ -56,7 +58,7 @@ public class Marinara { return this.reflectedMethodFactory; } - public InteractionExecutor getInteractionExecutor() { + public MethodExecutor getInteractionExecutor() { return interactionExecutor; } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/processor/AutocompleteInteractionProcessor.java b/lib/src/main/java/net/tomatentum/marinara/interaction/processor/AutocompleteInteractionProcessor.java index 4483659..b194946 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/processor/AutocompleteInteractionProcessor.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/processor/AutocompleteInteractionProcessor.java @@ -4,24 +4,31 @@ import java.util.Arrays; import java.util.List; import java.util.Objects; import java.util.Optional; +import java.util.Set; import net.tomatentum.marinara.Marinara; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; import net.tomatentum.marinara.interaction.ident.SlashCommandIdentifier; import net.tomatentum.marinara.registry.InteractionEntry; +import net.tomatentum.marinara.wrapper.IdentifierProvider; -public class AutocompleteInteractionProcessor implements InteractionProcessor { +public class AutocompleteInteractionProcessor extends InteractionMethodProcessor { + + private Marinara marinara; + + public AutocompleteInteractionProcessor(Marinara marinara, IdentifierProvider provider) { + super(provider, Set.of(InteractionType.AUTOCOMPLETE)); + this.marinara = marinara; + } @Override - public void process(Object context, InteractionIdentifier identifier, Marinara marinara) { - if (!identifier.type().equals(InteractionType.AUTOCOMPLETE)) - return; - Optional entry = marinara.getRegistry().findFor(convertToCommandIdentifier(identifier)); + public void processInteraction(Object context, InteractionIdentifier identifier) { + Optional entry = this.marinara.getRegistry().findFor(convertToCommandIdentifier(identifier)); if (entry.isPresent() && entry.get().identifier() instanceof SlashCommandIdentifier sIdent) { - List autocompleteRefs = Arrays.asList(marinara.getWrapper().getContextObjectProvider() + List autocompleteRefs = Arrays.asList(this.marinara.getWrapper().getContextObjectProvider() .getAutocompleteFocusedOption(context).getAutocompleteRefs(sIdent.options())); - List results = marinara.getRegistry().interactions().stream() + List results = this.marinara.getRegistry().interactions().stream() .filter(e -> e.type().equals(InteractionType.AUTOCOMPLETE)) .filter(e -> autocompleteRefs.contains(e.identifier().name())) .map(e -> e.runAll(context)) diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/processor/DirectInteractionProcessor.java b/lib/src/main/java/net/tomatentum/marinara/interaction/processor/DirectInteractionProcessor.java index b2d2296..3d1cf7a 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/processor/DirectInteractionProcessor.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/processor/DirectInteractionProcessor.java @@ -2,28 +2,23 @@ package net.tomatentum.marinara.interaction.processor; import java.util.Set; -import org.slf4j.Logger; - -import net.tomatentum.marinara.Marinara; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; -import net.tomatentum.marinara.util.LoggerUtil; +import net.tomatentum.marinara.registry.InteractionRegistry; +import net.tomatentum.marinara.wrapper.IdentifierProvider; -public class DirectInteractionProcessor implements InteractionProcessor { +public class DirectInteractionProcessor extends InteractionMethodProcessor { - private Logger logger = LoggerUtil.getLogger(getClass()); - private Set types; + private InteractionRegistry registry; - public DirectInteractionProcessor(InteractionType... types) { - this.types = Set.of(types); + public DirectInteractionProcessor(InteractionRegistry registry, IdentifierProvider provider, InteractionType... types) { + super(provider, Set.of(types)); + this.registry = registry; } @Override - public void process(Object context, InteractionIdentifier identifier, Marinara marinara) { - if (!types.contains(identifier.type())) - return; - logger.debug("Processing {} : {} with context {}", identifier, identifier.type(), context); - marinara.getRegistry().interactions().stream() + protected void processInteraction(Object context, InteractionIdentifier identifier) { + this.registry.interactions().stream() .filter(e -> e.identifier().equals(identifier)) .findFirst() .ifPresent(e -> e.runAll(context)); diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/processor/InteractionMethodProcessor.java b/lib/src/main/java/net/tomatentum/marinara/interaction/processor/InteractionMethodProcessor.java new file mode 100644 index 0000000..38a2742 --- /dev/null +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/processor/InteractionMethodProcessor.java @@ -0,0 +1,35 @@ +package net.tomatentum.marinara.interaction.processor; + +import java.util.Set; + +import org.slf4j.Logger; + +import net.tomatentum.marinara.interaction.InteractionType; +import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; +import net.tomatentum.marinara.reflection.MethodProcessor; +import net.tomatentum.marinara.util.LoggerUtil; +import net.tomatentum.marinara.wrapper.IdentifierProvider; + +public abstract class InteractionMethodProcessor implements MethodProcessor { + + private Logger logger = LoggerUtil.getLogger(getClass()); + + private IdentifierProvider provider; + private Set types; + + protected InteractionMethodProcessor(IdentifierProvider provider, Set types) { + this.provider = provider; + this.types = types; + } + + @Override + public void process(Object context) { + InteractionIdentifier identifier = this.provider.provide(context); + if (!this.types.contains(identifier.type())) return; + logger.debug("Processing {} : {} with context {}", identifier, identifier.type(), context); + this.processInteraction(context, identifier); + } + + protected abstract void processInteraction(Object context, InteractionIdentifier identifier); + +} diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/processor/InteractionProcessor.java b/lib/src/main/java/net/tomatentum/marinara/interaction/processor/InteractionProcessor.java deleted file mode 100644 index 24f0bbc..0000000 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/processor/InteractionProcessor.java +++ /dev/null @@ -1,10 +0,0 @@ -package net.tomatentum.marinara.interaction.processor; - -import net.tomatentum.marinara.Marinara; -import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; - -public interface InteractionProcessor { - - void process(Object context, InteractionIdentifier identifier, Marinara marinara); - -} diff --git a/lib/src/main/java/net/tomatentum/marinara/reflection/MethodExecutor.java b/lib/src/main/java/net/tomatentum/marinara/reflection/MethodExecutor.java new file mode 100644 index 0000000..a16c48f --- /dev/null +++ b/lib/src/main/java/net/tomatentum/marinara/reflection/MethodExecutor.java @@ -0,0 +1,7 @@ +package net.tomatentum.marinara.reflection; + +public interface MethodExecutor { + + void handle(Object context); + +} diff --git a/lib/src/main/java/net/tomatentum/marinara/reflection/MethodProcessor.java b/lib/src/main/java/net/tomatentum/marinara/reflection/MethodProcessor.java new file mode 100644 index 0000000..7cc4ce8 --- /dev/null +++ b/lib/src/main/java/net/tomatentum/marinara/reflection/MethodProcessor.java @@ -0,0 +1,7 @@ +package net.tomatentum.marinara.reflection; + +public interface MethodProcessor { + + void process(Object context); + +} diff --git a/lib/src/main/java/net/tomatentum/marinara/reflection/ProcessorContainer.java b/lib/src/main/java/net/tomatentum/marinara/reflection/ProcessorContainer.java new file mode 100644 index 0000000..0e33fe7 --- /dev/null +++ b/lib/src/main/java/net/tomatentum/marinara/reflection/ProcessorContainer.java @@ -0,0 +1,7 @@ +package net.tomatentum.marinara.reflection; + +public interface ProcessorContainer { + + ProcessorContainer addProcessor(MethodProcessor processor); + +} diff --git a/lib/src/main/java/net/tomatentum/marinara/reflection/ProcessorMethodExecutor.java b/lib/src/main/java/net/tomatentum/marinara/reflection/ProcessorMethodExecutor.java new file mode 100644 index 0000000..373ef93 --- /dev/null +++ b/lib/src/main/java/net/tomatentum/marinara/reflection/ProcessorMethodExecutor.java @@ -0,0 +1,32 @@ +package net.tomatentum.marinara.reflection; + +import java.util.HashSet; +import java.util.Set; + +import org.slf4j.Logger; + +import net.tomatentum.marinara.util.LoggerUtil; + +public class ProcessorMethodExecutor implements MethodExecutor, ProcessorContainer { + + private Logger logger = LoggerUtil.getLogger(getClass()); + + private Set processors; + + public ProcessorMethodExecutor() { + this.processors = new HashSet<>(); + } + + @Override + public ProcessorContainer addProcessor(MethodProcessor processor) { + processors.add(processor); + return this; + } + + @Override + public void handle(Object context) { + logger.debug("Received {} interaction ", context); + processors.forEach(x -> x.process(context)); + } + +} diff --git a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionExecutor.java b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionExecutor.java deleted file mode 100644 index 02d52bc..0000000 --- a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionExecutor.java +++ /dev/null @@ -1,7 +0,0 @@ -package net.tomatentum.marinara.registry; - -public interface InteractionExecutor { - - void handle(Object context); - -} diff --git a/lib/src/main/java/net/tomatentum/marinara/registry/ProcessorInteractionExecutor.java b/lib/src/main/java/net/tomatentum/marinara/registry/ProcessorInteractionExecutor.java deleted file mode 100644 index 03c2785..0000000 --- a/lib/src/main/java/net/tomatentum/marinara/registry/ProcessorInteractionExecutor.java +++ /dev/null @@ -1,41 +0,0 @@ -package net.tomatentum.marinara.registry; - -import java.util.HashSet; -import java.util.Set; - -import org.slf4j.Logger; - -import net.tomatentum.marinara.Marinara; -import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; -import net.tomatentum.marinara.interaction.processor.InteractionProcessor; -import net.tomatentum.marinara.util.LoggerUtil; -import net.tomatentum.marinara.wrapper.IdentifierProvider; - -public class ProcessorInteractionExecutor implements InteractionExecutor { - - private Logger logger = LoggerUtil.getLogger(getClass()); - - private Set processors; - private IdentifierProvider identifierProvider; - private Marinara marinara; - - public ProcessorInteractionExecutor(IdentifierProvider identifierProvider, Marinara marinara) { - this.processors = new HashSet<>(); - this.identifierProvider = identifierProvider; - this.marinara = marinara; - } - - public ProcessorInteractionExecutor addProcessor(InteractionProcessor processor) { - this.processors.add(processor); - return this; - } - - @Override - public void handle(Object context) { - logger.debug("Received {} interaction ", context); - InteractionIdentifier identifier = this.identifierProvider.provide(context); - logger.debug("Processing {} : {} interaction ", identifier, identifier.type()); - processors.forEach(x -> x.process(context, identifier, this.marinara)); - } - -} -- 2.47.2 From ebf5600e292020741ffff2d2033e1aa77b0c27bf Mon Sep 17 00:00:00 2001 From: tueem Date: Thu, 10 Apr 2025 13:39:10 +0200 Subject: [PATCH 14/18] add cutin dependency --- build.gradle.kts | 8 ++++++++ gradle/libs.versions.toml | 2 ++ lib/build.gradle.kts | 6 +----- wrapper/discord4j/build.gradle.kts | 5 ----- wrapper/javacord/build.gradle.kts | 5 ----- 5 files changed, 11 insertions(+), 15 deletions(-) diff --git a/build.gradle.kts b/build.gradle.kts index f32cd94..2cb87d1 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -13,6 +13,14 @@ allprojects { archiveBaseName.set("marinara-" + archiveBaseName.get()) } } + + repositories { + // Use Maven Central for resolving dependencies. + mavenCentral() + maven { + url = uri("https://git.tomatentum.net/api/packages/tueem/maven") + } + } } subprojects { diff --git a/gradle/libs.versions.toml b/gradle/libs.versions.toml index 5f2057a..5963d01 100644 --- a/gradle/libs.versions.toml +++ b/gradle/libs.versions.toml @@ -8,6 +8,7 @@ javacord = "3.8.0" discord4j = "3.2.7" geantyref = "2.0.0" mockito = "5.15.2" +cutin = "0.1.0" [libraries] junit-jupiter = { module = "org.junit.jupiter:junit-jupiter", version.ref = "junit-jupiter" } @@ -16,3 +17,4 @@ javacord = { module = "org.javacord:javacord", version.ref = "javacord"} discord4j = { module = "com.discord4j:discord4j-core", version.ref = "discord4j"} geantyref = { module = "io.leangen.geantyref:geantyref", version.ref = "geantyref"} mockito = {module = "org.mockito:mockito-core", version.ref = "mockito"} +cutin = {module = "net.tomatentum.cutin:lib", version.ref = "cutin"} diff --git a/lib/build.gradle.kts b/lib/build.gradle.kts index 19aca3b..25b66fd 100644 --- a/lib/build.gradle.kts +++ b/lib/build.gradle.kts @@ -10,11 +10,6 @@ plugins { `java-library` } -repositories { - // Use Maven Central for resolving dependencies. - mavenCentral() -} - dependencies { // Use JUnit Jupiter for testing. testImplementation(libs.junit.jupiter) @@ -22,6 +17,7 @@ dependencies { testRuntimeOnly("org.junit.platform:junit-platform-launcher") implementation(libs.slf4j) implementation(libs.geantyref) + implementation(libs.cutin) } // Apply a specific Java toolchain to ease working on different environments. diff --git a/wrapper/discord4j/build.gradle.kts b/wrapper/discord4j/build.gradle.kts index 49f2259..aa43096 100644 --- a/wrapper/discord4j/build.gradle.kts +++ b/wrapper/discord4j/build.gradle.kts @@ -10,11 +10,6 @@ plugins { `java-library` } -repositories { - // Use Maven Central for resolving dependencies. - mavenCentral() -} - dependencies { // Use JUnit Jupiter for testing. testImplementation(libs.junit.jupiter) diff --git a/wrapper/javacord/build.gradle.kts b/wrapper/javacord/build.gradle.kts index 608bc3a..525933d 100644 --- a/wrapper/javacord/build.gradle.kts +++ b/wrapper/javacord/build.gradle.kts @@ -10,11 +10,6 @@ plugins { `java-library` } -repositories { - // Use Maven Central for resolving dependencies. - mavenCentral() -} - dependencies { // Use JUnit Jupiter for testing. testImplementation(libs.junit.jupiter) -- 2.47.2 From ef9384336a8455ebdf7ee5e706107604cf87cb0e Mon Sep 17 00:00:00 2001 From: tueem Date: Sun, 13 Apr 2025 23:15:38 +0200 Subject: [PATCH 15/18] refactor(reflection): migrate to using cutin library --- gradle/libs.versions.toml | 4 +- lib/build.gradle.kts | 2 +- .../net/tomatentum/marinara/Marinara.java | 70 ++++++++---- .../marinara/checks/AppliedCheck.java | 46 ++------ .../checks/CheckExecutionContext.java | 7 ++ .../checks/CheckMethodIdentifier.java | 27 +++++ .../checks/InteractionCheckMethod.java | 66 +++++++++++ .../container/InteractionCheckContainer.java | 19 ++++ .../container/InteractionMethodContainer.java | 38 +++++++ .../methods/ButtonInteractionMethod.java | 38 +++++-- .../AutoCompleteInteractionMethod.java | 38 ++++--- .../methods/InteractionMethod.java | 42 ++++--- .../SlashCommandInteractionMethod.java | 36 ++++-- .../AutocompleteInteractionProcessor.java | 31 ++--- .../processor/DirectInteractionProcessor.java | 13 +-- .../processor/InteractionMethodProcessor.java | 14 ++- .../marinara/parser/AnnotationParser.java | 8 -- .../marinara/parser/AutocompleteParser.java | 18 +-- .../marinara/parser/ButtonParser.java | 14 +-- .../parser/InteractionCheckClassParser.java | 28 +++++ .../parser/InteractionCheckParser.java | 32 +++--- .../marinara/parser/SlashCommandParser.java | 12 +- .../marinara/reflection/MethodExecutor.java | 7 -- .../marinara/reflection/MethodProcessor.java | 7 -- .../reflection/ProcessorContainer.java | 7 -- .../reflection/ProcessorMethodExecutor.java | 32 ------ .../marinara/reflection/ReflectedMethod.java | 66 ----------- .../reflection/ReflectedMethodFactory.java | 20 ---- .../ReflectedMethodFactoryImpl.java | 62 ---------- .../registry/InteractionCheckRegistry.java | 40 ------- .../marinara/registry/InteractionEntry.java | 90 --------------- .../registry/InteractionRegistry.java | 80 ------------- .../marinara/util/ReflectionUtil.java | 107 ------------------ .../marinara/wrapper/IdentifierProvider.java | 2 +- .../test/discord4j/AutoCompleteTest.java | 2 +- .../marinara/test/discord4j/ButtonTest.java | 6 +- .../test/discord4j/InteractionCheckTest.java | 14 +-- .../test/discord4j/SlashCommandTest.java | 10 +- .../test/discord4j/TestAutocomplete.java | 5 +- .../marinara/test/discord4j/TestCommand.java | 2 +- .../test/javacord/AutoCompleteTest.java | 6 +- .../marinara/test/javacord/ButtonTest.java | 6 +- .../test/javacord/InteractionCheckTest.java | 14 +-- .../test/javacord/SlashCommandTest.java | 8 +- .../test/javacord/TestAutocomplete.java | 6 +- .../marinara/test/javacord/TestButton.java | 2 +- .../marinara/test/javacord/TestCommand.java | 4 +- 47 files changed, 452 insertions(+), 756 deletions(-) create mode 100644 lib/src/main/java/net/tomatentum/marinara/checks/CheckExecutionContext.java create mode 100644 lib/src/main/java/net/tomatentum/marinara/checks/CheckMethodIdentifier.java create mode 100644 lib/src/main/java/net/tomatentum/marinara/checks/InteractionCheckMethod.java create mode 100644 lib/src/main/java/net/tomatentum/marinara/container/InteractionCheckContainer.java create mode 100644 lib/src/main/java/net/tomatentum/marinara/container/InteractionMethodContainer.java delete mode 100644 lib/src/main/java/net/tomatentum/marinara/parser/AnnotationParser.java create mode 100644 lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckClassParser.java delete mode 100644 lib/src/main/java/net/tomatentum/marinara/reflection/MethodExecutor.java delete mode 100644 lib/src/main/java/net/tomatentum/marinara/reflection/MethodProcessor.java delete mode 100644 lib/src/main/java/net/tomatentum/marinara/reflection/ProcessorContainer.java delete mode 100644 lib/src/main/java/net/tomatentum/marinara/reflection/ProcessorMethodExecutor.java delete mode 100644 lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethod.java delete mode 100644 lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactory.java delete mode 100644 lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactoryImpl.java delete mode 100644 lib/src/main/java/net/tomatentum/marinara/registry/InteractionCheckRegistry.java delete mode 100644 lib/src/main/java/net/tomatentum/marinara/registry/InteractionEntry.java delete mode 100644 lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java delete mode 100644 lib/src/main/java/net/tomatentum/marinara/util/ReflectionUtil.java diff --git a/gradle/libs.versions.toml b/gradle/libs.versions.toml index 5963d01..fb7c6f0 100644 --- a/gradle/libs.versions.toml +++ b/gradle/libs.versions.toml @@ -8,7 +8,7 @@ javacord = "3.8.0" discord4j = "3.2.7" geantyref = "2.0.0" mockito = "5.15.2" -cutin = "0.1.0" +cutin = "0.1.1-cad019e" [libraries] junit-jupiter = { module = "org.junit.jupiter:junit-jupiter", version.ref = "junit-jupiter" } @@ -17,4 +17,4 @@ javacord = { module = "org.javacord:javacord", version.ref = "javacord"} discord4j = { module = "com.discord4j:discord4j-core", version.ref = "discord4j"} geantyref = { module = "io.leangen.geantyref:geantyref", version.ref = "geantyref"} mockito = {module = "org.mockito:mockito-core", version.ref = "mockito"} -cutin = {module = "net.tomatentum.cutin:lib", version.ref = "cutin"} +cutin = {module = "net.tomatentum.cutin:lib-dev", version.ref = "cutin"} diff --git a/lib/build.gradle.kts b/lib/build.gradle.kts index 25b66fd..5144454 100644 --- a/lib/build.gradle.kts +++ b/lib/build.gradle.kts @@ -17,7 +17,7 @@ dependencies { testRuntimeOnly("org.junit.platform:junit-platform-launcher") implementation(libs.slf4j) implementation(libs.geantyref) - implementation(libs.cutin) + api(libs.cutin) } // Apply a specific Java toolchain to ease working on different environments. diff --git a/lib/src/main/java/net/tomatentum/marinara/Marinara.java b/lib/src/main/java/net/tomatentum/marinara/Marinara.java index 77c57d7..643271c 100644 --- a/lib/src/main/java/net/tomatentum/marinara/Marinara.java +++ b/lib/src/main/java/net/tomatentum/marinara/Marinara.java @@ -1,17 +1,25 @@ package net.tomatentum.marinara; +import java.util.Arrays; +import java.util.List; + import org.slf4j.Logger; +import net.tomatentum.cutin.MethodExecutor; +import net.tomatentum.cutin.ProcessorMethodExecutor; +import net.tomatentum.cutin.container.MethodContainer; +import net.tomatentum.marinara.checks.CheckExecutionContext; +import net.tomatentum.marinara.checks.CheckMethodIdentifier; +import net.tomatentum.marinara.container.InteractionCheckContainer; +import net.tomatentum.marinara.container.InteractionMethodContainer; import net.tomatentum.marinara.interaction.InteractionType; +import net.tomatentum.marinara.interaction.commands.SlashCommandDefinition; +import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; +import net.tomatentum.marinara.interaction.ident.RootCommandIdentifier; import net.tomatentum.marinara.interaction.processor.AutocompleteInteractionProcessor; import net.tomatentum.marinara.interaction.processor.DirectInteractionProcessor; -import net.tomatentum.marinara.reflection.MethodExecutor; -import net.tomatentum.marinara.reflection.ProcessorMethodExecutor; -import net.tomatentum.marinara.reflection.ReflectedMethodFactory; -import net.tomatentum.marinara.reflection.ReflectedMethodFactoryImpl; -import net.tomatentum.marinara.registry.InteractionCheckRegistry; -import net.tomatentum.marinara.registry.InteractionRegistry; import net.tomatentum.marinara.util.LoggerUtil; +import net.tomatentum.marinara.util.ObjectAggregator; import net.tomatentum.marinara.wrapper.IdentifierProvider; import net.tomatentum.marinara.wrapper.LibraryWrapper; @@ -24,41 +32,53 @@ public class Marinara { } private LibraryWrapper wrapper; - private ReflectedMethodFactory reflectedMethodFactory; - private InteractionRegistry registry; - private InteractionCheckRegistry checkRegistry; - private MethodExecutor interactionExecutor; + private MethodContainer checkContainer; + private MethodContainer interactionContainer; + private MethodExecutor interactionExecutor; private Marinara(LibraryWrapper wrapper) { this.wrapper = wrapper; - this.reflectedMethodFactory = new ReflectedMethodFactoryImpl(this); - this.registry = new InteractionRegistry(this); - this.checkRegistry = new InteractionCheckRegistry(); + this.checkContainer = new InteractionCheckContainer(); + this.interactionContainer = new InteractionMethodContainer(getCheckContainer(), getWrapper().getContextObjectProvider()); IdentifierProvider provider = wrapper.createIdentifierProvider(); - this.interactionExecutor = (MethodExecutor) new ProcessorMethodExecutor() - .addProcessor(new DirectInteractionProcessor(getRegistry(), provider, InteractionType.COMMAND, InteractionType.BUTTON)) - .addProcessor(new AutocompleteInteractionProcessor(this, provider)); + ProcessorMethodExecutor exec = new ProcessorMethodExecutor<>(getInteractionContainer()); + exec + .addProcessor(new DirectInteractionProcessor(provider, InteractionType.COMMAND, InteractionType.BUTTON)) + .addProcessor(new AutocompleteInteractionProcessor(getWrapper(), provider)); + this.interactionExecutor = exec; wrapper.subscribeInteractions(this.interactionExecutor::handle); logger.info("Marinara loaded successfully!"); } + //TODO move to future interactionstructure module + public void registerCommands() { + List slashIdentifiers = getInteractionContainer().identifiers().stream() + .filter(i -> i.type().equals(InteractionType.COMMAND)) + .toList(); + + SlashCommandDefinition[] defs = new ObjectAggregator( + i -> Arrays.asList((RootCommandIdentifier)i.rootNode()), + SlashCommandDefinition::addIdentifier, + SlashCommandDefinition::new) + .aggregate(slashIdentifiers) + .toArray(SlashCommandDefinition[]::new); + + wrapper.getRegisterer().register(defs); + } + public LibraryWrapper getWrapper() { return this.wrapper; } - public InteractionRegistry getRegistry() { - return this.registry; + public MethodContainer getInteractionContainer() { + return this.interactionContainer; } - public InteractionCheckRegistry getCheckRegistry() { - return this.checkRegistry; + public MethodContainer getCheckContainer() { + return this.checkContainer; } - public ReflectedMethodFactory getReflectedMethodFactory() { - return this.reflectedMethodFactory; - } - - public MethodExecutor getInteractionExecutor() { + public MethodExecutor getInteractionExecutor() { return interactionExecutor; } diff --git a/lib/src/main/java/net/tomatentum/marinara/checks/AppliedCheck.java b/lib/src/main/java/net/tomatentum/marinara/checks/AppliedCheck.java index c20cf5a..50431ce 100644 --- a/lib/src/main/java/net/tomatentum/marinara/checks/AppliedCheck.java +++ b/lib/src/main/java/net/tomatentum/marinara/checks/AppliedCheck.java @@ -1,50 +1,28 @@ package net.tomatentum.marinara.checks; import java.lang.annotation.Annotation; -import java.lang.reflect.InvocationTargetException; -import java.lang.reflect.Method; -import java.util.Arrays; import org.slf4j.Logger; +import net.tomatentum.cutin.method.ReflectedMethod; import net.tomatentum.marinara.util.LoggerUtil; -import net.tomatentum.marinara.util.ReflectionUtil; -public record AppliedCheck(InteractionCheck check, Annotation annotation) { +public record AppliedCheck( + Annotation annotation, + ReflectedMethod preExec, + ReflectedMethod postExec + ) { + + private static Logger logger = LoggerUtil.getLogger(AppliedCheck.class); - private static Logger logger = LoggerUtil.getLogger(AppliedCheck.class); - public boolean pre(Object context) { - Method[] methods = Arrays.stream(check.getClass().getMethods()) - .filter(x -> x.getName().equals("preExec")) - .filter(x -> !x.isBridge()) - .toArray(s -> new Method[s]); - Method method = ReflectionUtil.getMostSpecificMethod(methods, context.getClass(), annotation.annotationType()); - method.setAccessible(true); - try { - logger.debug("Executing pre check {} with context {}", check.getClass().getName(), context.toString()); - boolean result = (boolean) method.invoke(check, context, annotation); - logger.debug("Pre Check {} {} with context {}", check.getClass().getName(), result ? "succeeded" : "failed", context.toString()); - return result; - } catch (IllegalAccessException | InvocationTargetException | SecurityException e) { - logger.error("Failed executing pre-check", e); - return false; - } + logger.debug("Running InteractionCheck preExec {} with annotation {}", preExec(), annotation()); + return (boolean) preExec().run(new CheckExecutionContext(annotation, context)); } public void post(Object context) { - Method[] methods = Arrays.stream(check.getClass().getMethods()) - .filter(x -> x.getName().equals("postExec")) - .filter(x -> !x.isBridge()) - .toArray(s -> new Method[s]); - Method method = ReflectionUtil.getMostSpecificMethod(methods, context.getClass(), annotation.annotationType()); - method.setAccessible(true); - try { - logger.debug("Executing post check {} with context {}", check.getClass().getName(), context.toString()); - method.invoke(check, context, annotation); - } catch (IllegalAccessException | InvocationTargetException | SecurityException e) { - logger.error("Failed executing post-check", e); - } + logger.debug("Running InteractionCheck postExec {} with annotation {}", postExec(), annotation()); + postExec().run(new CheckExecutionContext(annotation, context)); } } diff --git a/lib/src/main/java/net/tomatentum/marinara/checks/CheckExecutionContext.java b/lib/src/main/java/net/tomatentum/marinara/checks/CheckExecutionContext.java new file mode 100644 index 0000000..4dfbdac --- /dev/null +++ b/lib/src/main/java/net/tomatentum/marinara/checks/CheckExecutionContext.java @@ -0,0 +1,7 @@ +package net.tomatentum.marinara.checks; + +import java.lang.annotation.Annotation; + +public record CheckExecutionContext(Annotation annotation, Object originalContext) { + +} diff --git a/lib/src/main/java/net/tomatentum/marinara/checks/CheckMethodIdentifier.java b/lib/src/main/java/net/tomatentum/marinara/checks/CheckMethodIdentifier.java new file mode 100644 index 0000000..af3ca01 --- /dev/null +++ b/lib/src/main/java/net/tomatentum/marinara/checks/CheckMethodIdentifier.java @@ -0,0 +1,27 @@ +package net.tomatentum.marinara.checks; + +import java.lang.reflect.Type; + +public record CheckMethodIdentifier(Type annotationType, CheckMethodType type) { + + public enum CheckMethodType { + PRE("preExec"), + POST("postExec"); + + private String methodName; + + private CheckMethodType(String methodName) { + this.methodName = methodName; + } + + public String methodName() { + return this.methodName; + } + } + + @Override + public final String toString() { + return "InteractionCheck(%s, %s)".formatted(annotationType, type); + } + +} diff --git a/lib/src/main/java/net/tomatentum/marinara/checks/InteractionCheckMethod.java b/lib/src/main/java/net/tomatentum/marinara/checks/InteractionCheckMethod.java new file mode 100644 index 0000000..0774f26 --- /dev/null +++ b/lib/src/main/java/net/tomatentum/marinara/checks/InteractionCheckMethod.java @@ -0,0 +1,66 @@ +package net.tomatentum.marinara.checks; + +import java.util.List; +import java.util.Optional; + +import net.tomatentum.cutin.MethodParser; +import net.tomatentum.cutin.container.MethodContainer; +import net.tomatentum.cutin.method.BestCandidateMethod; +import net.tomatentum.cutin.method.ReflectedMethod; +import net.tomatentum.marinara.checks.CheckMethodIdentifier.CheckMethodType; +import net.tomatentum.marinara.parser.InteractionCheckClassParser; + +public class InteractionCheckMethod extends BestCandidateMethod { + + private CheckMethodIdentifier identifier; + + public InteractionCheckMethod(String methodName, Object containingObject) { + super(methodName, containingObject); + } + + @Override + public Object getParameter(CheckExecutionContext context, int index) { + switch (index) { + case 0: + return context.originalContext(); + case 1: + return context.annotation(); + default: + return null; + } + } + + @Override + public CheckMethodIdentifier identifier() { + return this.identifier; + } + + public static class InteractionCheckMethodFactory extends BestCandidateMethod.Factory { + + private CheckMethodType type; + + public InteractionCheckMethodFactory(MethodContainer methodContainer, CheckMethodType type) { + super(methodContainer, type.methodName()); + this.type = type; + } + + @SuppressWarnings("unchecked") + @Override + public void addParser(ReflectedMethod method, List parsers) { + parsers.add( + new InteractionCheckClassParser((Class>) method.containingObject().getClass(), + a -> ((InteractionCheckMethod) method).identifier = new CheckMethodIdentifier(a, type)) + ); + } + + @Override + protected Optional> bcProduce(String methodName, + Object containingObject) { + if (!(containingObject instanceof InteractionCheck)) + return Optional.empty(); + return Optional.of(new InteractionCheckMethod(methodName, containingObject)); + } + + } + +} diff --git a/lib/src/main/java/net/tomatentum/marinara/container/InteractionCheckContainer.java b/lib/src/main/java/net/tomatentum/marinara/container/InteractionCheckContainer.java new file mode 100644 index 0000000..11f8271 --- /dev/null +++ b/lib/src/main/java/net/tomatentum/marinara/container/InteractionCheckContainer.java @@ -0,0 +1,19 @@ +package net.tomatentum.marinara.container; + +import net.tomatentum.cutin.ReflectedMethodFactoryImpl; +import net.tomatentum.cutin.container.LoneMethodContainer; +import net.tomatentum.marinara.checks.CheckExecutionContext; +import net.tomatentum.marinara.checks.CheckMethodIdentifier; +import net.tomatentum.marinara.checks.CheckMethodIdentifier.CheckMethodType; +import net.tomatentum.marinara.checks.InteractionCheckMethod.InteractionCheckMethodFactory; + +public class InteractionCheckContainer extends LoneMethodContainer { + + public InteractionCheckContainer() { + super(new ReflectedMethodFactoryImpl<>()); + super.factory() + .addFactory(new InteractionCheckMethodFactory(this, CheckMethodType.PRE)) + .addFactory(new InteractionCheckMethodFactory(this, CheckMethodType.POST)); + } + +} diff --git a/lib/src/main/java/net/tomatentum/marinara/container/InteractionMethodContainer.java b/lib/src/main/java/net/tomatentum/marinara/container/InteractionMethodContainer.java new file mode 100644 index 0000000..0223c95 --- /dev/null +++ b/lib/src/main/java/net/tomatentum/marinara/container/InteractionMethodContainer.java @@ -0,0 +1,38 @@ +package net.tomatentum.marinara.container; + +import net.tomatentum.cutin.ReflectedMethodFactory; +import net.tomatentum.cutin.ReflectedMethodFactoryImpl; +import net.tomatentum.cutin.container.MethodContainer; +import net.tomatentum.cutin.container.MultiMethodContainer; +import net.tomatentum.cutin.method.ReflectedMethod; +import net.tomatentum.marinara.checks.CheckExecutionContext; +import net.tomatentum.marinara.checks.CheckMethodIdentifier; +import net.tomatentum.marinara.interaction.components.methods.ButtonInteractionMethod; +import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; +import net.tomatentum.marinara.wrapper.ContextObjectProvider; +import net.tomatentum.marinara.interaction.methods.AutoCompleteInteractionMethod; +import net.tomatentum.marinara.interaction.methods.SlashCommandInteractionMethod; + +public class InteractionMethodContainer extends MultiMethodContainer { + + + private static ReflectedMethodFactory createFactory(MethodContainer checkRegistry, ContextObjectProvider cop) { + return new ReflectedMethodFactoryImpl() + .addFactory(new AutoCompleteInteractionMethod.Factory(checkRegistry, cop)) + .addFactory(new SlashCommandInteractionMethod.Factory(checkRegistry, cop)) + .addFactory(new ButtonInteractionMethod.Factory(checkRegistry, cop)); + } + + public InteractionMethodContainer(MethodContainer checkRegistry, ContextObjectProvider cop) { + super(createFactory(checkRegistry, cop)); + } + + @Override + public MethodContainer addMethod(ReflectedMethod method) { + super.identifiers().stream() + .filter(method.identifier()::equals) + .forEach(i -> InteractionIdentifier.tryAddDescriptions(i, method.identifier())); + return super.addMethod(method); + } + +} diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/components/methods/ButtonInteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/components/methods/ButtonInteractionMethod.java index 7fd45a5..ffb4c0d 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/components/methods/ButtonInteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/components/methods/ButtonInteractionMethod.java @@ -4,28 +4,37 @@ import java.lang.reflect.Method; import java.util.List; import java.util.Optional; -import net.tomatentum.marinara.Marinara; +import net.tomatentum.cutin.MethodParser; +import net.tomatentum.cutin.container.MethodContainer; +import net.tomatentum.cutin.method.ReflectedMethod; +import net.tomatentum.marinara.checks.CheckExecutionContext; +import net.tomatentum.marinara.checks.CheckMethodIdentifier; import net.tomatentum.marinara.interaction.InteractionHandler; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.annotation.Button; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; import net.tomatentum.marinara.interaction.methods.InteractionMethod; -import net.tomatentum.marinara.parser.AnnotationParser; import net.tomatentum.marinara.parser.ButtonParser; -import net.tomatentum.marinara.reflection.ReflectedMethod; +import net.tomatentum.marinara.wrapper.ContextObjectProvider; public class ButtonInteractionMethod extends InteractionMethod { private String customId; + private ContextObjectProvider cop; - private ButtonInteractionMethod(Method method, InteractionHandler handler, Marinara marinara) { - super(method, handler, marinara); + private ButtonInteractionMethod(Method method, InteractionHandler handler, ContextObjectProvider cop) { + super(method, handler); + this.cop = cop; } @Override public Object getParameter(Object context, int index) { - Class type = method().getParameterTypes()[index+1]; - return marinara.getWrapper().getContextObjectProvider().getComponentContextObject(context, type); + Class type = method().getParameterTypes()[index]; + Object superResult = super.getParameter(context, index); + if (superResult == null) + return this.cop.getComponentContextObject(context, type); + else + return superResult; } @Override @@ -39,19 +48,26 @@ public class ButtonInteractionMethod extends InteractionMethod { public static class Factory extends InteractionMethod.Factory { + private ContextObjectProvider cop; + + public Factory(MethodContainer checkContainer, ContextObjectProvider cop) { + super(checkContainer); + this.cop = cop; + } + @Override - public Optional produce(Marinara marinara, Method method, Object containingObject) { - ReflectedMethod rMethod = null; + public Optional> produce(Method method, Object containingObject) { + ButtonInteractionMethod rMethod = null; if (method.isAnnotationPresent(Button.class) && (containingObject instanceof InteractionHandler iHandler) ) - rMethod = new ButtonInteractionMethod(method, iHandler, marinara); + rMethod = new ButtonInteractionMethod(method, iHandler, this.cop); return Optional.ofNullable(rMethod); } @Override - public void addParser(ReflectedMethod method, List parser) { + public void addParser(ReflectedMethod method, List parser) { super.addParser(method, parser); parser.add( diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java index af100e5..a00c008 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java @@ -4,40 +4,45 @@ import java.lang.reflect.Method; import java.util.List; import java.util.Optional; -import net.tomatentum.marinara.Marinara; +import net.tomatentum.cutin.MethodParser; +import net.tomatentum.cutin.container.MethodContainer; +import net.tomatentum.cutin.method.ReflectedMethod; +import net.tomatentum.marinara.checks.CheckExecutionContext; +import net.tomatentum.marinara.checks.CheckMethodIdentifier; import net.tomatentum.marinara.interaction.InteractionHandler; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.annotation.AutoComplete; import net.tomatentum.marinara.interaction.commands.annotation.SlashCommand; import net.tomatentum.marinara.interaction.commands.annotation.SubCommand; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; -import net.tomatentum.marinara.parser.AnnotationParser; import net.tomatentum.marinara.parser.AutocompleteParser; -import net.tomatentum.marinara.reflection.ReflectedMethod; +import net.tomatentum.marinara.wrapper.ContextObjectProvider; public class AutoCompleteInteractionMethod extends InteractionMethod { private String autocompleteRef; + private ContextObjectProvider cop; private AutoCompleteInteractionMethod(Method method, InteractionHandler handler, - Marinara marinara + ContextObjectProvider cop ) { - super(method, handler, marinara); + super(method, handler); + this.cop = cop; } @Override public Object getParameter(Object context, int index) { - Class type = method().getParameterTypes()[index+1]; - Object contextObject = marinara.getWrapper().getContextObjectProvider().getInteractionContextObject(context, type); + Class type = method().getParameterTypes()[index]; + Object contextObject = this.cop.getInteractionContextObject(context, type); if (contextObject != null) return contextObject; - Object autocompleteOptionValue = marinara.getWrapper().getContextObjectProvider().getAutocompleteFocusedOption(context).input(); + Object autocompleteOptionValue = this.cop.getAutocompleteFocusedOption(context).input(); if (type.isInstance(autocompleteOptionValue)) return autocompleteOptionValue; - return null; + return super.getParameter(context, index); } @Override @@ -51,20 +56,27 @@ public class AutoCompleteInteractionMethod extends InteractionMethod { public static class Factory extends InteractionMethod.Factory { + private ContextObjectProvider cop; + + public Factory(MethodContainer checkContainer, ContextObjectProvider cop) { + super(checkContainer); + this.cop = cop; + } + @Override - public Optional produce(Marinara marinara, Method method, Object containingObject) { - ReflectedMethod rMethod = null; + public Optional> produce(Method method, Object containingObject) { + AutoCompleteInteractionMethod rMethod = null; if ((containingObject instanceof InteractionHandler iHandler) && method.isAnnotationPresent(AutoComplete.class) && !(method.isAnnotationPresent(SlashCommand.class) || method.isAnnotationPresent(SubCommand.class))) - rMethod = new AutoCompleteInteractionMethod(method, iHandler, marinara); + rMethod = new AutoCompleteInteractionMethod(method, iHandler, cop); return Optional.ofNullable(rMethod); } @Override - public void addParser(ReflectedMethod method, List parser) { + public void addParser(ReflectedMethod method, List parser) { super.addParser(method, parser); parser.add( diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/InteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/InteractionMethod.java index caaa884..7dd316f 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/InteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/InteractionMethod.java @@ -4,29 +4,35 @@ import java.lang.reflect.Method; import java.util.ArrayList; import java.util.List; -import net.tomatentum.marinara.Marinara; +import net.tomatentum.cutin.MethodParser; +import net.tomatentum.cutin.ReflectedMethodFactory; +import net.tomatentum.cutin.container.MethodContainer; +import net.tomatentum.cutin.method.ReflectedMethod; import net.tomatentum.marinara.checks.AppliedCheck; +import net.tomatentum.marinara.checks.CheckExecutionContext; +import net.tomatentum.marinara.checks.CheckMethodIdentifier; import net.tomatentum.marinara.interaction.InteractionHandler; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; -import net.tomatentum.marinara.parser.AnnotationParser; import net.tomatentum.marinara.parser.InteractionCheckParser; -import net.tomatentum.marinara.reflection.ReflectedMethod; -import net.tomatentum.marinara.reflection.ReflectedMethodFactory; -public abstract class InteractionMethod extends ReflectedMethod { +public abstract class InteractionMethod extends ReflectedMethod { - protected Marinara marinara; protected List appliedChecks; protected InteractionMethod( Method method, - InteractionHandler handler, - Marinara marinara + InteractionHandler handler ) { super(method, handler); - this.marinara = marinara; this.appliedChecks = new ArrayList<>(); } + + @Override + public Object getParameter(Object context, int index) { + if (index == 0) + return context; + return null; + } @Override public Object run(Object context) { @@ -41,23 +47,23 @@ public abstract class InteractionMethod extends ReflectedMethod { return result; } - public abstract InteractionIdentifier identifier(); - - public Marinara marinara() { - return this.marinara; - } - public List appliedChecks() { return this.appliedChecks; } - public abstract static class Factory implements ReflectedMethodFactory.Factory { + public abstract static class Factory implements ReflectedMethodFactory.Factory { + + private MethodContainer checkContainer; + + protected Factory(MethodContainer checkContainer) { + this.checkContainer = checkContainer; + } @Override - public void addParser(ReflectedMethod method, List parser) { + public void addParser(ReflectedMethod method, List parser) { InteractionMethod imethod = (InteractionMethod) method; parser.add( - new InteractionCheckParser(method.method(), imethod.appliedChecks::add, imethod.marinara().getCheckRegistry()) + new InteractionCheckParser(method.method(), imethod.appliedChecks::add, this.checkContainer) ); } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java index a6bd130..8afa595 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java @@ -4,27 +4,36 @@ import java.lang.reflect.Method; import java.util.List; import java.util.Optional; -import net.tomatentum.marinara.Marinara; +import net.tomatentum.cutin.MethodParser; +import net.tomatentum.cutin.container.MethodContainer; +import net.tomatentum.cutin.method.ReflectedMethod; +import net.tomatentum.marinara.checks.CheckExecutionContext; +import net.tomatentum.marinara.checks.CheckMethodIdentifier; import net.tomatentum.marinara.interaction.InteractionHandler; import net.tomatentum.marinara.interaction.commands.annotation.SlashCommand; import net.tomatentum.marinara.interaction.commands.annotation.SubCommand; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; import net.tomatentum.marinara.interaction.ident.SlashCommandIdentifier; -import net.tomatentum.marinara.parser.AnnotationParser; import net.tomatentum.marinara.parser.SlashCommandParser; -import net.tomatentum.marinara.reflection.ReflectedMethod; +import net.tomatentum.marinara.wrapper.ContextObjectProvider; public class SlashCommandInteractionMethod extends InteractionMethod { private SlashCommandIdentifier interactionIdentifier; + private ContextObjectProvider cop; - private SlashCommandInteractionMethod(Method method, InteractionHandler handler, Marinara marinara) { - super(method, handler, marinara); + private SlashCommandInteractionMethod(Method method, InteractionHandler handler, ContextObjectProvider cop) { + super(method, handler); + this.cop = cop; } @Override public Object getParameter(Object context, int index) { - return marinara.getWrapper().getContextObjectProvider().convertCommandOption(context, interactionIdentifier.options()[index].name()); + Object superResult = super.getParameter(context, index); + if (superResult == null) + return this.cop.convertCommandOption(context, interactionIdentifier.options()[index-1].name()); + else + return superResult; } @Override @@ -34,18 +43,25 @@ public class SlashCommandInteractionMethod extends InteractionMethod { public static class Factory extends InteractionMethod.Factory { + private ContextObjectProvider cop; + + public Factory(MethodContainer checkContainer, ContextObjectProvider cop) { + super(checkContainer); + this.cop = cop; + } + @Override - public Optional produce(Marinara marinara, Method method, Object containingObject) { - ReflectedMethod rMethod = null; + public Optional> produce(Method method, Object containingObject) { + SlashCommandInteractionMethod rMethod = null; if ((containingObject instanceof InteractionHandler iHandler) && (method.isAnnotationPresent(SlashCommand.class) || method.isAnnotationPresent(SubCommand.class))) - rMethod = new SlashCommandInteractionMethod(method, iHandler, marinara); + rMethod = new SlashCommandInteractionMethod(method, iHandler, cop); return Optional.ofNullable(rMethod); } @Override - public void addParser(ReflectedMethod method, List parser) { + public void addParser(ReflectedMethod method, List parser) { super.addParser(method, parser); parser.add( diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/processor/AutocompleteInteractionProcessor.java b/lib/src/main/java/net/tomatentum/marinara/interaction/processor/AutocompleteInteractionProcessor.java index b194946..1d02b92 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/processor/AutocompleteInteractionProcessor.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/processor/AutocompleteInteractionProcessor.java @@ -6,37 +6,38 @@ import java.util.Objects; import java.util.Optional; import java.util.Set; -import net.tomatentum.marinara.Marinara; +import net.tomatentum.cutin.container.MethodContainer; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; import net.tomatentum.marinara.interaction.ident.SlashCommandIdentifier; -import net.tomatentum.marinara.registry.InteractionEntry; import net.tomatentum.marinara.wrapper.IdentifierProvider; +import net.tomatentum.marinara.wrapper.LibraryWrapper; public class AutocompleteInteractionProcessor extends InteractionMethodProcessor { - private Marinara marinara; + private LibraryWrapper wrapper; - public AutocompleteInteractionProcessor(Marinara marinara, IdentifierProvider provider) { + public AutocompleteInteractionProcessor(LibraryWrapper wrapper, IdentifierProvider provider) { super(provider, Set.of(InteractionType.AUTOCOMPLETE)); - this.marinara = marinara; + this.wrapper = wrapper; } @Override - public void processInteraction(Object context, InteractionIdentifier identifier) { - Optional entry = this.marinara.getRegistry().findFor(convertToCommandIdentifier(identifier)); - if (entry.isPresent() && entry.get().identifier() instanceof SlashCommandIdentifier sIdent) { - List autocompleteRefs = Arrays.asList(this.marinara.getWrapper().getContextObjectProvider() + public void processInteraction(Object context, MethodContainer container, InteractionIdentifier identifier) { + Optional oIdent = container.identifiers().stream() + .filter(i -> convertToCommandIdentifier(identifier).equals(i)) + .findFirst(); + if (oIdent.isPresent() && oIdent.get() instanceof SlashCommandIdentifier sIdent) { + List autocompleteRefs = Arrays.asList(this.wrapper.getContextObjectProvider() .getAutocompleteFocusedOption(context).getAutocompleteRefs(sIdent.options())); - List results = this.marinara.getRegistry().interactions().stream() - .filter(e -> e.type().equals(InteractionType.AUTOCOMPLETE)) - .filter(e -> autocompleteRefs.contains(e.identifier().name())) - .map(e -> e.runAll(context)) - .flatMap(Arrays::stream) + List results = container.methods().stream() + .filter(m -> m.identifier().type().equals(InteractionType.AUTOCOMPLETE)) + .filter(m -> autocompleteRefs.contains(m.identifier().name())) + .map(m -> m.run(context)) .filter(Objects::nonNull) .toList(); if (!results.isEmpty()) - marinara.getWrapper().respondAutocomplete(context, results); + this.wrapper.respondAutocomplete(context, results); } } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/processor/DirectInteractionProcessor.java b/lib/src/main/java/net/tomatentum/marinara/interaction/processor/DirectInteractionProcessor.java index 3d1cf7a..6856d2f 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/processor/DirectInteractionProcessor.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/processor/DirectInteractionProcessor.java @@ -2,26 +2,21 @@ package net.tomatentum.marinara.interaction.processor; import java.util.Set; +import net.tomatentum.cutin.container.MethodContainer; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; -import net.tomatentum.marinara.registry.InteractionRegistry; import net.tomatentum.marinara.wrapper.IdentifierProvider; public class DirectInteractionProcessor extends InteractionMethodProcessor { - private InteractionRegistry registry; - public DirectInteractionProcessor(InteractionRegistry registry, IdentifierProvider provider, InteractionType... types) { + public DirectInteractionProcessor(IdentifierProvider provider, InteractionType... types) { super(provider, Set.of(types)); - this.registry = registry; } @Override - protected void processInteraction(Object context, InteractionIdentifier identifier) { - this.registry.interactions().stream() - .filter(e -> e.identifier().equals(identifier)) - .findFirst() - .ifPresent(e -> e.runAll(context)); + protected void processInteraction(Object context, MethodContainer container, InteractionIdentifier identifier) { + container.findFor(identifier).forEach(m -> m.run(context)); } } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/processor/InteractionMethodProcessor.java b/lib/src/main/java/net/tomatentum/marinara/interaction/processor/InteractionMethodProcessor.java index 38a2742..9424c75 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/processor/InteractionMethodProcessor.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/processor/InteractionMethodProcessor.java @@ -4,13 +4,14 @@ import java.util.Set; import org.slf4j.Logger; +import net.tomatentum.cutin.MethodProcessor; +import net.tomatentum.cutin.container.MethodContainer; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; -import net.tomatentum.marinara.reflection.MethodProcessor; import net.tomatentum.marinara.util.LoggerUtil; import net.tomatentum.marinara.wrapper.IdentifierProvider; -public abstract class InteractionMethodProcessor implements MethodProcessor { +public abstract class InteractionMethodProcessor implements MethodProcessor { private Logger logger = LoggerUtil.getLogger(getClass()); @@ -23,13 +24,16 @@ public abstract class InteractionMethodProcessor implements MethodProcessor { } @Override - public void process(Object context) { + public void process(Object context, MethodContainer container) { InteractionIdentifier identifier = this.provider.provide(context); if (!this.types.contains(identifier.type())) return; logger.debug("Processing {} : {} with context {}", identifier, identifier.type(), context); - this.processInteraction(context, identifier); + this.processInteraction(context, container, identifier); } - protected abstract void processInteraction(Object context, InteractionIdentifier identifier); + protected abstract void processInteraction( + Object context, + MethodContainer container, + InteractionIdentifier identifier); } diff --git a/lib/src/main/java/net/tomatentum/marinara/parser/AnnotationParser.java b/lib/src/main/java/net/tomatentum/marinara/parser/AnnotationParser.java deleted file mode 100644 index 187a4a4..0000000 --- a/lib/src/main/java/net/tomatentum/marinara/parser/AnnotationParser.java +++ /dev/null @@ -1,8 +0,0 @@ -package net.tomatentum.marinara.parser; - -import java.lang.reflect.Method; - -public interface AnnotationParser { - void parse(); - Method getMethod(); -} diff --git a/lib/src/main/java/net/tomatentum/marinara/parser/AutocompleteParser.java b/lib/src/main/java/net/tomatentum/marinara/parser/AutocompleteParser.java index 37ab8c8..96a0eda 100644 --- a/lib/src/main/java/net/tomatentum/marinara/parser/AutocompleteParser.java +++ b/lib/src/main/java/net/tomatentum/marinara/parser/AutocompleteParser.java @@ -4,9 +4,16 @@ import java.lang.reflect.Method; import java.util.Arrays; import java.util.function.Consumer; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import net.tomatentum.cutin.MethodParser; +import net.tomatentum.cutin.util.ReflectionUtil; import net.tomatentum.marinara.interaction.annotation.AutoComplete; -public class AutocompleteParser implements AnnotationParser { +public class AutocompleteParser implements MethodParser { + + private Logger logger = LoggerFactory.getLogger(getClass()); private Method method; private Consumer consumer; @@ -21,13 +28,8 @@ public class AutocompleteParser implements AnnotationParser { String[] autocompletes = Arrays.stream(this.method.getAnnotationsByType(AutoComplete.class)) .map(AutoComplete::value) .toArray(String[]::new); - this.consumer.accept(autocompletes); - - } - - @Override - public Method getMethod() { - return this.method; + logger.trace("Parsed AutoComplete annotation {} for method {}", autocompletes, ReflectionUtil.getFullMethodName(method)); + this.consumer.accept(autocompletes); } } diff --git a/lib/src/main/java/net/tomatentum/marinara/parser/ButtonParser.java b/lib/src/main/java/net/tomatentum/marinara/parser/ButtonParser.java index ee8ab37..a2d533e 100644 --- a/lib/src/main/java/net/tomatentum/marinara/parser/ButtonParser.java +++ b/lib/src/main/java/net/tomatentum/marinara/parser/ButtonParser.java @@ -5,11 +5,12 @@ import java.util.function.Consumer; import org.slf4j.Logger; +import net.tomatentum.cutin.MethodParser; +import net.tomatentum.cutin.util.ReflectionUtil; import net.tomatentum.marinara.interaction.annotation.Button; import net.tomatentum.marinara.util.LoggerUtil; -import net.tomatentum.marinara.util.ReflectionUtil; -public class ButtonParser implements AnnotationParser { +public class ButtonParser implements MethodParser { private Method method; private Consumer consumer; @@ -23,14 +24,9 @@ public class ButtonParser implements AnnotationParser { @Override public void parse() { - Button button = getMethod().getAnnotation(Button.class); - logger.trace("Parsed Button annotation {} for method {}", button.toString(), ReflectionUtil.getFullMethodName(method)); + Button button = this.method.getAnnotation(Button.class); + logger.trace("Parsed Button annotation {} for method {}", button, ReflectionUtil.getFullMethodName(method)); this.consumer.accept(button.value()); } - - @Override - public Method getMethod() { - return this.method; - } } diff --git a/lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckClassParser.java b/lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckClassParser.java new file mode 100644 index 0000000..0023e3f --- /dev/null +++ b/lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckClassParser.java @@ -0,0 +1,28 @@ +package net.tomatentum.marinara.parser; + +import java.lang.reflect.ParameterizedType; +import java.lang.reflect.Type; +import java.util.function.Consumer; + +import io.leangen.geantyref.GenericTypeReflector; +import net.tomatentum.cutin.MethodParser; +import net.tomatentum.marinara.checks.InteractionCheck; + +public class InteractionCheckClassParser implements MethodParser { + + private Class> interactionCheckType; + private Consumer annotationTypeConsumer; + + public InteractionCheckClassParser(Class> interactionCheckType, Consumer annotationTypeConsumer) { + this.interactionCheckType = interactionCheckType; + this.annotationTypeConsumer = annotationTypeConsumer; + } + + @Override + public void parse() { + ParameterizedType type = (ParameterizedType) GenericTypeReflector.getExactSuperType(interactionCheckType, InteractionCheck.class); + Type typeParam = type.getActualTypeArguments()[0]; + this.annotationTypeConsumer.accept(typeParam); + } + +} diff --git a/lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckParser.java b/lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckParser.java index 7379141..4e3a36c 100644 --- a/lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckParser.java +++ b/lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckParser.java @@ -3,27 +3,29 @@ package net.tomatentum.marinara.parser; import java.lang.annotation.Annotation; import java.lang.reflect.Method; import java.util.Arrays; -import java.util.Optional; import java.util.function.Consumer; import org.slf4j.Logger; +import net.tomatentum.cutin.MethodParser; +import net.tomatentum.cutin.container.MethodContainer; +import net.tomatentum.cutin.util.ReflectionUtil; import net.tomatentum.marinara.checks.AppliedCheck; -import net.tomatentum.marinara.checks.InteractionCheck; -import net.tomatentum.marinara.registry.InteractionCheckRegistry; +import net.tomatentum.marinara.checks.CheckExecutionContext; +import net.tomatentum.marinara.checks.CheckMethodIdentifier; +import net.tomatentum.marinara.checks.CheckMethodIdentifier.CheckMethodType; import net.tomatentum.marinara.util.LoggerUtil; -import net.tomatentum.marinara.util.ReflectionUtil; -public class InteractionCheckParser implements AnnotationParser { +public class InteractionCheckParser implements MethodParser { - private InteractionCheckRegistry checkRegistry; + private MethodContainer checkContainer; private Method method; private Consumer consumer; private Logger logger = LoggerUtil.getLogger(getClass()); - public InteractionCheckParser(Method method, Consumer consumer, InteractionCheckRegistry checkRegistry) { - this.checkRegistry = checkRegistry; + public InteractionCheckParser(Method method, Consumer consumer, MethodContainer checkContainer) { + this.checkContainer = checkContainer; this.method = method; this.consumer = consumer; } @@ -35,17 +37,13 @@ public class InteractionCheckParser implements AnnotationParser { } private void convertAnnotation(Annotation annotation) { - Optional> check = this.checkRegistry.getCheckFromAnnotation(annotation.annotationType()); - if (check.isPresent()) { - AppliedCheck appliedCheck = new AppliedCheck(check.get(), annotation); - logger.trace("Parsed InteractionCheck {} for annotation {} for method {}", check.getClass().getName(), annotation.toString(), ReflectionUtil.getFullMethodName(method)); + var preExec = this.checkContainer.findFirstFor(new CheckMethodIdentifier(annotation.annotationType(), CheckMethodType.PRE)); + var postExec = this.checkContainer.findFirstFor(new CheckMethodIdentifier(annotation.annotationType(), CheckMethodType.POST)); + if (preExec.isPresent() && postExec.isPresent()) { + AppliedCheck appliedCheck = new AppliedCheck(annotation, preExec.get(), postExec.get()); + logger.trace("Parsed InteractionCheck {} for annotation {} for method {}", preExec.get().containingObject(), annotation, ReflectionUtil.getFullMethodName(method)); consumer.accept(appliedCheck); } } - - @Override - public Method getMethod() { - return this.method; - } } diff --git a/lib/src/main/java/net/tomatentum/marinara/parser/SlashCommandParser.java b/lib/src/main/java/net/tomatentum/marinara/parser/SlashCommandParser.java index b13efa1..c6ca43b 100644 --- a/lib/src/main/java/net/tomatentum/marinara/parser/SlashCommandParser.java +++ b/lib/src/main/java/net/tomatentum/marinara/parser/SlashCommandParser.java @@ -5,6 +5,8 @@ import java.util.function.Consumer; import org.slf4j.Logger; +import net.tomatentum.cutin.MethodParser; +import net.tomatentum.cutin.util.ReflectionUtil; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.commands.annotation.SlashCommand; import net.tomatentum.marinara.interaction.commands.annotation.SubCommand; @@ -12,9 +14,8 @@ import net.tomatentum.marinara.interaction.commands.annotation.SubCommandGroup; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; import net.tomatentum.marinara.interaction.ident.SlashCommandIdentifier; import net.tomatentum.marinara.util.LoggerUtil; -import net.tomatentum.marinara.util.ReflectionUtil; -public class SlashCommandParser implements AnnotationParser { +public class SlashCommandParser implements MethodParser { private Method method; private Consumer consumer; @@ -57,15 +58,10 @@ public class SlashCommandParser implements AnnotationParser { .build(); } - logger.trace("Parsed using SlashCommandParser for method {} with the result: {}", ReflectionUtil.getFullMethodName(method), lastIdentifier.toString()); + logger.trace("Parsed using SlashCommandParser for method {} with the result: {}", ReflectionUtil.getFullMethodName(method), lastIdentifier); consumer.accept((SlashCommandIdentifier) lastIdentifier); } - @Override - public Method getMethod() { - return this.method; - } - private void checkValidCommandMethod(Method method) { if (method.isAnnotationPresent(SlashCommand.class) && method.getDeclaringClass().isAnnotationPresent(SlashCommand.class)) { diff --git a/lib/src/main/java/net/tomatentum/marinara/reflection/MethodExecutor.java b/lib/src/main/java/net/tomatentum/marinara/reflection/MethodExecutor.java deleted file mode 100644 index a16c48f..0000000 --- a/lib/src/main/java/net/tomatentum/marinara/reflection/MethodExecutor.java +++ /dev/null @@ -1,7 +0,0 @@ -package net.tomatentum.marinara.reflection; - -public interface MethodExecutor { - - void handle(Object context); - -} diff --git a/lib/src/main/java/net/tomatentum/marinara/reflection/MethodProcessor.java b/lib/src/main/java/net/tomatentum/marinara/reflection/MethodProcessor.java deleted file mode 100644 index 7cc4ce8..0000000 --- a/lib/src/main/java/net/tomatentum/marinara/reflection/MethodProcessor.java +++ /dev/null @@ -1,7 +0,0 @@ -package net.tomatentum.marinara.reflection; - -public interface MethodProcessor { - - void process(Object context); - -} diff --git a/lib/src/main/java/net/tomatentum/marinara/reflection/ProcessorContainer.java b/lib/src/main/java/net/tomatentum/marinara/reflection/ProcessorContainer.java deleted file mode 100644 index 0e33fe7..0000000 --- a/lib/src/main/java/net/tomatentum/marinara/reflection/ProcessorContainer.java +++ /dev/null @@ -1,7 +0,0 @@ -package net.tomatentum.marinara.reflection; - -public interface ProcessorContainer { - - ProcessorContainer addProcessor(MethodProcessor processor); - -} diff --git a/lib/src/main/java/net/tomatentum/marinara/reflection/ProcessorMethodExecutor.java b/lib/src/main/java/net/tomatentum/marinara/reflection/ProcessorMethodExecutor.java deleted file mode 100644 index 373ef93..0000000 --- a/lib/src/main/java/net/tomatentum/marinara/reflection/ProcessorMethodExecutor.java +++ /dev/null @@ -1,32 +0,0 @@ -package net.tomatentum.marinara.reflection; - -import java.util.HashSet; -import java.util.Set; - -import org.slf4j.Logger; - -import net.tomatentum.marinara.util.LoggerUtil; - -public class ProcessorMethodExecutor implements MethodExecutor, ProcessorContainer { - - private Logger logger = LoggerUtil.getLogger(getClass()); - - private Set processors; - - public ProcessorMethodExecutor() { - this.processors = new HashSet<>(); - } - - @Override - public ProcessorContainer addProcessor(MethodProcessor processor) { - processors.add(processor); - return this; - } - - @Override - public void handle(Object context) { - logger.debug("Received {} interaction ", context); - processors.forEach(x -> x.process(context)); - } - -} diff --git a/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethod.java b/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethod.java deleted file mode 100644 index fa0a1fd..0000000 --- a/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethod.java +++ /dev/null @@ -1,66 +0,0 @@ -package net.tomatentum.marinara.reflection; - -import java.lang.reflect.InvocationTargetException; -import java.lang.reflect.Method; -import java.security.InvalidParameterException; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.List; - -import org.slf4j.Logger; - -import net.tomatentum.marinara.util.LoggerUtil; -import net.tomatentum.marinara.util.ReflectionUtil; - -public abstract class ReflectedMethod { - - private Logger logger = LoggerUtil.getLogger(getClass()); - - private Method method; - private Object containingObject; - - public ReflectedMethod(Method method, Object containingObject) { - if (!Arrays.asList(containingObject.getClass().getMethods()).contains(method)) - throw new InvalidParameterException("Method does not apply to specified handler"); - this.method = method; - this.containingObject = containingObject; - } - - public abstract Object getParameter(Object context, int index); - - public Object run(Object context) { - method.setAccessible(true); - try { - return method.invoke(containingObject, getParameters(context)); - }catch (IllegalAccessException | InvocationTargetException ex) { - logger.error("ReflectedMethod failed to run", ex); - return null; - } - } - - public Method method() { - return this.method; - } - - public Object containingObject() { - return this.containingObject; - } - - private Object[] getParameters(Object context) { - int parameterCount = method.getParameterCount(); - List parameters = new ArrayList<>(); - - for (int i = 0; i < parameterCount; i++) { - Object parameter; - if (i == 0) { - parameter = context; - }else - parameter = getParameter(context, i-1); - - logger.trace("Found parameter {}={} for method {}", parameter != null ? parameter.getClass().toString() : " ", parameter, ReflectionUtil.getFullMethodName(method)); - parameters.add(parameter); - } - return parameters.toArray(); - } - -} diff --git a/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactory.java b/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactory.java deleted file mode 100644 index e36da12..0000000 --- a/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactory.java +++ /dev/null @@ -1,20 +0,0 @@ -package net.tomatentum.marinara.reflection; - -import java.lang.reflect.Method; -import java.util.List; -import java.util.Optional; - -import net.tomatentum.marinara.Marinara; -import net.tomatentum.marinara.parser.AnnotationParser; - -public interface ReflectedMethodFactory { - Optional produce(Method method, Object containingClass); - ReflectedMethodFactory addFactory(Factory factory); - - public interface Factory { - - Optional produce(Marinara marinara, Method method, Object containingObject); - void addParser(ReflectedMethod method, List parser); - - } -} \ No newline at end of file diff --git a/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactoryImpl.java b/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactoryImpl.java deleted file mode 100644 index 485ea0c..0000000 --- a/lib/src/main/java/net/tomatentum/marinara/reflection/ReflectedMethodFactoryImpl.java +++ /dev/null @@ -1,62 +0,0 @@ -package net.tomatentum.marinara.reflection; - -import java.lang.reflect.Method; -import java.util.ArrayList; -import java.util.List; -import java.util.Optional; - -import org.slf4j.Logger; - -import net.tomatentum.marinara.Marinara; -import net.tomatentum.marinara.parser.AnnotationParser; -import net.tomatentum.marinara.util.LoggerUtil; -import net.tomatentum.marinara.util.ReflectionUtil; - -public class ReflectedMethodFactoryImpl implements ReflectedMethodFactory { - - private Logger logger = LoggerUtil.getLogger(getClass()); - - private Marinara marinara; - private List factories; - - public ReflectedMethodFactoryImpl(Marinara marinara) { - this(marinara, new ArrayList<>()); - } - - public ReflectedMethodFactoryImpl(Marinara marinara, List factories) { - this.marinara = marinara; - this.factories = factories; - } - - @Override - public Optional produce(Method method, Object containingClass) { - Optional imethod = this.factories.stream() - .map(f -> factoryProduce(f, method, containingClass)) - .filter(Optional::isPresent) - .map(Optional::get) - .findFirst(); - - if (imethod.isEmpty()) { - logger.debug("Could not produce a ReflectedMethod for Method {}", ReflectionUtil.getFullMethodName(method)); - } - - return imethod; - } - - @Override - public ReflectedMethodFactory addFactory(Factory factory) { - this.factories.add(factory); - return this; - } - - private Optional factoryProduce(Factory factory, Method method, Object containingClass) { - List parser = new ArrayList<>(); - Optional m = factory.produce(this.marinara, method, containingClass); - m.ifPresent(x -> { - factory.addParser(x, parser); - parser.forEach(AnnotationParser::parse); - }); - return m; - } - -} diff --git a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionCheckRegistry.java b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionCheckRegistry.java deleted file mode 100644 index 1093adf..0000000 --- a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionCheckRegistry.java +++ /dev/null @@ -1,40 +0,0 @@ -package net.tomatentum.marinara.registry; - -import java.lang.reflect.ParameterizedType; -import java.lang.reflect.Type; -import java.util.ArrayList; -import java.util.List; -import java.util.Optional; - -import org.slf4j.Logger; - -import io.leangen.geantyref.GenericTypeReflector; -import net.tomatentum.marinara.checks.InteractionCheck; -import net.tomatentum.marinara.util.LoggerUtil; - -public class InteractionCheckRegistry { - - private List> checks; - - private Logger logger = LoggerUtil.getLogger(getClass()); - - public InteractionCheckRegistry() { - this.checks = new ArrayList<>(); - } - - public void addCheck(InteractionCheck check) { - checks.add(check); - logger.info("Registered Check {}", check.getClass().getName()); - } - - public Optional> getCheckFromAnnotation(Type annotation) { - for (InteractionCheck interactionCheck : checks) { - ParameterizedType type = (ParameterizedType) GenericTypeReflector.getExactSuperType(interactionCheck.getClass(), InteractionCheck.class); - Type typeParam = type.getActualTypeArguments()[0]; - if (typeParam.equals(annotation)) - return Optional.of(interactionCheck); - } - return Optional.empty(); - } - -} diff --git a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionEntry.java b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionEntry.java deleted file mode 100644 index 5f0828e..0000000 --- a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionEntry.java +++ /dev/null @@ -1,90 +0,0 @@ -package net.tomatentum.marinara.registry; - -import java.util.Arrays; -import java.util.HashSet; -import java.util.Optional; -import java.util.Set; -import java.util.stream.Stream; - -import org.slf4j.Logger; - -import net.tomatentum.marinara.interaction.InteractionType; -import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; -import net.tomatentum.marinara.interaction.methods.InteractionMethod; -import net.tomatentum.marinara.util.LoggerUtil; - -public class InteractionEntry { - - public static InteractionEntry findEntry(Set entries, InteractionIdentifier identifier) { - Optional oentry = entries.stream() - .filter(i -> i.identifier().equals(identifier)) - .findFirst(); - - InteractionEntry entry = oentry.orElse(new InteractionEntry(identifier)); - if (oentry.isEmpty()) entries.add(entry); - return entry; - } - - private InteractionIdentifier identifier; - private Set methods; - - private Logger logger = LoggerUtil.getLogger(getClass()); - - public InteractionEntry(InteractionIdentifier identifier) { - this.identifier = identifier; - this.methods = new HashSet<>(); - } - - public InteractionEntry addMethod(InteractionMethod method) { - InteractionIdentifier midentifier = method.identifier(); - - if (!this.identifier().equals(midentifier)) - throw new IllegalArgumentException("Method's identifier did not equal the entry's identifier"); - - this.methods.add(method); - InteractionIdentifier.tryAddDescriptions(midentifier, midentifier); - logger.debug("Added method {} to entry {}", method.method().getName(), this.identifier); - return this; - } - - public Object[] runAll(Object context) { - return this.methods.stream() - .map(x -> { - logger.debug("Running Method {} from {} with context {}", x, this, context); - return x.run(context); - }) - .flatMap(o -> o instanceof Object[] oArray ? Arrays.stream(oArray) : Stream.of(o)) - .toArray(); - } - - @Override - public boolean equals(Object obj) { - if (!(obj instanceof InteractionEntry)) - return false; - InteractionEntry other = (InteractionEntry) obj; - return other.identifier().equals(identifier()); - } - - @Override - public int hashCode() { - return this.identifier().hashCode(); - } - - @Override - public String toString() { - return "InteractionEntry(%s)".formatted(identifier().toString()); - } - - public InteractionType type() { - return identifier().type(); - } - - public InteractionIdentifier identifier() { - return identifier; - } - - public Set methods() { - return methods; - } - -} diff --git a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java b/lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java deleted file mode 100644 index 0c7b244..0000000 --- a/lib/src/main/java/net/tomatentum/marinara/registry/InteractionRegistry.java +++ /dev/null @@ -1,80 +0,0 @@ -package net.tomatentum.marinara.registry; - -import java.lang.reflect.Method; -import java.util.Arrays; -import java.util.HashSet; -import java.util.List; -import java.util.Optional; -import java.util.Set; - -import org.slf4j.Logger; - -import net.tomatentum.marinara.Marinara; -import net.tomatentum.marinara.interaction.InteractionHandler; -import net.tomatentum.marinara.interaction.InteractionType; -import net.tomatentum.marinara.interaction.commands.SlashCommandDefinition; -import net.tomatentum.marinara.interaction.components.methods.ButtonInteractionMethod; -import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; -import net.tomatentum.marinara.interaction.ident.RootCommandIdentifier; -import net.tomatentum.marinara.util.LoggerUtil; -import net.tomatentum.marinara.util.ObjectAggregator; -import net.tomatentum.marinara.interaction.methods.AutoCompleteInteractionMethod; -import net.tomatentum.marinara.interaction.methods.InteractionMethod; -import net.tomatentum.marinara.interaction.methods.SlashCommandInteractionMethod; -import net.tomatentum.marinara.reflection.ReflectedMethod; - -public class InteractionRegistry { - private Logger logger = LoggerUtil.getLogger(getClass()); - private Set interactions; - private Marinara marinara; - - public InteractionRegistry(Marinara marinara) { - this.interactions = new HashSet<>(); - this.marinara = marinara; - marinara.getReflectedMethodFactory() - .addFactory(new AutoCompleteInteractionMethod.Factory()) - .addFactory(new SlashCommandInteractionMethod.Factory()) - .addFactory(new ButtonInteractionMethod.Factory()); - - } - - public void addInteractions(InteractionHandler interactionHandler) { - for (Method method : interactionHandler.getClass().getDeclaredMethods()) { - Optional rMethod = this.marinara.getReflectedMethodFactory().produce(method, interactionHandler); - rMethod.ifPresent(x -> { - if (x instanceof InteractionMethod) { - InteractionMethod iMethod = (InteractionMethod) x; - InteractionEntry.findEntry(interactions, iMethod.identifier()).addMethod(iMethod); - logger.debug("Added {} method from {}", iMethod.method().getName(), interactionHandler.getClass().getSimpleName()); - } - }); - } - logger.info("Added all Interactions from {}", interactionHandler.getClass().getSimpleName()); - } - - public void registerCommands() { - List slashIdentifiers = interactions.stream() - .filter((x) -> x.type().equals(InteractionType.COMMAND)) - .map((x) -> x.identifier()) - .toList(); - - SlashCommandDefinition[] defs = new ObjectAggregator( - i -> Arrays.asList((RootCommandIdentifier)i.rootNode()), - SlashCommandDefinition::addIdentifier, - SlashCommandDefinition::new) - .aggregate(slashIdentifiers) - .toArray(SlashCommandDefinition[]::new); - - marinara.getWrapper().getRegisterer().register(defs); - } - - public Optional findFor(InteractionIdentifier identifier) { - return this.interactions.stream() - .filter(x -> x.identifier().equals(identifier)) - .findFirst(); - } - - public Set interactions() { - return this.interactions; - } -} diff --git a/lib/src/main/java/net/tomatentum/marinara/util/ReflectionUtil.java b/lib/src/main/java/net/tomatentum/marinara/util/ReflectionUtil.java deleted file mode 100644 index 5bda90f..0000000 --- a/lib/src/main/java/net/tomatentum/marinara/util/ReflectionUtil.java +++ /dev/null @@ -1,107 +0,0 @@ -package net.tomatentum.marinara.util; - -import java.lang.annotation.Annotation; -import java.lang.reflect.Method; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.List; -import java.util.Objects; - -public final class ReflectionUtil { - - public static boolean isAnnotationPresent(Method method, Class annotationClass) { - if (method.isAnnotationPresent(annotationClass) || method.getDeclaringClass().isAnnotationPresent(annotationClass)) - return true; - - return false; - } - - public static T getAnnotation(Method method, Class annotationClass) { - return method.isAnnotationPresent(annotationClass) ? - method.getAnnotation(annotationClass) : - method.getDeclaringClass().getAnnotation(annotationClass); - } - - public static int getCastDepth(Class child, Class parent) { - - if (parent.equals(Object.class)) - return Integer.MAX_VALUE; - - if (!parent.isAssignableFrom(child)) { - throw new IllegalArgumentException("The specified class is not a child class of the specified parent."); - } - - int depth = 0; - Class curr = child; - List> parents = new ArrayList<>(); - - while (!curr.equals(parent)) { - depth++; - parents.add(curr.getSuperclass()); - parents.addAll(Arrays.asList(curr.getInterfaces())); - - for (Class currParent : parents) { - if (currParent != null && parent.isAssignableFrom(currParent)) { - curr = currParent; - break; - } - } - parents.clear(); - } - - return depth; - } - - public static Method getMostSpecificMethod(Method[] methods, Class... parameters) { - List compatibleMethods = Arrays.stream(methods) - .filter(x -> isMethodCallable(x, parameters)) - .toList(); - - if (compatibleMethods.size() == 0) - throw new IllegalArgumentException("There are no compatible Methods provided"); - - for (int i = 0; i < parameters.length; i++) { - final int currI = i; - Class[] parameterTypes = compatibleMethods.stream() - .map(x -> x.getParameterTypes()[currI]) - .toArray(x -> new Class[x]); - - Class mostSpecific = getMostSpecificClass(parameterTypes, parameters[i]); - - compatibleMethods = compatibleMethods.stream() - .filter(x -> Objects.equals(x.getParameterTypes()[currI], mostSpecific)) - .toList(); - } - - return compatibleMethods.getFirst(); - } - - public static Class getMostSpecificClass(Class[] classes, Class base) { - int min = Integer.MAX_VALUE; - Class currMostSpecific = null; - for (Class currClass : classes) { - int currCastDepth = getCastDepth(base, currClass); - if (currCastDepth <= min) { - min = currCastDepth; - currMostSpecific = currClass; - } - } - return currMostSpecific; - } - - public static boolean isMethodCallable(Method method, Class... parameters) { - if (!Objects.equals(method.getParameterCount(), parameters.length)) - return false; - - Class[] methodParams = method.getParameterTypes(); - for (int i = 0; i < parameters.length; i++) { - if (!methodParams[i].isAssignableFrom(parameters[i])) - return false; - } - return true; - } - - public static String getFullMethodName(Method method) { - return method.getDeclaringClass().getName() + "." + method.getName(); - } -} diff --git a/lib/src/main/java/net/tomatentum/marinara/wrapper/IdentifierProvider.java b/lib/src/main/java/net/tomatentum/marinara/wrapper/IdentifierProvider.java index 0adbee9..d96d6f2 100644 --- a/lib/src/main/java/net/tomatentum/marinara/wrapper/IdentifierProvider.java +++ b/lib/src/main/java/net/tomatentum/marinara/wrapper/IdentifierProvider.java @@ -10,9 +10,9 @@ import java.util.Map; import org.slf4j.Logger; import io.leangen.geantyref.GenericTypeReflector; +import net.tomatentum.cutin.util.ReflectionUtil; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; import net.tomatentum.marinara.util.LoggerUtil; -import net.tomatentum.marinara.util.ReflectionUtil; public class IdentifierProvider { diff --git a/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/AutoCompleteTest.java b/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/AutoCompleteTest.java index 2c20695..3f15b52 100644 --- a/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/AutoCompleteTest.java +++ b/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/AutoCompleteTest.java @@ -38,7 +38,7 @@ class AutoCompleteTest { LibraryWrapper wrapper = new Discord4JWrapper(null); //null okay as we don't use the discord API in this test. Marinara marinara = Marinara.load(wrapper); - marinara.getRegistry().addInteractions(new TestAutocomplete()); + marinara.getInteractionContainer().addAllMethods(new TestAutocomplete()); wrapper.handleInteraction(autoCompleteEventMock); verify(autoCompleteEventMock).respondWithSuggestions(any()); } diff --git a/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/ButtonTest.java b/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/ButtonTest.java index bb0c70b..4e8ff2b 100644 --- a/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/ButtonTest.java +++ b/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/ButtonTest.java @@ -13,15 +13,15 @@ import net.tomatentum.marinara.wrapper.LibraryWrapper; import net.tomatentum.marinara.wrapper.discord4j.Discord4JWrapper; @TestInstance(Lifecycle.PER_CLASS) -public class ButtonTest { +class ButtonTest { @Test - public void testButtonExecution() { + void testButtonExecution() { ButtonInteractionEvent buttonEventMock = CommonMocks.getButtonEventMock("test"); LibraryWrapper wrapper = new Discord4JWrapper(null); //null okay as we don't use the discord API in this test. Marinara marinara = Marinara.load(wrapper); - marinara.getRegistry().addInteractions(new TestButton()); + marinara.getInteractionContainer().addAllMethods(new TestButton()); wrapper.handleInteraction(buttonEventMock); assertTrue(TestButton.didRun); } diff --git a/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/InteractionCheckTest.java b/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/InteractionCheckTest.java index 0e7874c..8e0a9b7 100644 --- a/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/InteractionCheckTest.java +++ b/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/InteractionCheckTest.java @@ -24,16 +24,16 @@ import net.tomatentum.marinara.wrapper.discord4j.checks.PermissionCheck; import reactor.core.publisher.Mono; @TestInstance(Lifecycle.PER_CLASS) -public class InteractionCheckTest { +class InteractionCheckTest { @Test - public void testInteractionCheck() { + void testInteractionCheck() { ButtonInteractionEvent buttonEventMock = CommonMocks.getButtonEventMock("test"); LibraryWrapper wrapper = new Discord4JWrapper(null); Marinara marinara = Marinara.load(wrapper); - marinara.getCheckRegistry().addCheck(new TestInteractionCheck()); - marinara.getRegistry().addInteractions(new TestButton()); + marinara.getCheckContainer().addAllMethods(new TestInteractionCheck()); + marinara.getInteractionContainer().addAllMethods(new TestButton()); wrapper.handleInteraction(buttonEventMock); assertTrue(TestInteractionCheck.preExecuted); @@ -42,7 +42,7 @@ public class InteractionCheckTest { } @Test - public void testPermissionCheck() { + void testPermissionCheck() { Member memberMock = mock(); Interaction interactionMock = mock(); @@ -54,8 +54,8 @@ public class InteractionCheckTest { LibraryWrapper wrapper = new Discord4JWrapper(null); Marinara marinara = Marinara.load(wrapper); - marinara.getCheckRegistry().addCheck(new PermissionCheck()); - marinara.getRegistry().addInteractions(new TestButton()); + marinara.getCheckContainer().addAllMethods(new PermissionCheck()); + marinara.getInteractionContainer().addAllMethods(new TestButton()); wrapper.handleInteraction(buttonEventMock); assertFalse(TestButton.didPermRun); diff --git a/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/SlashCommandTest.java b/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/SlashCommandTest.java index 377f123..54ff156 100644 --- a/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/SlashCommandTest.java +++ b/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/SlashCommandTest.java @@ -22,9 +22,9 @@ import net.tomatentum.marinara.Marinara; import net.tomatentum.marinara.wrapper.LibraryWrapper; import net.tomatentum.marinara.wrapper.discord4j.Discord4JWrapper; @TestInstance(Lifecycle.PER_CLASS) -public class SlashCommandTest { +class SlashCommandTest { - String DISCORD_TOKEN = System.getenv("DISCORD_TEST_TOKEN"); + private static String DISCORD_TOKEN = System.getenv("DISCORD_TEST_TOKEN"); GatewayDiscordClient client; @BeforeAll @@ -41,8 +41,8 @@ public class SlashCommandTest { @Test void testSlashCommand() { Marinara marinara = Marinara.load(new Discord4JWrapper(client)); - marinara.getRegistry().addInteractions(new TestCommand()); - marinara.getRegistry().registerCommands(); + marinara.getInteractionContainer().addAllMethods(new TestCommand()); + marinara.registerCommands(); System.out.println("Success!"); } @@ -64,7 +64,7 @@ public class SlashCommandTest { LibraryWrapper wrapper = new Discord4JWrapper(client); Marinara marinara = Marinara.load(wrapper); - marinara.getRegistry().addInteractions(new TestCommand()); + marinara.getInteractionContainer().addAllMethods(new TestCommand()); wrapper.handleInteraction(eventMock); } diff --git a/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/TestAutocomplete.java b/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/TestAutocomplete.java index 18c0965..1c4517a 100644 --- a/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/TestAutocomplete.java +++ b/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/TestAutocomplete.java @@ -2,8 +2,6 @@ package net.tomatentum.marinara.test.discord4j; import static org.junit.jupiter.api.Assertions.assertEquals; -import java.util.Collections; - import discord4j.core.event.domain.interaction.ChatInputAutoCompleteEvent; import discord4j.core.event.domain.interaction.ChatInputInteractionEvent; import discord4j.discordjson.json.ApplicationCommandOptionChoiceData; @@ -23,9 +21,8 @@ public class TestAutocomplete implements InteractionHandler { autocompletes = @AutoComplete("testAuto") ) ) - @AutoComplete("testAuto") public void exec(ChatInputInteractionEvent context) { - + // Not executed just there for autocomplete to work } @AutoComplete("testAuto") diff --git a/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/TestCommand.java b/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/TestCommand.java index 9482748..3430155 100644 --- a/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/TestCommand.java +++ b/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/TestCommand.java @@ -26,7 +26,7 @@ public class TestCommand implements InteractionHandler { } ) public void exec(ChatInputInteractionEvent event, String test) { - assertEquals(test, "test"); + assertEquals("test", test); System.out.println("Success!"); } } diff --git a/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/AutoCompleteTest.java b/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/AutoCompleteTest.java index e10d19c..8724326 100644 --- a/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/AutoCompleteTest.java +++ b/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/AutoCompleteTest.java @@ -16,10 +16,10 @@ import net.tomatentum.marinara.Marinara; import net.tomatentum.marinara.wrapper.LibraryWrapper; import net.tomatentum.marinara.wrapper.javacord.JavacordWrapper; -public class AutoCompleteTest { +class AutoCompleteTest { @Test - public void testAutocomplete() { + void testAutocomplete() { SlashCommandInteractionOption optionMock = mock(); AutocompleteInteraction autocompleteInteractionMock = mock(); @@ -33,7 +33,7 @@ public class AutoCompleteTest { LibraryWrapper wrapper = new JavacordWrapper(null); //null okay as we don't use the discord API in this test. Marinara marinara = Marinara.load(wrapper); - marinara.getRegistry().addInteractions(new TestAutocomplete()); + marinara.getInteractionContainer().addAllMethods(new TestAutocomplete()); wrapper.handleInteraction(autocompleteInteractionMock); verify(autocompleteInteractionMock).respondWithChoices(any()); } diff --git a/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/ButtonTest.java b/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/ButtonTest.java index dc85d36..5e8a9b4 100644 --- a/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/ButtonTest.java +++ b/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/ButtonTest.java @@ -12,13 +12,13 @@ import net.tomatentum.marinara.wrapper.LibraryWrapper; import net.tomatentum.marinara.wrapper.javacord.JavacordWrapper; @TestInstance(Lifecycle.PER_CLASS) -public class ButtonTest { +class ButtonTest { @Test - public void testButtonExecution() { + void testButtonExecution() { LibraryWrapper wrapper = new JavacordWrapper(null); //null okay as we don't use the discord API in this test. Marinara marinara = Marinara.load(wrapper); - marinara.getRegistry().addInteractions(new TestButton()); + marinara.getInteractionContainer().addAllMethods(new TestButton()); wrapper.handleInteraction(CommonMocks.getButtonInteractionMock("test")); assertTrue(TestButton.didRun); } diff --git a/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/InteractionCheckTest.java b/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/InteractionCheckTest.java index 950c314..a522a27 100644 --- a/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/InteractionCheckTest.java +++ b/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/InteractionCheckTest.java @@ -19,25 +19,25 @@ import net.tomatentum.marinara.wrapper.javacord.JavacordWrapper; import net.tomatentum.marinara.wrapper.javacord.checks.PermissionCheck; @TestInstance(Lifecycle.PER_CLASS) -public class InteractionCheckTest { +class InteractionCheckTest { @Test - public void testInteractionCheck() { + void testInteractionCheck() { LibraryWrapper wrapper = new JavacordWrapper(null); Marinara marinara = Marinara.load(wrapper); - marinara.getCheckRegistry().addCheck(new TestInteractionCheck()); - marinara.getRegistry().addInteractions(new TestButton()); + marinara.getCheckContainer().addAllMethods(new TestInteractionCheck()); + marinara.getInteractionContainer().addAllMethods(new TestButton()); wrapper.handleInteraction(CommonMocks.getButtonInteractionMock("test")); assertTrue(TestInteractionCheck.preExecuted); assertTrue(TestInteractionCheck.postExecuted); } @Test - public void testPermissionCheck() { + void testPermissionCheck() { LibraryWrapper wrapper = new JavacordWrapper(null); Marinara marinara = Marinara.load(wrapper); - marinara.getCheckRegistry().addCheck(new PermissionCheck()); - marinara.getRegistry().addInteractions(new TestButton()); + marinara.getCheckContainer().addAllMethods(new PermissionCheck()); + marinara.getInteractionContainer().addAllMethods(new TestButton()); Server serverMock = mock(); ButtonInteraction buttonInteractionMock = CommonMocks.getButtonInteractionMock("permissionCheck", serverMock); diff --git a/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/SlashCommandTest.java b/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/SlashCommandTest.java index 8fd80d0..ce645a8 100644 --- a/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/SlashCommandTest.java +++ b/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/SlashCommandTest.java @@ -20,7 +20,7 @@ import net.tomatentum.marinara.Marinara; import net.tomatentum.marinara.wrapper.LibraryWrapper; import net.tomatentum.marinara.wrapper.javacord.JavacordWrapper; @TestInstance(Lifecycle.PER_CLASS) -public class SlashCommandTest { +class SlashCommandTest { String DISCORD_TOKEN = System.getenv("DISCORD_TEST_TOKEN"); DiscordApi api; @@ -41,8 +41,8 @@ public class SlashCommandTest { @Test void testSlashCommand() { Marinara marinara = Marinara.load(new JavacordWrapper(api)); - marinara.getRegistry().addInteractions(new TestCommand()); - marinara.getRegistry().registerCommands(); + marinara.getInteractionContainer().addAllMethods(new TestCommand()); + marinara.registerCommands(); System.out.println("Success!"); } @@ -50,7 +50,7 @@ public class SlashCommandTest { void testSlashCommandExecution() { LibraryWrapper wrapper = new JavacordWrapper(api); Marinara marinara = Marinara.load(wrapper); - marinara.getRegistry().addInteractions(new TestCommand()); + marinara.getInteractionContainer().addAllMethods(new TestCommand()); SlashCommandInteractionOption optionMock = mock(); SlashCommandInteraction interactionMock = mock(); diff --git a/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/TestAutocomplete.java b/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/TestAutocomplete.java index da37684..0285cff 100644 --- a/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/TestAutocomplete.java +++ b/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/TestAutocomplete.java @@ -4,7 +4,6 @@ import static org.junit.jupiter.api.Assertions.assertEquals; import java.util.Collections; -import org.javacord.api.event.interaction.SlashCommandCreateEvent; import org.javacord.api.interaction.AutocompleteInteraction; import org.javacord.api.interaction.SlashCommandInteraction; @@ -24,15 +23,14 @@ public class TestAutocomplete implements InteractionHandler { autocompletes = @AutoComplete("testAuto") ) ) - @AutoComplete("testAuto") public void exec(SlashCommandInteraction context) { - + //only here for command definition } @AutoComplete("testAuto") public void autocomplete(AutocompleteInteraction context, String value) { System.out.println("Success!"); - assertEquals(value, "test"); + assertEquals("test", value); context.respondWithChoices(Collections.emptyList()); } diff --git a/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/TestButton.java b/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/TestButton.java index f838e5e..e1e65ac 100644 --- a/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/TestButton.java +++ b/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/TestButton.java @@ -16,8 +16,8 @@ import net.tomatentum.marinara.wrapper.javacord.checks.PermissionCheck.HasPermis public class TestButton implements InteractionHandler { - public static boolean didRun = false; + @Button("test") @TestCheck public void exec(ButtonInteraction interaction, TextChannel channel, Message message, User member, Server server) { diff --git a/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/TestCommand.java b/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/TestCommand.java index d6f371c..2a95ba7 100644 --- a/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/TestCommand.java +++ b/wrapper/javacord/src/test/java/net/tomatentum/marinara/test/javacord/TestCommand.java @@ -11,6 +11,7 @@ import net.tomatentum.marinara.interaction.commands.annotation.SlashCommandOptio import net.tomatentum.marinara.interaction.commands.option.SlashCommandOptionType; public class TestCommand implements InteractionHandler { + @SlashCommand( name = "test", description = "testingen", @@ -27,7 +28,8 @@ public class TestCommand implements InteractionHandler { } ) public void exec(SlashCommandInteraction interaction, String test) { - assertEquals(test, "test"); + assertEquals("test", test); System.out.println("Success!"); } + } -- 2.47.2 From 83b446e6fb6ff64fd819085b19bf0fc817a99d27 Mon Sep 17 00:00:00 2001 From: Tueem Date: Mon, 14 Apr 2025 02:09:33 +0200 Subject: [PATCH 16/18] refactor(logger): remove LoggerUtil and add simplelogger for tests --- gradle/libs.versions.toml | 1 + .../net/tomatentum/marinara/Marinara.java | 4 +- .../marinara/checks/AppliedCheck.java | 4 +- .../commands/SlashCommandDefinition.java | 4 +- .../ident/InteractionIdentifier.java | 4 +- .../processor/InteractionMethodProcessor.java | 4 +- .../marinara/parser/ButtonParser.java | 4 +- .../parser/InteractionCheckClassParser.java | 6 ++ .../parser/InteractionCheckParser.java | 4 +- .../marinara/parser/SlashCommandParser.java | 4 +- .../tomatentum/marinara/util/LoggerUtil.java | 17 ------ .../marinara/util/SimpleLogger.java | 55 ------------------- .../marinara/wrapper/CommandConverter.java | 4 +- .../marinara/wrapper/CommandRegisterer.java | 10 +++- .../marinara/wrapper/IdentifierProvider.java | 9 ++- wrapper/discord4j/build.gradle.kts | 2 + .../Discord4JRegistererStrategy.java | 2 +- .../test/resources/simplelogger.properties | 7 +++ wrapper/javacord/build.gradle.kts | 2 + .../test/resources/simplelogger.properties | 7 +++ 20 files changed, 57 insertions(+), 97 deletions(-) delete mode 100644 lib/src/main/java/net/tomatentum/marinara/util/LoggerUtil.java delete mode 100644 lib/src/main/java/net/tomatentum/marinara/util/SimpleLogger.java create mode 100644 wrapper/discord4j/src/test/resources/simplelogger.properties create mode 100644 wrapper/javacord/src/test/resources/simplelogger.properties diff --git a/gradle/libs.versions.toml b/gradle/libs.versions.toml index fb7c6f0..692ea9c 100644 --- a/gradle/libs.versions.toml +++ b/gradle/libs.versions.toml @@ -13,6 +13,7 @@ cutin = "0.1.1-cad019e" [libraries] junit-jupiter = { module = "org.junit.jupiter:junit-jupiter", version.ref = "junit-jupiter" } slf4j = { module = "org.slf4j:slf4j-api", version.ref = "slf4j"} +slf4j-simple = { module = "org.slf4j:slf4j-simple", version.ref = "slf4j"} javacord = { module = "org.javacord:javacord", version.ref = "javacord"} discord4j = { module = "com.discord4j:discord4j-core", version.ref = "discord4j"} geantyref = { module = "io.leangen.geantyref:geantyref", version.ref = "geantyref"} diff --git a/lib/src/main/java/net/tomatentum/marinara/Marinara.java b/lib/src/main/java/net/tomatentum/marinara/Marinara.java index 643271c..8f65794 100644 --- a/lib/src/main/java/net/tomatentum/marinara/Marinara.java +++ b/lib/src/main/java/net/tomatentum/marinara/Marinara.java @@ -4,6 +4,7 @@ import java.util.Arrays; import java.util.List; import org.slf4j.Logger; +import org.slf4j.LoggerFactory; import net.tomatentum.cutin.MethodExecutor; import net.tomatentum.cutin.ProcessorMethodExecutor; @@ -18,14 +19,13 @@ import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; import net.tomatentum.marinara.interaction.ident.RootCommandIdentifier; import net.tomatentum.marinara.interaction.processor.AutocompleteInteractionProcessor; import net.tomatentum.marinara.interaction.processor.DirectInteractionProcessor; -import net.tomatentum.marinara.util.LoggerUtil; import net.tomatentum.marinara.util.ObjectAggregator; import net.tomatentum.marinara.wrapper.IdentifierProvider; import net.tomatentum.marinara.wrapper.LibraryWrapper; public class Marinara { - private Logger logger = LoggerUtil.getLogger(getClass()); + private Logger logger = LoggerFactory.getLogger(getClass()); public static Marinara load(LibraryWrapper wrapper) { return new Marinara(wrapper); diff --git a/lib/src/main/java/net/tomatentum/marinara/checks/AppliedCheck.java b/lib/src/main/java/net/tomatentum/marinara/checks/AppliedCheck.java index 50431ce..5dac01f 100644 --- a/lib/src/main/java/net/tomatentum/marinara/checks/AppliedCheck.java +++ b/lib/src/main/java/net/tomatentum/marinara/checks/AppliedCheck.java @@ -3,9 +3,9 @@ package net.tomatentum.marinara.checks; import java.lang.annotation.Annotation; import org.slf4j.Logger; +import org.slf4j.LoggerFactory; import net.tomatentum.cutin.method.ReflectedMethod; -import net.tomatentum.marinara.util.LoggerUtil; public record AppliedCheck( Annotation annotation, @@ -13,7 +13,7 @@ public record AppliedCheck( ReflectedMethod postExec ) { - private static Logger logger = LoggerUtil.getLogger(AppliedCheck.class); + private static Logger logger = LoggerFactory.getLogger(AppliedCheck.class); public boolean pre(Object context) { logger.debug("Running InteractionCheck preExec {} with annotation {}", preExec(), annotation()); diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/commands/SlashCommandDefinition.java b/lib/src/main/java/net/tomatentum/marinara/interaction/commands/SlashCommandDefinition.java index 0fc0f67..0c931c8 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/commands/SlashCommandDefinition.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/commands/SlashCommandDefinition.java @@ -5,6 +5,7 @@ import java.util.List; import java.util.Set; import org.slf4j.Logger; +import org.slf4j.LoggerFactory; import net.tomatentum.marinara.interaction.commands.annotation.CommandChoices; import net.tomatentum.marinara.interaction.commands.annotation.SlashCommandOption; @@ -14,7 +15,6 @@ import net.tomatentum.marinara.interaction.commands.choice.EnumChoices; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; import net.tomatentum.marinara.interaction.ident.RootCommandIdentifier; import net.tomatentum.marinara.interaction.ident.SlashCommandIdentifier; -import net.tomatentum.marinara.util.LoggerUtil; public class SlashCommandDefinition { @@ -30,7 +30,7 @@ public class SlashCommandDefinition { private RootCommandIdentifier rootIdentifier; private boolean isRootCommand; - private Logger logger = LoggerUtil.getLogger(getClass()); + private Logger logger = LoggerFactory.getLogger(getClass()); public SlashCommandDefinition(RootCommandIdentifier rootIdentifier) { this.entries = new HashSet<>(); diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/ident/InteractionIdentifier.java b/lib/src/main/java/net/tomatentum/marinara/interaction/ident/InteractionIdentifier.java index 5f4e090..2fd6b42 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/ident/InteractionIdentifier.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/ident/InteractionIdentifier.java @@ -91,8 +91,8 @@ public class InteractionIdentifier { @Override public String toString() { if (parent() == null) - return name(); - return "%s.%s".formatted(name(), parent().toString()); + return name() + " - " + type(); + return "%s:%s".formatted(name(), parent().toString()); } public static class Builder { diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/processor/InteractionMethodProcessor.java b/lib/src/main/java/net/tomatentum/marinara/interaction/processor/InteractionMethodProcessor.java index 9424c75..273ff00 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/processor/InteractionMethodProcessor.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/processor/InteractionMethodProcessor.java @@ -3,17 +3,17 @@ package net.tomatentum.marinara.interaction.processor; import java.util.Set; import org.slf4j.Logger; +import org.slf4j.LoggerFactory; import net.tomatentum.cutin.MethodProcessor; import net.tomatentum.cutin.container.MethodContainer; import net.tomatentum.marinara.interaction.InteractionType; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; -import net.tomatentum.marinara.util.LoggerUtil; import net.tomatentum.marinara.wrapper.IdentifierProvider; public abstract class InteractionMethodProcessor implements MethodProcessor { - private Logger logger = LoggerUtil.getLogger(getClass()); + private Logger logger = LoggerFactory.getLogger(getClass()); private IdentifierProvider provider; private Set types; diff --git a/lib/src/main/java/net/tomatentum/marinara/parser/ButtonParser.java b/lib/src/main/java/net/tomatentum/marinara/parser/ButtonParser.java index a2d533e..7af03fc 100644 --- a/lib/src/main/java/net/tomatentum/marinara/parser/ButtonParser.java +++ b/lib/src/main/java/net/tomatentum/marinara/parser/ButtonParser.java @@ -4,18 +4,18 @@ import java.lang.reflect.Method; import java.util.function.Consumer; import org.slf4j.Logger; +import org.slf4j.LoggerFactory; import net.tomatentum.cutin.MethodParser; import net.tomatentum.cutin.util.ReflectionUtil; import net.tomatentum.marinara.interaction.annotation.Button; -import net.tomatentum.marinara.util.LoggerUtil; public class ButtonParser implements MethodParser { private Method method; private Consumer consumer; - private Logger logger = LoggerUtil.getLogger(getClass()); + private Logger logger = LoggerFactory.getLogger(getClass()); public ButtonParser(Method method, Consumer consumer) { this.method = method; diff --git a/lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckClassParser.java b/lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckClassParser.java index 0023e3f..26da135 100644 --- a/lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckClassParser.java +++ b/lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckClassParser.java @@ -4,12 +4,17 @@ import java.lang.reflect.ParameterizedType; import java.lang.reflect.Type; import java.util.function.Consumer; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + import io.leangen.geantyref.GenericTypeReflector; import net.tomatentum.cutin.MethodParser; import net.tomatentum.marinara.checks.InteractionCheck; public class InteractionCheckClassParser implements MethodParser { + private Logger logger = LoggerFactory.getLogger(getClass()); + private Class> interactionCheckType; private Consumer annotationTypeConsumer; @@ -22,6 +27,7 @@ public class InteractionCheckClassParser implements MethodParser { public void parse() { ParameterizedType type = (ParameterizedType) GenericTypeReflector.getExactSuperType(interactionCheckType, InteractionCheck.class); Type typeParam = type.getActualTypeArguments()[0]; + logger.trace("Parsed InteractionCheck Annotation {}", typeParam); this.annotationTypeConsumer.accept(typeParam); } diff --git a/lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckParser.java b/lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckParser.java index 4e3a36c..ebdcd48 100644 --- a/lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckParser.java +++ b/lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckParser.java @@ -6,6 +6,7 @@ import java.util.Arrays; import java.util.function.Consumer; import org.slf4j.Logger; +import org.slf4j.LoggerFactory; import net.tomatentum.cutin.MethodParser; import net.tomatentum.cutin.container.MethodContainer; @@ -14,7 +15,6 @@ import net.tomatentum.marinara.checks.AppliedCheck; import net.tomatentum.marinara.checks.CheckExecutionContext; import net.tomatentum.marinara.checks.CheckMethodIdentifier; import net.tomatentum.marinara.checks.CheckMethodIdentifier.CheckMethodType; -import net.tomatentum.marinara.util.LoggerUtil; public class InteractionCheckParser implements MethodParser { @@ -22,7 +22,7 @@ public class InteractionCheckParser implements MethodParser { private Method method; private Consumer consumer; - private Logger logger = LoggerUtil.getLogger(getClass()); + private Logger logger = LoggerFactory.getLogger(getClass()); public InteractionCheckParser(Method method, Consumer consumer, MethodContainer checkContainer) { this.checkContainer = checkContainer; diff --git a/lib/src/main/java/net/tomatentum/marinara/parser/SlashCommandParser.java b/lib/src/main/java/net/tomatentum/marinara/parser/SlashCommandParser.java index c6ca43b..2f1bab5 100644 --- a/lib/src/main/java/net/tomatentum/marinara/parser/SlashCommandParser.java +++ b/lib/src/main/java/net/tomatentum/marinara/parser/SlashCommandParser.java @@ -4,6 +4,7 @@ import java.lang.reflect.Method; import java.util.function.Consumer; import org.slf4j.Logger; +import org.slf4j.LoggerFactory; import net.tomatentum.cutin.MethodParser; import net.tomatentum.cutin.util.ReflectionUtil; @@ -13,14 +14,13 @@ import net.tomatentum.marinara.interaction.commands.annotation.SubCommand; import net.tomatentum.marinara.interaction.commands.annotation.SubCommandGroup; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; import net.tomatentum.marinara.interaction.ident.SlashCommandIdentifier; -import net.tomatentum.marinara.util.LoggerUtil; public class SlashCommandParser implements MethodParser { private Method method; private Consumer consumer; - private Logger logger = LoggerUtil.getLogger(getClass()); + private Logger logger = LoggerFactory.getLogger(getClass()); public SlashCommandParser(Method method, Consumer consumer) { this.method = method; diff --git a/lib/src/main/java/net/tomatentum/marinara/util/LoggerUtil.java b/lib/src/main/java/net/tomatentum/marinara/util/LoggerUtil.java deleted file mode 100644 index 54eb77b..0000000 --- a/lib/src/main/java/net/tomatentum/marinara/util/LoggerUtil.java +++ /dev/null @@ -1,17 +0,0 @@ -package net.tomatentum.marinara.util; - -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import org.slf4j.helpers.NOPLoggerFactory; - -public class LoggerUtil { - public static Logger getLogger(String name) { - if (LoggerFactory.getILoggerFactory() instanceof NOPLoggerFactory) - return new SimpleLogger(name); - return LoggerFactory.getLogger(name); - } - - public static Logger getLogger(Class clazz) { - return getLogger(clazz.getName()); - } -} diff --git a/lib/src/main/java/net/tomatentum/marinara/util/SimpleLogger.java b/lib/src/main/java/net/tomatentum/marinara/util/SimpleLogger.java deleted file mode 100644 index db6a2a5..0000000 --- a/lib/src/main/java/net/tomatentum/marinara/util/SimpleLogger.java +++ /dev/null @@ -1,55 +0,0 @@ -package net.tomatentum.marinara.util; - -import org.slf4j.Marker; -import org.slf4j.event.Level; -import org.slf4j.helpers.LegacyAbstractLogger; -import org.slf4j.helpers.MessageFormatter; - -public class SimpleLogger extends LegacyAbstractLogger { - - private String name; - - public SimpleLogger(String name) { - this.name = name; - } - - @Override - public boolean isTraceEnabled() { - return true; - } - - @Override - public boolean isDebugEnabled() { - return true; - } - - @Override - public boolean isInfoEnabled() { - return true; - } - - @Override - public boolean isWarnEnabled() { - return true; - } - - @Override - public boolean isErrorEnabled() { - return true; - } - - @Override - protected String getFullyQualifiedCallerName() { - return this.name; - } - - @Override - protected void handleNormalizedLoggingCall(Level level, Marker marker, String messagePattern, Object[] arguments, - Throwable throwable) { - String formatted = MessageFormatter.basicArrayFormat(messagePattern, arguments); - System.out.println("[%s] %s => %s".formatted(level, this.name, formatted)); - } - - - -} diff --git a/lib/src/main/java/net/tomatentum/marinara/wrapper/CommandConverter.java b/lib/src/main/java/net/tomatentum/marinara/wrapper/CommandConverter.java index 0183de4..5624f2a 100644 --- a/lib/src/main/java/net/tomatentum/marinara/wrapper/CommandConverter.java +++ b/lib/src/main/java/net/tomatentum/marinara/wrapper/CommandConverter.java @@ -5,6 +5,7 @@ import java.util.Arrays; import java.util.List; import org.slf4j.Logger; +import org.slf4j.LoggerFactory; import net.tomatentum.marinara.interaction.commands.SlashCommandDefinition; import net.tomatentum.marinara.interaction.commands.annotation.SlashCommandOption; @@ -12,7 +13,6 @@ import net.tomatentum.marinara.interaction.commands.annotation.SlashCommandOptio import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; import net.tomatentum.marinara.interaction.ident.RootCommandIdentifier; import net.tomatentum.marinara.interaction.ident.SlashCommandIdentifier; -import net.tomatentum.marinara.util.LoggerUtil; public class CommandConverter { @@ -20,7 +20,7 @@ public class CommandConverter(spec); } - private Logger logger = LoggerUtil.getLogger(getClass()); + private Logger logger = LoggerFactory.getLogger(getClass()); private Spec spec; diff --git a/lib/src/main/java/net/tomatentum/marinara/wrapper/CommandRegisterer.java b/lib/src/main/java/net/tomatentum/marinara/wrapper/CommandRegisterer.java index 5cc8053..d178411 100644 --- a/lib/src/main/java/net/tomatentum/marinara/wrapper/CommandRegisterer.java +++ b/lib/src/main/java/net/tomatentum/marinara/wrapper/CommandRegisterer.java @@ -5,9 +5,9 @@ import java.util.Set; import java.util.stream.Collectors; import org.slf4j.Logger; +import org.slf4j.LoggerFactory; import net.tomatentum.marinara.interaction.commands.SlashCommandDefinition; -import net.tomatentum.marinara.util.LoggerUtil; import net.tomatentum.marinara.util.ObjectAggregator; public class CommandRegisterer { @@ -16,7 +16,7 @@ public class CommandRegisterer { return new CommandRegisterer(strategy, converter); } - private Logger logger = LoggerUtil.getLogger(getClass()); + private Logger logger = LoggerFactory.getLogger(getClass()); private Strategy strategy; private CommandConverter converter; @@ -29,13 +29,17 @@ public class CommandRegisterer { public void register(SlashCommandDefinition[] slashDefs) { Set> serverCommands = new ObjectAggregator>( def -> Arrays.stream(def.serverIds()).boxed().toList(), - (l, o) -> l.add(converter.convert(o)), + (l, o) -> { + logger.debug("Added {} for server ({}) registration.", o.rootIdentifier(), l.serverId()); + l.add(converter.convert(o)); + }, ServerCommandList::new) .aggregate(Arrays.asList(slashDefs)).stream() .collect(Collectors.toSet()); Set globalCommands = Arrays.stream(slashDefs) .filter(x -> x.serverIds().length <= 0) + .peek(c -> logger.debug("Added {} for global registration.", c.rootIdentifier())) .map(converter::convert) .collect(Collectors.toSet()); diff --git a/lib/src/main/java/net/tomatentum/marinara/wrapper/IdentifierProvider.java b/lib/src/main/java/net/tomatentum/marinara/wrapper/IdentifierProvider.java index d96d6f2..28d23fc 100644 --- a/lib/src/main/java/net/tomatentum/marinara/wrapper/IdentifierProvider.java +++ b/lib/src/main/java/net/tomatentum/marinara/wrapper/IdentifierProvider.java @@ -8,11 +8,11 @@ import java.util.List; import java.util.Map; import org.slf4j.Logger; +import org.slf4j.LoggerFactory; import io.leangen.geantyref.GenericTypeReflector; import net.tomatentum.cutin.util.ReflectionUtil; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; -import net.tomatentum.marinara.util.LoggerUtil; public class IdentifierProvider { @@ -20,8 +20,9 @@ public class IdentifierProvider { return new IdentifierProvider(Arrays.asList(converter)); } + private Logger logger = LoggerFactory.getLogger(getClass()); + private Map, Converter> converter; - private Logger logger = LoggerUtil.getLogger(getClass()); private IdentifierProvider(List> converter) { this.converter = new HashMap<>(); @@ -47,7 +48,9 @@ public class IdentifierProvider { @SuppressWarnings("unchecked") Converter conv = (Converter) converter.get(type); - return conv.convert(context); + InteractionIdentifier result = conv.convert(context); + logger.trace("Converted {} to {} using {}", context, result, conv); + return result; } @FunctionalInterface diff --git a/wrapper/discord4j/build.gradle.kts b/wrapper/discord4j/build.gradle.kts index aa43096..b89d503 100644 --- a/wrapper/discord4j/build.gradle.kts +++ b/wrapper/discord4j/build.gradle.kts @@ -17,6 +17,8 @@ dependencies { testImplementation(libs.discord4j) testRuntimeOnly("org.junit.platform:junit-platform-launcher") + testImplementation(libs.slf4j.simple) + implementation(libs.slf4j) implementation(libs.discord4j) { exclude(module="discord4j-voice") diff --git a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/Discord4JRegistererStrategy.java b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/Discord4JRegistererStrategy.java index fea6e5c..7f84f82 100644 --- a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/Discord4JRegistererStrategy.java +++ b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/Discord4JRegistererStrategy.java @@ -10,7 +10,7 @@ import net.tomatentum.marinara.wrapper.CommandRegisterer; import net.tomatentum.marinara.wrapper.ServerCommandList; public class Discord4JRegistererStrategy implements CommandRegisterer.Strategy { - + private ApplicationService appService; private long applicationId; diff --git a/wrapper/discord4j/src/test/resources/simplelogger.properties b/wrapper/discord4j/src/test/resources/simplelogger.properties new file mode 100644 index 0000000..a25b6c7 --- /dev/null +++ b/wrapper/discord4j/src/test/resources/simplelogger.properties @@ -0,0 +1,7 @@ +# SLF4J's SimpleLogger configuration file +# Simple implementation of Logger that sends all enabled log messages, for all defined loggers, to System.err. + +# Default logging detail level for all instances of SimpleLogger. +# Must be one of ("trace", "debug", "info", "warn", or "error"). +# If not specified, defaults to "info". +org.slf4j.simpleLogger.defaultLogLevel=trace \ No newline at end of file diff --git a/wrapper/javacord/build.gradle.kts b/wrapper/javacord/build.gradle.kts index 525933d..d5eb471 100644 --- a/wrapper/javacord/build.gradle.kts +++ b/wrapper/javacord/build.gradle.kts @@ -16,6 +16,8 @@ dependencies { testImplementation(libs.mockito) testRuntimeOnly("org.junit.platform:junit-platform-launcher") + testImplementation(libs.slf4j.simple) + implementation(libs.slf4j) implementation(libs.javacord) implementation(libs.geantyref) diff --git a/wrapper/javacord/src/test/resources/simplelogger.properties b/wrapper/javacord/src/test/resources/simplelogger.properties new file mode 100644 index 0000000..a25b6c7 --- /dev/null +++ b/wrapper/javacord/src/test/resources/simplelogger.properties @@ -0,0 +1,7 @@ +# SLF4J's SimpleLogger configuration file +# Simple implementation of Logger that sends all enabled log messages, for all defined loggers, to System.err. + +# Default logging detail level for all instances of SimpleLogger. +# Must be one of ("trace", "debug", "info", "warn", or "error"). +# If not specified, defaults to "info". +org.slf4j.simpleLogger.defaultLogLevel=trace \ No newline at end of file -- 2.47.2 From eea1597b15d157886a2e6ecdd2222d4391db7bf7 Mon Sep 17 00:00:00 2001 From: Tueem Date: Wed, 16 Apr 2025 00:00:25 +0200 Subject: [PATCH 17/18] fix(wrapper): also remove LoggerUtil in wrapper --- .../marinara/wrapper/discord4j/Discord4JWrapper.java | 4 ++-- .../tomatentum/marinara/test/discord4j/SlashCommandTest.java | 1 + .../tomatentum/marinara/wrapper/javacord/JavacordWrapper.java | 4 ++-- 3 files changed, 5 insertions(+), 4 deletions(-) diff --git a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/Discord4JWrapper.java b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/Discord4JWrapper.java index a4d1569..74f710f 100644 --- a/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/Discord4JWrapper.java +++ b/wrapper/discord4j/src/main/java/net/tomatentum/marinara/wrapper/discord4j/Discord4JWrapper.java @@ -4,6 +4,7 @@ import java.util.List; import java.util.function.UnaryOperator; import org.slf4j.Logger; +import org.slf4j.LoggerFactory; import discord4j.core.GatewayDiscordClient; import discord4j.core.event.domain.interaction.ChatInputAutoCompleteEvent; @@ -13,7 +14,6 @@ import discord4j.core.object.command.ApplicationCommandOption.Type; import discord4j.discordjson.json.ApplicationCommandOptionChoiceData; import discord4j.discordjson.json.ApplicationCommandRequest; -import net.tomatentum.marinara.util.LoggerUtil; import net.tomatentum.marinara.wrapper.CommandConverter; import net.tomatentum.marinara.wrapper.CommandRegisterer; import net.tomatentum.marinara.wrapper.ContextObjectProvider; @@ -37,7 +37,7 @@ public class Discord4JWrapper extends LibraryWrapper { private Discord4JContextObjectProvider contextObjectProvider; private CommandRegisterer commandRegisterer; - private Logger logger = LoggerUtil.getLogger(getClass()); + private Logger logger = LoggerFactory.getLogger(getClass()); public Discord4JWrapper(GatewayDiscordClient api) { this.contextObjectProvider = new Discord4JContextObjectProvider(); diff --git a/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/SlashCommandTest.java b/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/SlashCommandTest.java index 54ff156..17764f7 100644 --- a/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/SlashCommandTest.java +++ b/wrapper/discord4j/src/test/java/net/tomatentum/marinara/test/discord4j/SlashCommandTest.java @@ -21,6 +21,7 @@ import discord4j.core.object.command.ApplicationCommandOption.Type; import net.tomatentum.marinara.Marinara; import net.tomatentum.marinara.wrapper.LibraryWrapper; import net.tomatentum.marinara.wrapper.discord4j.Discord4JWrapper; + @TestInstance(Lifecycle.PER_CLASS) class SlashCommandTest { diff --git a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/JavacordWrapper.java b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/JavacordWrapper.java index 0bf1718..62a9cf1 100644 --- a/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/JavacordWrapper.java +++ b/wrapper/javacord/src/main/java/net/tomatentum/marinara/wrapper/javacord/JavacordWrapper.java @@ -7,12 +7,12 @@ import org.javacord.api.interaction.AutocompleteInteraction; import org.javacord.api.interaction.SlashCommandBuilder; import org.javacord.api.interaction.SlashCommandOptionChoice; import org.slf4j.Logger; +import org.slf4j.LoggerFactory; import net.tomatentum.marinara.wrapper.CommandConverter; import net.tomatentum.marinara.wrapper.CommandRegisterer; import net.tomatentum.marinara.wrapper.ContextObjectProvider; import net.tomatentum.marinara.wrapper.IdentifierProvider; -import net.tomatentum.marinara.util.LoggerUtil; import net.tomatentum.marinara.wrapper.LibraryWrapper; import net.tomatentum.marinara.wrapper.javacord.identifierconverter.AutocompleteIdentifierConverter; import net.tomatentum.marinara.wrapper.javacord.identifierconverter.ButtonIdentifierConverter; @@ -23,7 +23,7 @@ public class JavacordWrapper extends LibraryWrapper { private JavacordContextObjectProvider contextObjectProvider; private CommandRegisterer commandRegisterer; - private Logger logger = LoggerUtil.getLogger(getClass()); + private Logger logger = LoggerFactory.getLogger(getClass()); public JavacordWrapper(DiscordApi api) { this.contextObjectProvider = new JavacordContextObjectProvider(); -- 2.47.2 From 42a675dc967df727df24fa542fbd2c8f411b1c9a Mon Sep 17 00:00:00 2001 From: Tueem Date: Wed, 16 Apr 2025 00:00:47 +0200 Subject: [PATCH 18/18] feat(method): implement MethodParser rework --- gradle/libs.versions.toml | 4 +- .../checks/InteractionCheckMethod.java | 32 ++++++++----- .../methods/ButtonInteractionMethod.java | 41 ++++++++++------ .../AutoCompleteInteractionMethod.java | 45 +++++++++++------- .../methods/InteractionMethod.java | 12 ++--- .../SlashCommandInteractionMethod.java | 47 ++++++++++++------- .../marinara/parser/AutocompleteParser.java | 18 ++----- .../marinara/parser/ButtonParser.java | 15 ++---- .../parser/InteractionCheckClassParser.java | 22 ++++----- .../parser/InteractionCheckParser.java | 20 ++++---- .../marinara/parser/SlashCommandParser.java | 20 +++----- 11 files changed, 147 insertions(+), 129 deletions(-) diff --git a/gradle/libs.versions.toml b/gradle/libs.versions.toml index 692ea9c..4268ec0 100644 --- a/gradle/libs.versions.toml +++ b/gradle/libs.versions.toml @@ -8,7 +8,7 @@ javacord = "3.8.0" discord4j = "3.2.7" geantyref = "2.0.0" mockito = "5.15.2" -cutin = "0.1.1-cad019e" +cutin = "0.2.0" [libraries] junit-jupiter = { module = "org.junit.jupiter:junit-jupiter", version.ref = "junit-jupiter" } @@ -18,4 +18,4 @@ javacord = { module = "org.javacord:javacord", version.ref = "javacord"} discord4j = { module = "com.discord4j:discord4j-core", version.ref = "discord4j"} geantyref = { module = "io.leangen.geantyref:geantyref", version.ref = "geantyref"} mockito = {module = "org.mockito:mockito-core", version.ref = "mockito"} -cutin = {module = "net.tomatentum.cutin:lib-dev", version.ref = "cutin"} +cutin = {module = "net.tomatentum.cutin:lib", version.ref = "cutin"} diff --git a/lib/src/main/java/net/tomatentum/marinara/checks/InteractionCheckMethod.java b/lib/src/main/java/net/tomatentum/marinara/checks/InteractionCheckMethod.java index 0774f26..56ce052 100644 --- a/lib/src/main/java/net/tomatentum/marinara/checks/InteractionCheckMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/checks/InteractionCheckMethod.java @@ -1,12 +1,12 @@ package net.tomatentum.marinara.checks; -import java.util.List; import java.util.Optional; +import java.util.Set; import net.tomatentum.cutin.MethodParser; +import net.tomatentum.cutin.ReflectedMethodFactory.ParserResults; import net.tomatentum.cutin.container.MethodContainer; import net.tomatentum.cutin.method.BestCandidateMethod; -import net.tomatentum.cutin.method.ReflectedMethod; import net.tomatentum.marinara.checks.CheckMethodIdentifier.CheckMethodType; import net.tomatentum.marinara.parser.InteractionCheckClassParser; @@ -14,8 +14,13 @@ public class InteractionCheckMethod extends BestCandidateMethod method, List parsers) { + public void addParser(Set parsers) { parsers.add( - new InteractionCheckClassParser((Class>) method.containingObject().getClass(), - a -> ((InteractionCheckMethod) method).identifier = new CheckMethodIdentifier(a, type)) + new InteractionCheckClassParser() ); } @Override - protected Optional> bcProduce(String methodName, - Object containingObject) { - if (!(containingObject instanceof InteractionCheck)) - return Optional.empty(); - return Optional.of(new InteractionCheckMethod(methodName, containingObject)); + protected Optional> bcProduce( + String methodName, + Object containingObject, + ParserResults parserResults + ) { + + CheckMethodIdentifier identifier = new CheckMethodIdentifier(parserResults.get(InteractionCheckClassParser.class), type); + if (identifier.annotationType() == null) + return null; + return Optional.of(new InteractionCheckMethod(methodName, containingObject, identifier)); } } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/components/methods/ButtonInteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/components/methods/ButtonInteractionMethod.java index ffb4c0d..164d666 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/components/methods/ButtonInteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/components/methods/ButtonInteractionMethod.java @@ -3,18 +3,21 @@ package net.tomatentum.marinara.interaction.components.methods; import java.lang.reflect.Method; import java.util.List; import java.util.Optional; +import java.util.Set; import net.tomatentum.cutin.MethodParser; +import net.tomatentum.cutin.ReflectedMethodFactory.ParserResults; import net.tomatentum.cutin.container.MethodContainer; import net.tomatentum.cutin.method.ReflectedMethod; +import net.tomatentum.marinara.checks.AppliedCheck; import net.tomatentum.marinara.checks.CheckExecutionContext; import net.tomatentum.marinara.checks.CheckMethodIdentifier; import net.tomatentum.marinara.interaction.InteractionHandler; import net.tomatentum.marinara.interaction.InteractionType; -import net.tomatentum.marinara.interaction.annotation.Button; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; import net.tomatentum.marinara.interaction.methods.InteractionMethod; import net.tomatentum.marinara.parser.ButtonParser; +import net.tomatentum.marinara.parser.InteractionCheckParser; import net.tomatentum.marinara.wrapper.ContextObjectProvider; public class ButtonInteractionMethod extends InteractionMethod { @@ -22,8 +25,15 @@ public class ButtonInteractionMethod extends InteractionMethod { private String customId; private ContextObjectProvider cop; - private ButtonInteractionMethod(Method method, InteractionHandler handler, ContextObjectProvider cop) { - super(method, handler); + private ButtonInteractionMethod( + Method method, + InteractionHandler handler, + List appliedChecks, + String customId, + ContextObjectProvider cop + ) { + super(method, handler, appliedChecks); + this.customId = customId; this.cop = cop; } @@ -56,22 +66,25 @@ public class ButtonInteractionMethod extends InteractionMethod { } @Override - public Optional> produce(Method method, Object containingObject) { - ButtonInteractionMethod rMethod = null; - if (method.isAnnotationPresent(Button.class) && - (containingObject instanceof InteractionHandler iHandler) - ) - rMethod = new ButtonInteractionMethod(method, iHandler, this.cop); - - return Optional.ofNullable(rMethod); + public Optional> produce(Method method, Object containingObject, ParserResults parserResults) { + if (!(containingObject instanceof InteractionHandler)) return Optional.empty(); + String customId = parserResults.get(ButtonParser.class); + if (customId == null) return Optional.empty(); + return Optional.of(new ButtonInteractionMethod( + method, + (InteractionHandler) containingObject, + parserResults.get(InteractionCheckParser.class), + customId, + this.cop + )); } @Override - public void addParser(ReflectedMethod method, List parser) { - super.addParser(method, parser); + public void addParser(Set parser) { + super.addParser(parser); parser.add( - new ButtonParser(method.method(), x -> ((ButtonInteractionMethod) method).customId = x) + new ButtonParser() ); } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java index a00c008..fb1d4d5 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/AutoCompleteInteractionMethod.java @@ -3,19 +3,20 @@ package net.tomatentum.marinara.interaction.methods; import java.lang.reflect.Method; import java.util.List; import java.util.Optional; +import java.util.Set; import net.tomatentum.cutin.MethodParser; +import net.tomatentum.cutin.ReflectedMethodFactory.ParserResults; import net.tomatentum.cutin.container.MethodContainer; import net.tomatentum.cutin.method.ReflectedMethod; +import net.tomatentum.marinara.checks.AppliedCheck; import net.tomatentum.marinara.checks.CheckExecutionContext; import net.tomatentum.marinara.checks.CheckMethodIdentifier; import net.tomatentum.marinara.interaction.InteractionHandler; import net.tomatentum.marinara.interaction.InteractionType; -import net.tomatentum.marinara.interaction.annotation.AutoComplete; -import net.tomatentum.marinara.interaction.commands.annotation.SlashCommand; -import net.tomatentum.marinara.interaction.commands.annotation.SubCommand; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; import net.tomatentum.marinara.parser.AutocompleteParser; +import net.tomatentum.marinara.parser.InteractionCheckParser; import net.tomatentum.marinara.wrapper.ContextObjectProvider; public class AutoCompleteInteractionMethod extends InteractionMethod { @@ -23,11 +24,15 @@ public class AutoCompleteInteractionMethod extends InteractionMethod { private String autocompleteRef; private ContextObjectProvider cop; - private AutoCompleteInteractionMethod(Method method, - InteractionHandler handler, - ContextObjectProvider cop + private AutoCompleteInteractionMethod( + Method method, + InteractionHandler handler, + List appliedChecks, + String autocompleteRef, + ContextObjectProvider cop ) { - super(method, handler); + super(method, handler, appliedChecks); + this.autocompleteRef = autocompleteRef; this.cop = cop; } @@ -64,23 +69,27 @@ public class AutoCompleteInteractionMethod extends InteractionMethod { } @Override - public Optional> produce(Method method, Object containingObject) { - AutoCompleteInteractionMethod rMethod = null; - if ((containingObject instanceof InteractionHandler iHandler) && - method.isAnnotationPresent(AutoComplete.class) && - !(method.isAnnotationPresent(SlashCommand.class) || - method.isAnnotationPresent(SubCommand.class))) - rMethod = new AutoCompleteInteractionMethod(method, iHandler, cop); + public Optional> produce(Method method, Object containingObject, ParserResults parserResults) { + if (!(containingObject instanceof InteractionHandler)) return Optional.empty(); + String[] autocompletes = parserResults.get(AutocompleteParser.class); + if (autocompletes.length <= 0) return Optional.empty(); + + return Optional.of(new AutoCompleteInteractionMethod( + method, + (InteractionHandler) containingObject, + parserResults.get(InteractionCheckParser.class), + autocompletes[0], + cop + )); - return Optional.ofNullable(rMethod); } @Override - public void addParser(ReflectedMethod method, List parser) { - super.addParser(method, parser); + public void addParser(Set parser) { + super.addParser(parser); parser.add( - new AutocompleteParser(method.method(), x -> ((AutoCompleteInteractionMethod) method).autocompleteRef = x[0]) + new AutocompleteParser() ); } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/InteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/InteractionMethod.java index 7dd316f..12fbb53 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/InteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/InteractionMethod.java @@ -1,8 +1,8 @@ package net.tomatentum.marinara.interaction.methods; import java.lang.reflect.Method; -import java.util.ArrayList; import java.util.List; +import java.util.Set; import net.tomatentum.cutin.MethodParser; import net.tomatentum.cutin.ReflectedMethodFactory; @@ -21,10 +21,11 @@ public abstract class InteractionMethod extends ReflectedMethod appliedChecks ) { super(method, handler); - this.appliedChecks = new ArrayList<>(); + this.appliedChecks = appliedChecks; } @Override @@ -60,10 +61,9 @@ public abstract class InteractionMethod extends ReflectedMethod method, List parser) { - InteractionMethod imethod = (InteractionMethod) method; + public void addParser(Set parser) { parser.add( - new InteractionCheckParser(method.method(), imethod.appliedChecks::add, this.checkContainer) + new InteractionCheckParser(this.checkContainer) ); } diff --git a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java index 8afa595..87fe208 100644 --- a/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java +++ b/lib/src/main/java/net/tomatentum/marinara/interaction/methods/SlashCommandInteractionMethod.java @@ -3,27 +3,36 @@ package net.tomatentum.marinara.interaction.methods; import java.lang.reflect.Method; import java.util.List; import java.util.Optional; +import java.util.Set; import net.tomatentum.cutin.MethodParser; +import net.tomatentum.cutin.ReflectedMethodFactory.ParserResults; import net.tomatentum.cutin.container.MethodContainer; import net.tomatentum.cutin.method.ReflectedMethod; +import net.tomatentum.marinara.checks.AppliedCheck; import net.tomatentum.marinara.checks.CheckExecutionContext; import net.tomatentum.marinara.checks.CheckMethodIdentifier; import net.tomatentum.marinara.interaction.InteractionHandler; -import net.tomatentum.marinara.interaction.commands.annotation.SlashCommand; -import net.tomatentum.marinara.interaction.commands.annotation.SubCommand; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; import net.tomatentum.marinara.interaction.ident.SlashCommandIdentifier; +import net.tomatentum.marinara.parser.InteractionCheckParser; import net.tomatentum.marinara.parser.SlashCommandParser; import net.tomatentum.marinara.wrapper.ContextObjectProvider; public class SlashCommandInteractionMethod extends InteractionMethod { - private SlashCommandIdentifier interactionIdentifier; + private SlashCommandIdentifier identifier; private ContextObjectProvider cop; - private SlashCommandInteractionMethod(Method method, InteractionHandler handler, ContextObjectProvider cop) { - super(method, handler); + private SlashCommandInteractionMethod( + Method method, + InteractionHandler handler, + List appliedChecks, + SlashCommandIdentifier identifier, + ContextObjectProvider cop + ) { + super(method, handler, appliedChecks); + this.identifier = identifier; this.cop = cop; } @@ -31,14 +40,14 @@ public class SlashCommandInteractionMethod extends InteractionMethod { public Object getParameter(Object context, int index) { Object superResult = super.getParameter(context, index); if (superResult == null) - return this.cop.convertCommandOption(context, interactionIdentifier.options()[index-1].name()); + return this.cop.convertCommandOption(context, identifier.options()[index-1].name()); else return superResult; } @Override public InteractionIdentifier identifier() { - return interactionIdentifier; + return identifier; } public static class Factory extends InteractionMethod.Factory { @@ -51,21 +60,25 @@ public class SlashCommandInteractionMethod extends InteractionMethod { } @Override - public Optional> produce(Method method, Object containingObject) { - SlashCommandInteractionMethod rMethod = null; - if ((containingObject instanceof InteractionHandler iHandler) && - (method.isAnnotationPresent(SlashCommand.class) || - method.isAnnotationPresent(SubCommand.class))) - rMethod = new SlashCommandInteractionMethod(method, iHandler, cop); - return Optional.ofNullable(rMethod); + public Optional> produce(Method method, Object containingObject, ParserResults parserResults) { + if (!(containingObject instanceof InteractionHandler)) return Optional.empty(); + SlashCommandIdentifier ident = parserResults.get(SlashCommandParser.class); + if (ident == null) return Optional.empty(); + return Optional.of(new SlashCommandInteractionMethod( + method, + (InteractionHandler) containingObject, + parserResults.get(InteractionCheckParser.class), + ident, + cop + )); } @Override - public void addParser(ReflectedMethod method, List parser) { - super.addParser(method, parser); + public void addParser(Set parser) { + super.addParser(parser); parser.add( - new SlashCommandParser(method.method(), x -> ((SlashCommandInteractionMethod) method).interactionIdentifier = x) + new SlashCommandParser() ); } diff --git a/lib/src/main/java/net/tomatentum/marinara/parser/AutocompleteParser.java b/lib/src/main/java/net/tomatentum/marinara/parser/AutocompleteParser.java index 96a0eda..c325b6a 100644 --- a/lib/src/main/java/net/tomatentum/marinara/parser/AutocompleteParser.java +++ b/lib/src/main/java/net/tomatentum/marinara/parser/AutocompleteParser.java @@ -2,7 +2,6 @@ package net.tomatentum.marinara.parser; import java.lang.reflect.Method; import java.util.Arrays; -import java.util.function.Consumer; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -15,21 +14,14 @@ public class AutocompleteParser implements MethodParser { private Logger logger = LoggerFactory.getLogger(getClass()); - private Method method; - private Consumer consumer; - - public AutocompleteParser(Method method, Consumer consumer) { - this.method = method; - this.consumer = consumer; - } - @Override - public void parse() { - String[] autocompletes = Arrays.stream(this.method.getAnnotationsByType(AutoComplete.class)) + public Object parse(Method method, Object containingObject) { + String[] autoCompletes = Arrays.stream(method.getAnnotationsByType(AutoComplete.class)) .map(AutoComplete::value) .toArray(String[]::new); - logger.trace("Parsed AutoComplete annotation {} for method {}", autocompletes, ReflectionUtil.getFullMethodName(method)); - this.consumer.accept(autocompletes); + if (autoCompletes.length > 0) + logger.trace("Parsed AutoComplete annotations {} for method {}", autoCompletes, ReflectionUtil.getFullMethodName(method)); + return autoCompletes; } } diff --git a/lib/src/main/java/net/tomatentum/marinara/parser/ButtonParser.java b/lib/src/main/java/net/tomatentum/marinara/parser/ButtonParser.java index 7af03fc..98f9aaa 100644 --- a/lib/src/main/java/net/tomatentum/marinara/parser/ButtonParser.java +++ b/lib/src/main/java/net/tomatentum/marinara/parser/ButtonParser.java @@ -1,7 +1,6 @@ package net.tomatentum.marinara.parser; import java.lang.reflect.Method; -import java.util.function.Consumer; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -12,21 +11,17 @@ import net.tomatentum.marinara.interaction.annotation.Button; public class ButtonParser implements MethodParser { - private Method method; - private Consumer consumer; - private Logger logger = LoggerFactory.getLogger(getClass()); - public ButtonParser(Method method, Consumer consumer) { - this.method = method; - this.consumer = consumer; + public ButtonParser() { } @Override - public void parse() { - Button button = this.method.getAnnotation(Button.class); + public Object parse(Method method, Object containingObject) { + Button button = method.getAnnotation(Button.class); + if (button == null) return null; logger.trace("Parsed Button annotation {} for method {}", button, ReflectionUtil.getFullMethodName(method)); - this.consumer.accept(button.value()); + return button.value(); } } diff --git a/lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckClassParser.java b/lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckClassParser.java index 26da135..db0457c 100644 --- a/lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckClassParser.java +++ b/lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckClassParser.java @@ -1,8 +1,8 @@ package net.tomatentum.marinara.parser; +import java.lang.reflect.Method; import java.lang.reflect.ParameterizedType; import java.lang.reflect.Type; -import java.util.function.Consumer; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -15,20 +15,14 @@ public class InteractionCheckClassParser implements MethodParser { private Logger logger = LoggerFactory.getLogger(getClass()); - private Class> interactionCheckType; - private Consumer annotationTypeConsumer; - - public InteractionCheckClassParser(Class> interactionCheckType, Consumer annotationTypeConsumer) { - this.interactionCheckType = interactionCheckType; - this.annotationTypeConsumer = annotationTypeConsumer; - } - @Override - public void parse() { - ParameterizedType type = (ParameterizedType) GenericTypeReflector.getExactSuperType(interactionCheckType, InteractionCheck.class); - Type typeParam = type.getActualTypeArguments()[0]; - logger.trace("Parsed InteractionCheck Annotation {}", typeParam); - this.annotationTypeConsumer.accept(typeParam); + public Object parse(Method method, Object containingObject) { + ParameterizedType type = (ParameterizedType) GenericTypeReflector.getExactSuperType(containingObject.getClass(), InteractionCheck.class); + if (type == null) return null; + Type typeParam = type.getActualTypeArguments().length == 1 ? type.getActualTypeArguments()[0] : null; + if (typeParam != null) + logger.trace("Parsed InteractionCheck Annotation {}", typeParam); + return typeParam; } } diff --git a/lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckParser.java b/lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckParser.java index ebdcd48..7faa568 100644 --- a/lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckParser.java +++ b/lib/src/main/java/net/tomatentum/marinara/parser/InteractionCheckParser.java @@ -3,7 +3,7 @@ package net.tomatentum.marinara.parser; import java.lang.annotation.Annotation; import java.lang.reflect.Method; import java.util.Arrays; -import java.util.function.Consumer; +import java.util.Objects; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -19,31 +19,31 @@ import net.tomatentum.marinara.checks.CheckMethodIdentifier.CheckMethodType; public class InteractionCheckParser implements MethodParser { private MethodContainer checkContainer; - private Method method; - private Consumer consumer; private Logger logger = LoggerFactory.getLogger(getClass()); - public InteractionCheckParser(Method method, Consumer consumer, MethodContainer checkContainer) { + public InteractionCheckParser(MethodContainer checkContainer) { this.checkContainer = checkContainer; - this.method = method; - this.consumer = consumer; } @Override - public void parse() { + public Object parse(Method method, Object containingObject) { Annotation[] annotations = method.getAnnotations(); - Arrays.stream(annotations).forEach(this::convertAnnotation); + return Arrays.stream(annotations) + .map(a -> convertAnnotation(a, method)) + .filter(Objects::nonNull) + .toList(); } - private void convertAnnotation(Annotation annotation) { + private AppliedCheck convertAnnotation(Annotation annotation, Method method) { var preExec = this.checkContainer.findFirstFor(new CheckMethodIdentifier(annotation.annotationType(), CheckMethodType.PRE)); var postExec = this.checkContainer.findFirstFor(new CheckMethodIdentifier(annotation.annotationType(), CheckMethodType.POST)); if (preExec.isPresent() && postExec.isPresent()) { AppliedCheck appliedCheck = new AppliedCheck(annotation, preExec.get(), postExec.get()); logger.trace("Parsed InteractionCheck {} for annotation {} for method {}", preExec.get().containingObject(), annotation, ReflectionUtil.getFullMethodName(method)); - consumer.accept(appliedCheck); + return appliedCheck; } + return null; } } diff --git a/lib/src/main/java/net/tomatentum/marinara/parser/SlashCommandParser.java b/lib/src/main/java/net/tomatentum/marinara/parser/SlashCommandParser.java index 2f1bab5..ad75258 100644 --- a/lib/src/main/java/net/tomatentum/marinara/parser/SlashCommandParser.java +++ b/lib/src/main/java/net/tomatentum/marinara/parser/SlashCommandParser.java @@ -1,7 +1,6 @@ package net.tomatentum.marinara.parser; import java.lang.reflect.Method; -import java.util.function.Consumer; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -13,22 +12,17 @@ import net.tomatentum.marinara.interaction.commands.annotation.SlashCommand; import net.tomatentum.marinara.interaction.commands.annotation.SubCommand; import net.tomatentum.marinara.interaction.commands.annotation.SubCommandGroup; import net.tomatentum.marinara.interaction.ident.InteractionIdentifier; -import net.tomatentum.marinara.interaction.ident.SlashCommandIdentifier; public class SlashCommandParser implements MethodParser { - private Method method; - private Consumer consumer; - private Logger logger = LoggerFactory.getLogger(getClass()); - public SlashCommandParser(Method method, Consumer consumer) { - this.method = method; - this.consumer = consumer; + public SlashCommandParser() { } @Override - public void parse() { + public Object parse(Method method, Object containingObject) { + if (!method.isAnnotationPresent(SlashCommand.class) && !method.isAnnotationPresent(SubCommand.class)) return null; this.checkValidCommandMethod(method); SlashCommand cmd = ReflectionUtil.getAnnotation(method, SlashCommand.class); @@ -59,21 +53,21 @@ public class SlashCommandParser implements MethodParser { } logger.trace("Parsed using SlashCommandParser for method {} with the result: {}", ReflectionUtil.getFullMethodName(method), lastIdentifier); - consumer.accept((SlashCommandIdentifier) lastIdentifier); + return lastIdentifier; } private void checkValidCommandMethod(Method method) { if (method.isAnnotationPresent(SlashCommand.class) && method.getDeclaringClass().isAnnotationPresent(SlashCommand.class)) { - throw new RuntimeException(method.getName() + ": Can't have ApplicationCommand Annotation on Class and Method"); + throw new RuntimeException(method.getName() + ": Can't have SlashCommand Annotation on Class and Method"); } if (!ReflectionUtil.isAnnotationPresent(method, SlashCommand.class)) - throw new RuntimeException(method.getName() + ": Missing ApplicationCommand Annotation on either Class or Method"); + throw new RuntimeException(method.getName() + ": Missing SlashCommand Annotation on either Class or Method"); if ((method.isAnnotationPresent(SubCommand.class) && !ReflectionUtil.isAnnotationPresent(method, SlashCommand.class))) { - throw new RuntimeException(method.getName() + ": Missing ApplicationCommand Annotation on either Method or Class"); + throw new RuntimeException(method.getName() + ": Missing SlashCommand Annotation on either Method or Class"); } } -- 2.47.2