From e161768e8b47f4d0a5fdf4d9ce86f2d669456d5e Mon Sep 17 00:00:00 2001 From: Rollczi Date: Thu, 21 Sep 2023 08:48:52 +0200 Subject: [PATCH] Refactor argument api and create flow. --- .../rollczi/example/bukkit/ExamplePlugin.java | 6 +- .../example/bukkit/command/BanCommand.java | 2 +- .../bukkit/command/ConvertCommand.java | 2 +- .../bukkit/command/GameModeCommand.java | 2 +- .../bukkit/command/TeleportCommand.java | 2 +- .../example/velocity/ExamplePlugin.java | 3 +- .../example/velocity/command/SendCommand.java | 2 +- .../litecommands/benchmark/LiteBenchmark.java | 2 +- .../annotation/AnnotationHolder.java | 0 .../annotation/AnnotationHolderImpl.java | 0 .../annotation}/ArgumentFactory.java | 4 +- .../ArgumentRequirementFactory.java | 20 +++ .../annotation/ContextRequirementFactory.java | 14 ++ .../annotation/ContextRequirementImpl.java | 42 +++++ .../annotation/RequirementFactory.java | 11 ++ .../annotation/RequirementProcessor.java | 29 +++ .../processor/AnnotationInvoker.java | 5 + .../processor/AnnotationProcessor.java | 12 +- .../processor/AnnotationProcessorService.java | 59 +++++++ .../annotations/InstanceSourceProcessor.java | 29 +-- .../annotations/LiteAnnotationCommands.java | 25 +-- .../annotations/MethodCommandExecutor.java | 13 +- .../annotations/MethodDefinition.java | 72 +++++--- .../annotations/MethodInvoker.java | 73 ++++++-- .../annotations/ParameterInvoker.java | 41 +++-- .../rollczi/litecommands/argument/Arg.java | 14 ++ .../argument/ArgArgumentFactory.java | 5 +- .../dev/rollczi/litecommands/async/Async.java | 0 .../async/AsyncAnnotationResolver.java | 1 - .../rollczi/litecommands/command/Command.java | 4 +- .../command/CommandAnnotationProcessor.java | 2 + .../litecommands/command/RootCommand.java | 0 .../RootCommandAnnotationProcessor.java | 0 .../rollczi/litecommands/context/Context.java | 0 .../litecommands/description/Description.java | 0 .../DescriptionAnnotationResolver.java | 0 .../edit}/AnnotationEditorService.java | 3 +- .../dev/rollczi/litecommands/edit}/Edit.java | 2 +- .../litecommands/execute}/Execute.java | 2 +- .../execute}/ExecuteAnnotationResolver.java | 10 +- .../dev/rollczi/litecommands/flag/Flag.java | 14 ++ .../flag/FlagArgumentFactory.java | 5 +- .../rollczi/litecommands/inject/Inject.java | 0 .../rollczi/litecommands/inject/Injector.java | 0 .../dev/rollczi/litecommands/join/Join.java | 19 ++ .../join/JoinArgumentFactory.java | 5 +- .../rollczi/litecommands/meta/MarkMeta.java | 17 ++ .../meta/MarkMetaAnnotationResolver.java | 14 ++ .../litecommands/permission/Permission.java | 17 ++ .../PermissionAnnotationResolver.java | 18 ++ .../litecommands/permission/Permissions.java | 19 ++ .../PermissionsAnnotationResolver.java | 22 +++ .../programmatic/LiteCommand.java | 165 +++++++++-------- .../LiteCommandsProgrammatic.java | 22 +-- .../ProgrammaticCommandExecutor.java | 63 ------- .../ProgrammaticExecutorStructureInvoker.java | 40 ----- .../ProgrammaticRequirementInvoker.java | 38 ---- .../ProgrammaticSourceProcessor.java | 39 ---- .../ProgrammaticStructureInvoker.java | 48 ----- .../litecommands/validator/Validate.java | 15 ++ .../validator/ValidateAnnotationResolver.java | 17 ++ .../annotations/ExampleUnitTest.java | 2 +- .../ArgumentResolverAnnotationTest.java | 20 +-- .../argument/MultiArgumentsTest.java | 2 +- .../argument/SimpleArgumentTest.java | 58 ------ .../argument/flag/FlagArgumentTest.java | 2 +- .../argument/join/JoinArgumentTest.java | 2 +- .../annotations/async/AsyncCommandTest.java | 50 +++--- .../annotations/dsl/ProgrammaticApiTest.java | 2 +- .../editor/AnnotationEditorServiceTest.java | 6 +- .../exception/ExceptionHandleTest.java | 2 +- .../invalid/InvalidHandlerTest.java | 2 +- .../ChildCommandPermissionHandleTest.java | 2 +- ...ultMissingPermissionResultHandlerTest.java | 2 +- .../MissingPermissionResultHandlerTest.java | 2 +- .../permission/PermissionAnnotationTest.java | 2 +- .../annotations/route/RootCommandTest.java | 2 +- .../annotations/schematic/SchematicTest.java | 2 +- .../validator/CustomValidatorTest.java | 2 +- .../wrapper/OptionalWrapperTest.java | 2 +- .../litecommands/LiteCommandsFactory.java | 45 +---- .../processor/AnnotationProcessorService.java | 25 --- .../annotation/processor/SourceProcessor.java | 9 - .../rollczi/litecommands/argument/Arg.java | 34 ---- .../litecommands/argument/Argument.java | 12 +- .../litecommands/argument/SimpleArgument.java | 34 ++-- ...solver.java => TypedArgumentResolver.java} | 4 +- .../resolver/std/StringArgumentResolver.java | 5 - .../builder/LiteCommandsBaseBuilder.java | 21 +-- .../builder/LiteCommandsBuilder.java | 3 - .../LiteCommandsInternalBuilderApi.java | 3 - .../builder/LiteCommandsProvider.java | 1 + .../command/CommandExecutorProvider.java | 9 + .../litecommands/command/CommandProvider.java | 8 + .../litecommands/command/CommandRoute.java | 2 +- .../command/builder/CommandBuilder.java | 6 +- .../command/builder/CommandBuilderBase.java | 18 +- .../builder/CommandBuilderExecutor.java | 71 -------- .../builder/CommandBuilderRootImpl.java | 6 +- .../executor/AbstractCommandExecutor.java | 20 ++- .../executor/CommandExecuteService.java | 77 ++++++-- .../command/executor/CommandExecutor.java | 13 +- .../executor/CommandExecutorBuilder.java | 97 ++++++++++ .../executor/CommandExecutorFactory.java | 2 +- .../command/executor}/LiteContext.java | 4 +- .../context/LegacyContextProvider.java | 1 + .../dev/rollczi/litecommands/flag/Flag.java | 38 ---- .../litecommands/flag/FlagArgument.java | 17 +- .../flag/FlagArgumentResolver.java | 9 +- .../dev/rollczi/litecommands/join/Join.java | 45 ----- .../litecommands/join/JoinArgument.java | 33 +++- .../join/JoinArgumentResolver.java | 13 +- .../rollczi/litecommands/meta/MarkMeta.java | 29 --- .../litecommands/meta/MetaListEditor.java | 7 + .../litecommands/permission/Permission.java | 52 ------ .../litecommands/permission/Permissions.java | 35 ---- .../requirement/ArgumentRequirement.java | 12 -- .../ArgumentRequirementFactory.java | 48 ----- .../requirement/ArgumentRequirementImpl.java | 80 --------- .../requirement/ContextRequirement.java | 14 +- .../ContextRequirementFactory.java | 28 --- .../requirement/ContextRequirementImpl.java | 42 ++--- .../litecommands/requirement/Requirement.java | 13 +- .../requirement/RequirementFactory.java | 11 -- .../RequirementFactoryRegistry.java | 29 --- .../requirement/RequirementMatch.java | 2 +- .../requirement/RequirementProcessor.java | 37 ---- .../requirement/RequirementsResult.java | 10 +- .../schematic/SchematicGenerator.java | 5 +- .../SchematicGeneratorSimpleImpl.java | 17 +- .../suggestion/SuggestionService.java | 20 +-- .../litecommands/validator/Validate.java | 31 ---- .../MissingPermissionValidatorTest.java | 12 +- .../MethodCommandExecutorFactoryTest.java | 52 ------ .../schematic/SchematicGeneratorTest.java | 4 +- .../jda/JDACommandTranslator.java | 18 +- .../rollczi/litecommands/jda/JDAPlatform.java | 14 +- .../litecommands/jda/LiteJDAFactory.java | 46 ++--- .../litecommands/jda/LiteJDASettings.java | 12 ++ .../jda/JDACommandTranslatorTest.java | 4 +- .../minestom/MinestomIntegrationTest.java | 2 +- .../litecommands/unit/TestExecutor.java | 167 +----------------- 142 files changed, 1138 insertions(+), 1674 deletions(-) rename {litecommands-core => litecommands-core-annotations}/src/dev/rollczi/litecommands/annotation/AnnotationHolder.java (100%) rename {litecommands-core => litecommands-core-annotations}/src/dev/rollczi/litecommands/annotation/AnnotationHolderImpl.java (100%) rename {litecommands-core/src/dev/rollczi/litecommands/argument => litecommands-core-annotations/src/dev/rollczi/litecommands/annotation}/ArgumentFactory.java (61%) create mode 100644 litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/ArgumentRequirementFactory.java create mode 100644 litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/ContextRequirementFactory.java create mode 100644 litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/ContextRequirementImpl.java create mode 100644 litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/RequirementFactory.java create mode 100644 litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/RequirementProcessor.java rename {litecommands-core => litecommands-core-annotations}/src/dev/rollczi/litecommands/annotation/processor/AnnotationInvoker.java (83%) rename {litecommands-core => litecommands-core-annotations}/src/dev/rollczi/litecommands/annotation/processor/AnnotationProcessor.java (59%) create mode 100644 litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/processor/AnnotationProcessorService.java create mode 100644 litecommands-core-annotations/src/dev/rollczi/litecommands/argument/Arg.java rename {litecommands-core => litecommands-core-annotations}/src/dev/rollczi/litecommands/argument/ArgArgumentFactory.java (77%) rename {litecommands-core => litecommands-core-annotations}/src/dev/rollczi/litecommands/async/Async.java (100%) rename {litecommands-core => litecommands-core-annotations}/src/dev/rollczi/litecommands/async/AsyncAnnotationResolver.java (99%) rename {litecommands-core => litecommands-core-annotations}/src/dev/rollczi/litecommands/command/Command.java (94%) rename {litecommands-core => litecommands-core-annotations}/src/dev/rollczi/litecommands/command/CommandAnnotationProcessor.java (94%) rename {litecommands-core => litecommands-core-annotations}/src/dev/rollczi/litecommands/command/RootCommand.java (100%) rename {litecommands-core => litecommands-core-annotations}/src/dev/rollczi/litecommands/command/RootCommandAnnotationProcessor.java (100%) rename {litecommands-core => litecommands-core-annotations}/src/dev/rollczi/litecommands/context/Context.java (100%) rename {litecommands-core => litecommands-core-annotations}/src/dev/rollczi/litecommands/description/Description.java (100%) rename {litecommands-core => litecommands-core-annotations}/src/dev/rollczi/litecommands/description/DescriptionAnnotationResolver.java (100%) rename {litecommands-core/src/dev/rollczi/litecommands/editor => litecommands-core-annotations/src/dev/rollczi/litecommands/edit}/AnnotationEditorService.java (90%) rename {litecommands-core/src/dev/rollczi/litecommands/editor => litecommands-core-annotations/src/dev/rollczi/litecommands/edit}/Edit.java (87%) rename {litecommands-core/src/dev/rollczi/litecommands/command/executor => litecommands-core-annotations/src/dev/rollczi/litecommands/execute}/Execute.java (96%) rename {litecommands-core/src/dev/rollczi/litecommands/command/executor => litecommands-core-annotations/src/dev/rollczi/litecommands/execute}/ExecuteAnnotationResolver.java (80%) create mode 100644 litecommands-core-annotations/src/dev/rollczi/litecommands/flag/Flag.java rename {litecommands-core => litecommands-core-annotations}/src/dev/rollczi/litecommands/flag/FlagArgumentFactory.java (80%) rename {litecommands-core => litecommands-core-annotations}/src/dev/rollczi/litecommands/inject/Inject.java (100%) rename {litecommands-core => litecommands-core-annotations}/src/dev/rollczi/litecommands/inject/Injector.java (100%) create mode 100644 litecommands-core-annotations/src/dev/rollczi/litecommands/join/Join.java rename {litecommands-core => litecommands-core-annotations}/src/dev/rollczi/litecommands/join/JoinArgumentFactory.java (57%) create mode 100644 litecommands-core-annotations/src/dev/rollczi/litecommands/meta/MarkMeta.java create mode 100644 litecommands-core-annotations/src/dev/rollczi/litecommands/meta/MarkMetaAnnotationResolver.java create mode 100644 litecommands-core-annotations/src/dev/rollczi/litecommands/permission/Permission.java create mode 100644 litecommands-core-annotations/src/dev/rollczi/litecommands/permission/PermissionAnnotationResolver.java create mode 100644 litecommands-core-annotations/src/dev/rollczi/litecommands/permission/Permissions.java create mode 100644 litecommands-core-annotations/src/dev/rollczi/litecommands/permission/PermissionsAnnotationResolver.java delete mode 100644 litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/ProgrammaticCommandExecutor.java delete mode 100644 litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/ProgrammaticExecutorStructureInvoker.java delete mode 100644 litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/ProgrammaticRequirementInvoker.java delete mode 100644 litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/ProgrammaticSourceProcessor.java delete mode 100644 litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/ProgrammaticStructureInvoker.java create mode 100644 litecommands-core-annotations/src/dev/rollczi/litecommands/validator/Validate.java create mode 100644 litecommands-core-annotations/src/dev/rollczi/litecommands/validator/ValidateAnnotationResolver.java delete mode 100644 litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/argument/SimpleArgumentTest.java delete mode 100644 litecommands-core/src/dev/rollczi/litecommands/annotation/processor/AnnotationProcessorService.java delete mode 100644 litecommands-core/src/dev/rollczi/litecommands/annotation/processor/SourceProcessor.java delete mode 100644 litecommands-core/src/dev/rollczi/litecommands/argument/Arg.java rename litecommands-core/src/dev/rollczi/litecommands/argument/resolver/{AnnotationArgumentResolver.java => TypedArgumentResolver.java} (79%) create mode 100644 litecommands-core/src/dev/rollczi/litecommands/command/CommandExecutorProvider.java create mode 100644 litecommands-core/src/dev/rollczi/litecommands/command/CommandProvider.java delete mode 100644 litecommands-core/src/dev/rollczi/litecommands/command/builder/CommandBuilderExecutor.java create mode 100644 litecommands-core/src/dev/rollczi/litecommands/command/executor/CommandExecutorBuilder.java rename {litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic => litecommands-core/src/dev/rollczi/litecommands/command/executor}/LiteContext.java (95%) delete mode 100644 litecommands-core/src/dev/rollczi/litecommands/flag/Flag.java delete mode 100644 litecommands-core/src/dev/rollczi/litecommands/join/Join.java delete mode 100644 litecommands-core/src/dev/rollczi/litecommands/meta/MarkMeta.java delete mode 100644 litecommands-core/src/dev/rollczi/litecommands/permission/Permission.java delete mode 100644 litecommands-core/src/dev/rollczi/litecommands/permission/Permissions.java delete mode 100644 litecommands-core/src/dev/rollczi/litecommands/requirement/ArgumentRequirement.java delete mode 100644 litecommands-core/src/dev/rollczi/litecommands/requirement/ArgumentRequirementFactory.java delete mode 100644 litecommands-core/src/dev/rollczi/litecommands/requirement/ArgumentRequirementImpl.java delete mode 100644 litecommands-core/src/dev/rollczi/litecommands/requirement/ContextRequirementFactory.java delete mode 100644 litecommands-core/src/dev/rollczi/litecommands/requirement/RequirementFactory.java delete mode 100644 litecommands-core/src/dev/rollczi/litecommands/requirement/RequirementFactoryRegistry.java delete mode 100644 litecommands-core/src/dev/rollczi/litecommands/requirement/RequirementProcessor.java delete mode 100644 litecommands-core/src/dev/rollczi/litecommands/validator/Validate.java delete mode 100644 litecommands-core/test/dev/rollczi/litecommands/requirement/MethodCommandExecutorFactoryTest.java diff --git a/examples/bukkit/src/main/java/dev/rollczi/example/bukkit/ExamplePlugin.java b/examples/bukkit/src/main/java/dev/rollczi/example/bukkit/ExamplePlugin.java index 2d5a0aef4..998d3f19e 100644 --- a/examples/bukkit/src/main/java/dev/rollczi/example/bukkit/ExamplePlugin.java +++ b/examples/bukkit/src/main/java/dev/rollczi/example/bukkit/ExamplePlugin.java @@ -10,6 +10,7 @@ import dev.rollczi.litecommands.LiteCommands; import dev.rollczi.litecommands.adventure.LiteAdventureExtension; import dev.rollczi.litecommands.annotations.LiteAnnotationCommands; +import dev.rollczi.litecommands.join.JoinArgument; import dev.rollczi.litecommands.programmatic.LiteCommand; import dev.rollczi.litecommands.programmatic.LiteCommandsProgrammatic; import dev.rollczi.litecommands.join.Join; @@ -43,9 +44,8 @@ public void onEnable() { new ConvertCommand() )) .commands(LiteCommandsProgrammatic.of( - new LiteCommand("ban") - .permission("example.ban") + .permissions("example.ban") .argument("player", Player.class) .onExecute(context -> { Player player = context.argument("player", Player.class); @@ -63,7 +63,7 @@ public void onEnable() { // Suggestions, if you want you can override default argument suggesters .argumentSuggester(String.class, SuggestionResult.of("name", "argument")) .argumentSuggester(Integer.class, SuggestionResult.of("1", "2", "3")) - .argumentSuggester(String.class, Join.ARGUMENT_KEY, SuggestionResult.of("Simple suggestion", "Simple suggestion 2")) + .argumentSuggester(String.class, JoinArgument.KEY, SuggestionResult.of("Simple suggestion", "Simple suggestion 2")) // Context resolver for @Context Player .context(Player.class, new BukkitOnlyPlayerContextual<>("&cOnly player can execute this command!")) diff --git a/examples/bukkit/src/main/java/dev/rollczi/example/bukkit/command/BanCommand.java b/examples/bukkit/src/main/java/dev/rollczi/example/bukkit/command/BanCommand.java index 61888b51e..6690d2fca 100644 --- a/examples/bukkit/src/main/java/dev/rollczi/example/bukkit/command/BanCommand.java +++ b/examples/bukkit/src/main/java/dev/rollczi/example/bukkit/command/BanCommand.java @@ -2,7 +2,7 @@ import dev.rollczi.litecommands.argument.Arg; import dev.rollczi.litecommands.command.Command; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import dev.rollczi.litecommands.permission.Permission; import org.bukkit.entity.Player; diff --git a/examples/bukkit/src/main/java/dev/rollczi/example/bukkit/command/ConvertCommand.java b/examples/bukkit/src/main/java/dev/rollczi/example/bukkit/command/ConvertCommand.java index afd8d01d7..df2844466 100644 --- a/examples/bukkit/src/main/java/dev/rollczi/example/bukkit/command/ConvertCommand.java +++ b/examples/bukkit/src/main/java/dev/rollczi/example/bukkit/command/ConvertCommand.java @@ -1,7 +1,7 @@ package dev.rollczi.example.bukkit.command; import dev.rollczi.litecommands.argument.Arg; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import dev.rollczi.litecommands.permission.Permission; import dev.rollczi.litecommands.command.Command; diff --git a/examples/bukkit/src/main/java/dev/rollczi/example/bukkit/command/GameModeCommand.java b/examples/bukkit/src/main/java/dev/rollczi/example/bukkit/command/GameModeCommand.java index f05faa4e9..69608a4b0 100644 --- a/examples/bukkit/src/main/java/dev/rollczi/example/bukkit/command/GameModeCommand.java +++ b/examples/bukkit/src/main/java/dev/rollczi/example/bukkit/command/GameModeCommand.java @@ -2,7 +2,7 @@ import dev.rollczi.litecommands.argument.Arg; import dev.rollczi.litecommands.context.Context; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import dev.rollczi.litecommands.permission.Permission; import dev.rollczi.litecommands.command.Command; import org.bukkit.GameMode; diff --git a/examples/bukkit/src/main/java/dev/rollczi/example/bukkit/command/TeleportCommand.java b/examples/bukkit/src/main/java/dev/rollczi/example/bukkit/command/TeleportCommand.java index df8c09778..85ab81a18 100644 --- a/examples/bukkit/src/main/java/dev/rollczi/example/bukkit/command/TeleportCommand.java +++ b/examples/bukkit/src/main/java/dev/rollczi/example/bukkit/command/TeleportCommand.java @@ -2,7 +2,7 @@ import dev.rollczi.litecommands.argument.Arg; import dev.rollczi.litecommands.context.Context; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import dev.rollczi.litecommands.permission.Permission; import dev.rollczi.litecommands.command.Command; import org.bukkit.Location; diff --git a/examples/velocity/src/main/java/dev/rollczi/example/velocity/ExamplePlugin.java b/examples/velocity/src/main/java/dev/rollczi/example/velocity/ExamplePlugin.java index 9912fcc8d..9f9de7e59 100644 --- a/examples/velocity/src/main/java/dev/rollczi/example/velocity/ExamplePlugin.java +++ b/examples/velocity/src/main/java/dev/rollczi/example/velocity/ExamplePlugin.java @@ -17,6 +17,7 @@ import dev.rollczi.litecommands.LiteCommands; import dev.rollczi.litecommands.annotations.LiteAnnotationCommands; import dev.rollczi.litecommands.join.Join; +import dev.rollczi.litecommands.join.JoinArgument; import dev.rollczi.litecommands.suggestion.SuggestionResult; import dev.rollczi.litecommands.schematic.SchematicFormat; import dev.rollczi.litecommands.velocity.LiteVelocityFactory; @@ -54,7 +55,7 @@ public void onProxyInitialization(ProxyInitializeEvent event) { // Suggestions, if you want you can override default argument suggesters .argumentSuggester(String.class, SuggestionResult.of("name", "argument")) .argumentSuggester(Integer.class, SuggestionResult.of("1", "2", "3")) - .argumentSuggester(String.class, Join.ARGUMENT_KEY, SuggestionResult.of("Simple suggestion", "Simple suggestion 2")) + .argumentSuggester(String.class, JoinArgument.KEY, SuggestionResult.of("Simple suggestion", "Simple suggestion 2")) // Context resolvers @Context .context(Player.class, new VelocityOnlyPlayerContextual<>("&cOnly player can execute this command!")) diff --git a/examples/velocity/src/main/java/dev/rollczi/example/velocity/command/SendCommand.java b/examples/velocity/src/main/java/dev/rollczi/example/velocity/command/SendCommand.java index 6150aae83..c41612580 100644 --- a/examples/velocity/src/main/java/dev/rollczi/example/velocity/command/SendCommand.java +++ b/examples/velocity/src/main/java/dev/rollczi/example/velocity/command/SendCommand.java @@ -3,7 +3,7 @@ import com.velocitypowered.api.proxy.Player; import com.velocitypowered.api.proxy.server.RegisteredServer; import dev.rollczi.litecommands.argument.Arg; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import dev.rollczi.litecommands.command.Command; import net.kyori.adventure.text.minimessage.MiniMessage; diff --git a/litecommands-core-annotations/benchmark/dev/rollczi/litecommands/benchmark/LiteBenchmark.java b/litecommands-core-annotations/benchmark/dev/rollczi/litecommands/benchmark/LiteBenchmark.java index 98277e87e..e3e11e8be 100644 --- a/litecommands-core-annotations/benchmark/dev/rollczi/litecommands/benchmark/LiteBenchmark.java +++ b/litecommands-core-annotations/benchmark/dev/rollczi/litecommands/benchmark/LiteBenchmark.java @@ -3,7 +3,7 @@ import dev.rollczi.litecommands.annotations.LiteAnnotationCommands; import dev.rollczi.litecommands.argument.Arg; import dev.rollczi.litecommands.command.Command; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import dev.rollczi.litecommands.unit.AssertExecute; import dev.rollczi.litecommands.unit.LiteCommandsTestFactory; import dev.rollczi.litecommands.unit.TestPlatform; diff --git a/litecommands-core/src/dev/rollczi/litecommands/annotation/AnnotationHolder.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/AnnotationHolder.java similarity index 100% rename from litecommands-core/src/dev/rollczi/litecommands/annotation/AnnotationHolder.java rename to litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/AnnotationHolder.java diff --git a/litecommands-core/src/dev/rollczi/litecommands/annotation/AnnotationHolderImpl.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/AnnotationHolderImpl.java similarity index 100% rename from litecommands-core/src/dev/rollczi/litecommands/annotation/AnnotationHolderImpl.java rename to litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/AnnotationHolderImpl.java diff --git a/litecommands-core/src/dev/rollczi/litecommands/argument/ArgumentFactory.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/ArgumentFactory.java similarity index 61% rename from litecommands-core/src/dev/rollczi/litecommands/argument/ArgumentFactory.java rename to litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/ArgumentFactory.java index e0b77ebcd..869136a12 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/argument/ArgumentFactory.java +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/ArgumentFactory.java @@ -1,6 +1,6 @@ -package dev.rollczi.litecommands.argument; +package dev.rollczi.litecommands.annotation; -import dev.rollczi.litecommands.annotation.AnnotationHolder; +import dev.rollczi.litecommands.argument.Argument; import java.lang.annotation.Annotation; diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/ArgumentRequirementFactory.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/ArgumentRequirementFactory.java new file mode 100644 index 000000000..ab0e92178 --- /dev/null +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/ArgumentRequirementFactory.java @@ -0,0 +1,20 @@ +package dev.rollczi.litecommands.annotation; + +import dev.rollczi.litecommands.requirement.Requirement; + +import java.lang.annotation.Annotation; + +class ArgumentRequirementFactory implements RequirementFactory { + + private final ArgumentFactory argumentFactory; + + public ArgumentRequirementFactory(ArgumentFactory argumentFactory) { + this.argumentFactory = argumentFactory; + } + + @Override + public Requirement create(AnnotationHolder holder) { + return argumentFactory.create(holder); + } + +} diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/ContextRequirementFactory.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/ContextRequirementFactory.java new file mode 100644 index 000000000..29b647628 --- /dev/null +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/ContextRequirementFactory.java @@ -0,0 +1,14 @@ +package dev.rollczi.litecommands.annotation; + +import dev.rollczi.litecommands.requirement.Requirement; + +import java.lang.annotation.Annotation; + +class ContextRequirementFactory implements RequirementFactory { + + @Override + public Requirement create(AnnotationHolder holder) { + return new ContextRequirementImpl<>(holder); + } + +} diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/ContextRequirementImpl.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/ContextRequirementImpl.java new file mode 100644 index 000000000..f6c0923b0 --- /dev/null +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/ContextRequirementImpl.java @@ -0,0 +1,42 @@ +package dev.rollczi.litecommands.annotation; + +import dev.rollczi.litecommands.meta.Meta; +import dev.rollczi.litecommands.meta.MetaHolder; +import dev.rollczi.litecommands.annotation.AnnotationHolder; +import dev.rollczi.litecommands.requirement.ContextRequirement; +import dev.rollczi.litecommands.wrapper.WrapFormat; +import org.jetbrains.annotations.Nullable; + +import java.lang.annotation.Annotation; + +class ContextRequirementImpl implements ContextRequirement { + + private final AnnotationHolder holder; + private final Meta meta = Meta.create(); + + ContextRequirementImpl(AnnotationHolder holder) { + this.holder = holder; + } + + @Override + public String getName() { + return this.holder.getName(); + } + + @Override + public WrapFormat getWrapperFormat() { + return holder.getFormat(); + } + + + @Override + public Meta meta() { + return meta; + } + + @Override + public @Nullable MetaHolder parentMeta() { + return null; + } + +} diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/RequirementFactory.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/RequirementFactory.java new file mode 100644 index 000000000..c69066331 --- /dev/null +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/RequirementFactory.java @@ -0,0 +1,11 @@ +package dev.rollczi.litecommands.annotation; + +import dev.rollczi.litecommands.requirement.Requirement; + +import java.lang.annotation.Annotation; + +interface RequirementFactory { + + Requirement create(AnnotationHolder holder); + +} diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/RequirementProcessor.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/RequirementProcessor.java new file mode 100644 index 000000000..84e8fb8be --- /dev/null +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/RequirementProcessor.java @@ -0,0 +1,29 @@ +package dev.rollczi.litecommands.annotation; + +import dev.rollczi.litecommands.annotation.processor.AnnotationInvoker; +import dev.rollczi.litecommands.annotation.processor.AnnotationProcessor; + +import java.lang.annotation.Annotation; +import java.util.Optional; + +public class RequirementProcessor implements AnnotationProcessor { + + private final RequirementFactory requirementFactory; + private final Class annotationClass; + + public RequirementProcessor(Class annotationClass, ArgumentFactory argumentFactory) { + this.requirementFactory = new ArgumentRequirementFactory<>(argumentFactory); + this.annotationClass = annotationClass; + } + + public RequirementProcessor(Class annotationClass) { + this.requirementFactory = new ContextRequirementFactory<>(); + this.annotationClass = annotationClass; + } + + @Override + public AnnotationInvoker process(AnnotationInvoker invoker) { + return invoker.onRequirement(annotationClass, (holder, builder) -> Optional.of(requirementFactory.create(holder))); + } + +} diff --git a/litecommands-core/src/dev/rollczi/litecommands/annotation/processor/AnnotationInvoker.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/processor/AnnotationInvoker.java similarity index 83% rename from litecommands-core/src/dev/rollczi/litecommands/annotation/processor/AnnotationInvoker.java rename to litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/processor/AnnotationInvoker.java index 411a964bd..4fc2267db 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/annotation/processor/AnnotationInvoker.java +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/processor/AnnotationInvoker.java @@ -26,6 +26,11 @@ AnnotationInvoker onRequirement(Class annotationType, AnnotationProce return this; } + default + AnnotationInvoker onRequirementMeta(Class annotationType, AnnotationProcessor.RequirementMetaListener listener) { + return this; + } + CommandBuilder getResult(); } diff --git a/litecommands-core/src/dev/rollczi/litecommands/annotation/processor/AnnotationProcessor.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/processor/AnnotationProcessor.java similarity index 59% rename from litecommands-core/src/dev/rollczi/litecommands/annotation/processor/AnnotationProcessor.java rename to litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/processor/AnnotationProcessor.java index e7f86fe26..176b460cb 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/annotation/processor/AnnotationProcessor.java +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/processor/AnnotationProcessor.java @@ -1,11 +1,14 @@ package dev.rollczi.litecommands.annotation.processor; import dev.rollczi.litecommands.annotation.AnnotationHolder; +import dev.rollczi.litecommands.command.CommandExecutorProvider; import dev.rollczi.litecommands.command.builder.CommandBuilder; -import dev.rollczi.litecommands.command.builder.CommandBuilderExecutor; +import dev.rollczi.litecommands.command.executor.CommandExecutorBuilder; import dev.rollczi.litecommands.meta.MetaHolder; +import dev.rollczi.litecommands.requirement.Requirement; import java.lang.annotation.Annotation; +import java.util.Optional; public interface AnnotationProcessor { @@ -20,12 +23,15 @@ interface StructureListener { } interface StructureExecutorListener { - CommandBuilder call(A annotation, CommandBuilder builder, CommandBuilderExecutor executorBuilder); + CommandBuilder call(A annotation, CommandBuilder builder, CommandExecutorProvider executorProvider); } interface RequirementListener { - CommandBuilder call(AnnotationHolder annotationHolder, CommandBuilder builder, CommandBuilderExecutor executorBuilder); + Optional> call(AnnotationHolder annotationHolder, CommandBuilder builder); } + interface RequirementMetaListener { + void call(AnnotationHolder annotationHolder, CommandBuilder builder, Requirement requirement); + } } diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/processor/AnnotationProcessorService.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/processor/AnnotationProcessorService.java new file mode 100644 index 000000000..41dff5a39 --- /dev/null +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotation/processor/AnnotationProcessorService.java @@ -0,0 +1,59 @@ +package dev.rollczi.litecommands.annotation.processor; + +import dev.rollczi.litecommands.annotation.RequirementProcessor; +import dev.rollczi.litecommands.argument.Arg; +import dev.rollczi.litecommands.argument.ArgArgumentFactory; +import dev.rollczi.litecommands.async.AsyncAnnotationResolver; +import dev.rollczi.litecommands.command.CommandAnnotationProcessor; +import dev.rollczi.litecommands.command.RootCommandAnnotationProcessor; +import dev.rollczi.litecommands.command.builder.CommandBuilder; +import dev.rollczi.litecommands.execute.ExecuteAnnotationResolver; +import dev.rollczi.litecommands.context.Context; +import dev.rollczi.litecommands.description.DescriptionAnnotationResolver; +import dev.rollczi.litecommands.flag.Flag; +import dev.rollczi.litecommands.flag.FlagArgumentFactory; +import dev.rollczi.litecommands.join.Join; +import dev.rollczi.litecommands.join.JoinArgumentFactory; +import dev.rollczi.litecommands.meta.MarkMetaAnnotationResolver; +import dev.rollczi.litecommands.permission.PermissionAnnotationResolver; +import dev.rollczi.litecommands.permission.PermissionsAnnotationResolver; +import dev.rollczi.litecommands.validator.ValidateAnnotationResolver; + +import java.util.ArrayList; +import java.util.List; + +public class AnnotationProcessorService { + + private final List> annotationProcessors = new ArrayList<>(); + + public > AnnotationProcessorService register(A processor) { + annotationProcessors.add(processor); + return this; + } + + public CommandBuilder process(AnnotationInvoker invoker) { + for (AnnotationProcessor processor : annotationProcessors) { + invoker = processor.process(invoker); + } + + return invoker.getResult(); + } + + public static AnnotationProcessorService defaultService() { + return new AnnotationProcessorService() + .register(new CommandAnnotationProcessor<>()) + .register(new RootCommandAnnotationProcessor<>()) + .register(new MarkMetaAnnotationResolver<>()) + .register(new DescriptionAnnotationResolver<>()) + .register(new AsyncAnnotationResolver<>()) + .register(new PermissionAnnotationResolver<>()) + .register(new PermissionsAnnotationResolver<>()) + .register(new ValidateAnnotationResolver<>()) + .register(new ExecuteAnnotationResolver<>()) + .register(new RequirementProcessor<>(Flag.class, new FlagArgumentFactory())) + .register(new RequirementProcessor<>(Arg.class, new ArgArgumentFactory())) + .register(new RequirementProcessor<>(Join.class, new JoinArgumentFactory())) + .register(new RequirementProcessor<>(Context.class)); + } + +} diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/InstanceSourceProcessor.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/InstanceSourceProcessor.java index da46d9de5..b739eb02a 100644 --- a/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/InstanceSourceProcessor.java +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/InstanceSourceProcessor.java @@ -1,17 +1,13 @@ package dev.rollczi.litecommands.annotations; import dev.rollczi.litecommands.command.builder.CommandBuilder; -import dev.rollczi.litecommands.command.builder.CommandBuilderExecutor; import dev.rollczi.litecommands.annotation.processor.AnnotationInvoker; import dev.rollczi.litecommands.annotation.processor.AnnotationProcessorService; -import dev.rollczi.litecommands.annotation.processor.SourceProcessor; -import dev.rollczi.litecommands.reflect.LiteCommandsReflectException; import dev.rollczi.litecommands.wrapper.WrapperRegistry; import java.lang.reflect.Method; -import java.lang.reflect.Parameter; -class InstanceSourceProcessor implements SourceProcessor { +class InstanceSourceProcessor { private final AnnotationProcessorService annotationProcessorService; private final WrapperRegistry wrapperRegistry; @@ -24,7 +20,6 @@ public InstanceSourceProcessor( this.wrapperRegistry = wrapperRegistry; } - @Override public CommandBuilder processBuilder(InstanceSource source) { Object instance = source.getInstance(); Class type = instance.getClass(); @@ -34,29 +29,9 @@ public CommandBuilder processBuilder(InstanceSource source) { context = annotationProcessorService.process(classInvoker); for (Method method : type.getDeclaredMethods()) { - CommandBuilderExecutor executorBuilder = new CommandBuilderExecutor<>(context); - MethodInvoker methodInvoker = new MethodInvoker<>(instance, method, context, executorBuilder); + MethodInvoker methodInvoker = new MethodInvoker<>(annotationProcessorService, wrapperRegistry, instance, method, context); context = annotationProcessorService.process(methodInvoker); - - if (!executorBuilder.buildable()) { - continue; - } - - int exceptedParametersCount = 1; - for (Parameter parameter : method.getParameters()) { - AnnotationInvoker parameterInvoker = new ParameterInvoker<>(wrapperRegistry, parameter, context, executorBuilder); - - context = annotationProcessorService.process(parameterInvoker); - - if (executorBuilder.getRequirementsCount() != exceptedParametersCount) { //TODO może zrobić return value flow? - throw new LiteCommandsReflectException(method, parameter, "Cannot find annotation processor for parameter!"); - } - - exceptedParametersCount++; - } - - } return context; diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/LiteAnnotationCommands.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/LiteAnnotationCommands.java index d14884514..b81bd93a6 100644 --- a/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/LiteAnnotationCommands.java +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/LiteAnnotationCommands.java @@ -17,16 +17,21 @@ public class LiteAnnotationCommands implements LiteCommandsProvider commandInstances; private final List> commandClasses; + private final AnnotationProcessorService annotationProcessorService; - private LiteAnnotationCommands() { + private LiteAnnotationCommands(AnnotationProcessorService annotationProcessorService) { + this.annotationProcessorService = annotationProcessorService; this.commandInstances = new ArrayList<>(); this.commandClasses = new ArrayList<>(); } + private LiteAnnotationCommands() { + this(AnnotationProcessorService.defaultService()); + } + @Override public List> provide(LiteCommandsInternalBuilderApi builder) { WrapperRegistry wrapperRegistry = builder.getWrapperRegistry(); - AnnotationProcessorService annotationProcessorService = builder.getAnnotationProcessorRegistry(); InstanceSourceProcessor processor = new InstanceSourceProcessor<>(annotationProcessorService, wrapperRegistry); Injector injector = new Injector<>(builder.getBindRegistry()); @@ -55,14 +60,6 @@ public LiteAnnotationCommands loadClasses(Class... commands) { return this; } - public LiteAnnotationCommands loadPackages(String... packageNames) { - throw new UnsupportedOperationException("Not implemented yet"); - } - - public LiteAnnotationCommands loadPackages(Package... packages) { - throw new UnsupportedOperationException("Not implemented yet"); - } - public static LiteAnnotationCommands create() { return new LiteAnnotationCommands<>(); } @@ -75,12 +72,4 @@ public static LiteAnnotationCommands ofClasses(Class... comm return new LiteAnnotationCommands().loadClasses(commands); } - public static LiteAnnotationCommands ofPackages(String... packageNames) { - return new LiteAnnotationCommands().loadPackages(packageNames); - } - - public static LiteAnnotationCommands ofPackages(Package... packages) { - return new LiteAnnotationCommands().loadPackages(packages); - } - } \ No newline at end of file diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/MethodCommandExecutor.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/MethodCommandExecutor.java index fc1aa36a1..5eb8a4007 100644 --- a/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/MethodCommandExecutor.java +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/MethodCommandExecutor.java @@ -4,6 +4,7 @@ import dev.rollczi.litecommands.command.executor.AbstractCommandExecutor; import dev.rollczi.litecommands.command.executor.CommandExecuteResult; import dev.rollczi.litecommands.command.executor.CommandExecutorMatchResult; +import dev.rollczi.litecommands.meta.Meta; import dev.rollczi.litecommands.requirement.Requirement; import dev.rollczi.litecommands.requirement.RequirementMatch; import dev.rollczi.litecommands.requirement.RequirementsResult; @@ -16,18 +17,20 @@ class MethodCommandExecutor extends AbstractCommandExecutor { private final Method method; private final Object instance; - private final MethodDefinition definition; + private final MethodDefinition definition; MethodCommandExecutor( CommandRoute parent, Method method, Object instance, - MethodDefinition definition + MethodDefinition definition, + Meta meta ) { - super(parent, definition.getRequirements()); + super(parent, definition.getArguments(), definition.getContextRequirements()); this.method = method; this.instance = instance; this.definition = definition; + this.meta.apply(meta); } @Override @@ -35,14 +38,14 @@ public CommandExecutorMatchResult match(RequirementsResult results) { Object[] objects = new Object[method.getParameterCount()]; for (int parameterIndex = 0; parameterIndex < method.getParameterCount(); parameterIndex++) { - Requirement requirement = definition.getRequirement(parameterIndex); + Requirement requirement = definition.getRequirement(parameterIndex); String name = requirement.getName(); if (!results.has(name)) { return CommandExecutorMatchResult.failed(new IllegalStateException("Not all parameters are resolved, missing " + name)); } - RequirementMatch requirementMatch = results.get(name); + RequirementMatch requirementMatch = results.get(name); Object unwrapped = requirementMatch.getResult().unwrap(); objects[parameterIndex] = unwrapped; diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/MethodDefinition.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/MethodDefinition.java index 68ed278c8..fc47d55dd 100644 --- a/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/MethodDefinition.java +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/MethodDefinition.java @@ -1,5 +1,8 @@ package dev.rollczi.litecommands.annotations; +import dev.rollczi.litecommands.argument.Argument; +import dev.rollczi.litecommands.reflect.LiteCommandsReflectException; +import dev.rollczi.litecommands.requirement.ContextRequirement; import dev.rollczi.litecommands.requirement.Requirement; import dev.rollczi.litecommands.wrapper.WrapFormat; @@ -7,45 +10,70 @@ import java.lang.reflect.Parameter; import java.util.Collection; import java.util.HashMap; -import java.util.List; import java.util.Map; -class MethodDefinition { +class MethodDefinition { - private final Map> requirements = new HashMap<>(); + private final Method method; + private final Map> arguments = new HashMap<>(); + private final Map> contextRequirements = new HashMap<>(); - void putRequirement(int parameterIndex, Requirement requirement) { - requirements.put(parameterIndex, requirement); + MethodDefinition(Method method) { + this.method = method; } - Requirement getRequirement(int parameterIndex) { - return requirements.get(parameterIndex); + Requirement getRequirement(int parameterIndex) { + Argument argument = arguments.get(parameterIndex); + + if (argument != null) { + return argument; + } + + ContextRequirement contextRequirement = contextRequirements.get(parameterIndex); + + if (contextRequirement != null) { + return contextRequirement; + } + + throw new IllegalArgumentException("Cannot find requirement for parameter index " + parameterIndex); } - Collection> getRequirements() { - return requirements.values(); + public Collection> getArguments() { + return arguments.values(); } - static MethodDefinition createDefinition(Method method, List> requirements) { - MethodDefinition definition = new MethodDefinition<>(); + public Collection> getContextRequirements() { + return contextRequirements.values(); + } + + void putRequirement(int parameterIndex, Requirement requirement) { + WrapFormat wrapperFormat = requirement.getWrapperFormat(); + Class typeOrParsed = wrapperFormat.getOutTypeOrParsed(); + Parameter parameter = method.getParameters()[parameterIndex]; + + if (!typeOrParsed.isAssignableFrom(parameter.getType())) { + throw new LiteCommandsReflectException(method, parameter, "Parameter type is not assignable from " + typeOrParsed.getSimpleName()); + } - int index = 0; - for (Parameter parameter : method.getParameters()) { - Requirement requirement = requirements.get(index); + if (requirement instanceof Argument) { + if (arguments.containsKey(parameterIndex)) { + throw new IllegalArgumentException("Cannot put argument on index " + parameterIndex + " because it is already occupied!"); + } - WrapFormat format = requirement.getAnnotationHolder().getFormat(); - Class typeToCheck = format.getOutTypeOrParsed(); - Class currentType = parameter.getType(); + arguments.put(parameterIndex, (Argument) requirement); + return; + } - if (!typeToCheck.equals(currentType)) { - throw new IllegalStateException("Parameter type mismatch for " + parameter.getName() + " in " + method.getName() + " method (expected " + currentType.getSimpleName() + " but got " + typeToCheck.getSimpleName()); + if (requirement instanceof ContextRequirement) { + if (contextRequirements.containsKey(parameterIndex)) { + throw new IllegalArgumentException("Cannot put context requirement on index " + parameterIndex + " because it is already occupied!"); } - definition.putRequirement(index, requirement); - index++; + contextRequirements.put(parameterIndex, (ContextRequirement) requirement); + return; } - return definition; + throw new IllegalArgumentException("Cannot put requirement on index " + parameterIndex + " because it is not supported!"); } } diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/MethodInvoker.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/MethodInvoker.java index a554e2cf8..dc7d099c9 100644 --- a/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/MethodInvoker.java +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/MethodInvoker.java @@ -1,25 +1,40 @@ package dev.rollczi.litecommands.annotations; +import dev.rollczi.litecommands.annotation.AnnotationHolder; +import dev.rollczi.litecommands.annotation.processor.AnnotationProcessorService; +import dev.rollczi.litecommands.command.CommandExecutorProvider; import dev.rollczi.litecommands.command.builder.CommandBuilder; -import dev.rollczi.litecommands.command.builder.CommandBuilderExecutor; import dev.rollczi.litecommands.annotation.processor.AnnotationInvoker; import dev.rollczi.litecommands.annotation.processor.AnnotationProcessor; +import dev.rollczi.litecommands.meta.Meta; +import dev.rollczi.litecommands.meta.MetaHolder; +import dev.rollczi.litecommands.requirement.Requirement; +import dev.rollczi.litecommands.wrapper.WrapFormat; +import dev.rollczi.litecommands.wrapper.WrapperRegistry; +import org.jetbrains.annotations.Nullable; import java.lang.annotation.Annotation; import java.lang.reflect.Method; +import java.lang.reflect.Parameter; +import java.util.Optional; -class MethodInvoker implements AnnotationInvoker { +class MethodInvoker implements AnnotationInvoker, MetaHolder { - private final Object instance; + private final AnnotationProcessorService annotationProcessorService; + private final WrapperRegistry wrapperRegistry; private final Method method; private CommandBuilder commandBuilder; - private final CommandBuilderExecutor executorBuilder; + private final MethodDefinition methodDefinition; + private final CommandExecutorProvider executorProvider; + private final Meta meta = Meta.create(); - public MethodInvoker(Object instance, Method method, CommandBuilder commandBuilder, CommandBuilderExecutor executorBuilder) { - this.instance = instance; + public MethodInvoker(AnnotationProcessorService annotationProcessorService, WrapperRegistry wrapperRegistry, Object instance, Method method, CommandBuilder commandBuilder) { + this.annotationProcessorService = annotationProcessorService; + this.wrapperRegistry = wrapperRegistry; this.method = method; this.commandBuilder = commandBuilder; - this.executorBuilder = executorBuilder; + this.methodDefinition = new MethodDefinition(method); + this.executorProvider = parent -> new MethodCommandExecutor<>(parent, method, instance, methodDefinition, meta); } @Override @@ -30,7 +45,7 @@ public AnnotationInvoker on(Class annotationTy return this; } - listener.call(annotation, executorBuilder); + listener.call(annotation, this); return this; } @@ -42,13 +57,30 @@ public AnnotationInvoker onExecutorStructure(Clas return this; } - executorBuilder.setExecutorFactory((parent, requirements) -> { - MethodDefinition definition = MethodDefinition.createDefinition(method, requirements); + commandBuilder = listener.call(methodAnnotation, commandBuilder, executorProvider); + return this; + } + + @Override + public AnnotationInvoker onRequirement(Class annotationType, AnnotationProcessor.RequirementListener listener) { + for (int index = 0; index < method.getParameterCount(); index++) { + Parameter parameter = method.getParameters()[index]; + A parameterAnnotation = parameter.getAnnotation(annotationType); + + if (parameterAnnotation == null) { + continue; + } - return new MethodCommandExecutor<>(parent, method, instance, definition); - }); + Optional> requirementOptional = listener.call(createHolder(parameterAnnotation, parameter), commandBuilder); + + if (requirementOptional.isPresent()) { + Requirement requirement = requirementOptional.get(); + + methodDefinition.putRequirement(index, requirement); + annotationProcessorService.process(new ParameterInvoker<>(wrapperRegistry, commandBuilder, parameter, requirement)); + } + } - commandBuilder = listener.call(methodAnnotation, commandBuilder, executorBuilder); return this; } @@ -57,5 +89,20 @@ public CommandBuilder getResult() { return commandBuilder; } + private AnnotationHolder createHolder(A annotation, Parameter parameter) { + WrapFormat format = MethodParameterUtil.wrapperFormat(wrapperRegistry, parameter); + + return AnnotationHolder.of(annotation, format, () -> parameter.getName()); + } + + @Override + public Meta meta() { + return meta; + } + + @Override + public @Nullable MetaHolder parentMeta() { + return commandBuilder; + } } diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/ParameterInvoker.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/ParameterInvoker.java index a2ce1777f..db50816d4 100644 --- a/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/ParameterInvoker.java +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/annotations/ParameterInvoker.java @@ -1,46 +1,52 @@ - package dev.rollczi.litecommands.annotations; -import dev.rollczi.litecommands.command.builder.CommandBuilder; -import dev.rollczi.litecommands.command.builder.CommandBuilderExecutor; import dev.rollczi.litecommands.annotation.AnnotationHolder; import dev.rollczi.litecommands.annotation.processor.AnnotationInvoker; import dev.rollczi.litecommands.annotation.processor.AnnotationProcessor; +import dev.rollczi.litecommands.command.builder.CommandBuilder; +import dev.rollczi.litecommands.requirement.Requirement; import dev.rollczi.litecommands.wrapper.WrapFormat; import dev.rollczi.litecommands.wrapper.WrapperRegistry; import java.lang.annotation.Annotation; import java.lang.reflect.Parameter; -class ParameterInvoker implements AnnotationInvoker { +public class ParameterInvoker implements AnnotationInvoker { private final WrapperRegistry wrapperRegistry; + private final CommandBuilder commandBuilder; private final Parameter parameter; - private CommandBuilder commandBuilder; - private final CommandBuilderExecutor executorBuilder; + private final Requirement requirement; - public ParameterInvoker(WrapperRegistry wrapperRegistry, Parameter parameter, CommandBuilder commandBuilder, CommandBuilderExecutor executorBuilder) { + public ParameterInvoker(WrapperRegistry wrapperRegistry, CommandBuilder commandBuilder, Parameter parameter, Requirement requirement) { this.wrapperRegistry = wrapperRegistry; - this.parameter = parameter; this.commandBuilder = commandBuilder; - this.executorBuilder = executorBuilder; + this.parameter = parameter; + this.requirement = requirement; } @Override - public AnnotationInvoker onRequirement(Class annotationType, AnnotationProcessor.RequirementListener listener) { - A parameterAnnotation = parameter.getAnnotation(annotationType); + public AnnotationInvoker on(Class annotationType, AnnotationProcessor.Listener listener) { + A annotation = parameter.getAnnotation(annotationType); - if (parameterAnnotation == null) { + if (annotation == null) { return this; } - commandBuilder = listener.call(createHolder(parameterAnnotation, parameter), commandBuilder, executorBuilder); + listener.call(annotation, requirement); return this; } @Override - public CommandBuilder getResult() { - return commandBuilder; + public AnnotationInvoker onRequirementMeta(Class annotationType, AnnotationProcessor.RequirementMetaListener listener) { + A annotation = parameter.getAnnotation(annotationType); + + if (annotation == null) { + return this; + } + + listener.call(createHolder(annotation, parameter), commandBuilder, requirement); + return this; } private AnnotationHolder createHolder(A annotation, Parameter parameter) { @@ -49,4 +55,9 @@ public CommandBuilder getResult() { return AnnotationHolder.of(annotation, format, () -> parameter.getName()); } + @Override + public CommandBuilder getResult() { + return commandBuilder; + } + } diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/argument/Arg.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/argument/Arg.java new file mode 100644 index 000000000..c284040e1 --- /dev/null +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/argument/Arg.java @@ -0,0 +1,14 @@ +package dev.rollczi.litecommands.argument; + +import java.lang.annotation.ElementType; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; +import java.lang.annotation.Target; + +@Target({ ElementType.PARAMETER }) +@Retention(RetentionPolicy.RUNTIME) +public @interface Arg { + + String value() default ""; + +} diff --git a/litecommands-core/src/dev/rollczi/litecommands/argument/ArgArgumentFactory.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/argument/ArgArgumentFactory.java similarity index 77% rename from litecommands-core/src/dev/rollczi/litecommands/argument/ArgArgumentFactory.java rename to litecommands-core-annotations/src/dev/rollczi/litecommands/argument/ArgArgumentFactory.java index 09edd0557..cb7730283 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/argument/ArgArgumentFactory.java +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/argument/ArgArgumentFactory.java @@ -1,6 +1,7 @@ package dev.rollczi.litecommands.argument; import dev.rollczi.litecommands.annotation.AnnotationHolder; +import dev.rollczi.litecommands.annotation.ArgumentFactory; public class ArgArgumentFactory implements ArgumentFactory { @@ -8,7 +9,7 @@ public class ArgArgumentFactory implements ArgumentFactory { public Argument create(AnnotationHolder holder) { Arg annotation = holder.getAnnotation(); - return new SimpleArgument<>(AnnotationHolder.of(annotation, holder.getFormat(), () -> { + return new SimpleArgument<>(() -> { String name = annotation.value(); if (!name.isEmpty()) { @@ -16,6 +17,6 @@ public Argument create(AnnotationHolder holder) { } return holder.getName(); - })); + }, holder.getFormat()); } } diff --git a/litecommands-core/src/dev/rollczi/litecommands/async/Async.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/async/Async.java similarity index 100% rename from litecommands-core/src/dev/rollczi/litecommands/async/Async.java rename to litecommands-core-annotations/src/dev/rollczi/litecommands/async/Async.java diff --git a/litecommands-core/src/dev/rollczi/litecommands/async/AsyncAnnotationResolver.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/async/AsyncAnnotationResolver.java similarity index 99% rename from litecommands-core/src/dev/rollczi/litecommands/async/AsyncAnnotationResolver.java rename to litecommands-core-annotations/src/dev/rollczi/litecommands/async/AsyncAnnotationResolver.java index 7ebdbba6c..876eb4326 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/async/AsyncAnnotationResolver.java +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/async/AsyncAnnotationResolver.java @@ -12,7 +12,6 @@ public class AsyncAnnotationResolver implements AnnotationProcessor process(AnnotationInvoker invoker) { return invoker.on(Async.class, (annotation, metaHolder) -> { metaHolder.meta().put(Meta.POLL_TYPE, SchedulerPollType.ASYNC); - }); } diff --git a/litecommands-core/src/dev/rollczi/litecommands/command/Command.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/command/Command.java similarity index 94% rename from litecommands-core/src/dev/rollczi/litecommands/command/Command.java rename to litecommands-core-annotations/src/dev/rollczi/litecommands/command/Command.java index 8ae3229bf..64e64d782 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/command/Command.java +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/command/Command.java @@ -1,7 +1,5 @@ package dev.rollczi.litecommands.command; -import dev.rollczi.litecommands.command.executor.Execute; - import java.lang.annotation.Annotation; import java.lang.annotation.ElementType; import java.lang.annotation.Retention; @@ -12,7 +10,7 @@ * Is used to mark the class as a command. * This annotation is required for the class to be registered. * - * @see Execute + * @see dev.rollczi.litecommands.execute.Execute * @see RootCommand */ @Target({ ElementType.TYPE }) diff --git a/litecommands-core/src/dev/rollczi/litecommands/command/CommandAnnotationProcessor.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/command/CommandAnnotationProcessor.java similarity index 94% rename from litecommands-core/src/dev/rollczi/litecommands/command/CommandAnnotationProcessor.java rename to litecommands-core-annotations/src/dev/rollczi/litecommands/command/CommandAnnotationProcessor.java index ca4ed8de0..652dc93e4 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/command/CommandAnnotationProcessor.java +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/command/CommandAnnotationProcessor.java @@ -2,6 +2,7 @@ import dev.rollczi.litecommands.annotation.processor.AnnotationInvoker; import dev.rollczi.litecommands.annotation.processor.AnnotationProcessor; +import dev.rollczi.litecommands.command.Command; import dev.rollczi.litecommands.util.LiteCommandsUtil; import java.util.Arrays; @@ -22,4 +23,5 @@ public AnnotationInvoker process(AnnotationInvoker invoker) { throw new IllegalArgumentException("Route name cannot be empty"); }); } + } diff --git a/litecommands-core/src/dev/rollczi/litecommands/command/RootCommand.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/command/RootCommand.java similarity index 100% rename from litecommands-core/src/dev/rollczi/litecommands/command/RootCommand.java rename to litecommands-core-annotations/src/dev/rollczi/litecommands/command/RootCommand.java diff --git a/litecommands-core/src/dev/rollczi/litecommands/command/RootCommandAnnotationProcessor.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/command/RootCommandAnnotationProcessor.java similarity index 100% rename from litecommands-core/src/dev/rollczi/litecommands/command/RootCommandAnnotationProcessor.java rename to litecommands-core-annotations/src/dev/rollczi/litecommands/command/RootCommandAnnotationProcessor.java diff --git a/litecommands-core/src/dev/rollczi/litecommands/context/Context.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/context/Context.java similarity index 100% rename from litecommands-core/src/dev/rollczi/litecommands/context/Context.java rename to litecommands-core-annotations/src/dev/rollczi/litecommands/context/Context.java diff --git a/litecommands-core/src/dev/rollczi/litecommands/description/Description.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/description/Description.java similarity index 100% rename from litecommands-core/src/dev/rollczi/litecommands/description/Description.java rename to litecommands-core-annotations/src/dev/rollczi/litecommands/description/Description.java diff --git a/litecommands-core/src/dev/rollczi/litecommands/description/DescriptionAnnotationResolver.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/description/DescriptionAnnotationResolver.java similarity index 100% rename from litecommands-core/src/dev/rollczi/litecommands/description/DescriptionAnnotationResolver.java rename to litecommands-core-annotations/src/dev/rollczi/litecommands/description/DescriptionAnnotationResolver.java diff --git a/litecommands-core/src/dev/rollczi/litecommands/editor/AnnotationEditorService.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/edit/AnnotationEditorService.java similarity index 90% rename from litecommands-core/src/dev/rollczi/litecommands/editor/AnnotationEditorService.java rename to litecommands-core-annotations/src/dev/rollczi/litecommands/edit/AnnotationEditorService.java index 471d70a1d..12be2df11 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/editor/AnnotationEditorService.java +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/edit/AnnotationEditorService.java @@ -1,6 +1,7 @@ -package dev.rollczi.litecommands.editor; +package dev.rollczi.litecommands.edit; import dev.rollczi.litecommands.command.builder.CommandBuilder; +import dev.rollczi.litecommands.editor.Editor; import java.util.HashMap; import java.util.Map; diff --git a/litecommands-core/src/dev/rollczi/litecommands/editor/Edit.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/edit/Edit.java similarity index 87% rename from litecommands-core/src/dev/rollczi/litecommands/editor/Edit.java rename to litecommands-core-annotations/src/dev/rollczi/litecommands/edit/Edit.java index 065e4f022..e458194d1 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/editor/Edit.java +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/edit/Edit.java @@ -1,4 +1,4 @@ -package dev.rollczi.litecommands.editor; +package dev.rollczi.litecommands.edit; import java.lang.annotation.ElementType; import java.lang.annotation.Retention; diff --git a/litecommands-core/src/dev/rollczi/litecommands/command/executor/Execute.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/execute/Execute.java similarity index 96% rename from litecommands-core/src/dev/rollczi/litecommands/command/executor/Execute.java rename to litecommands-core-annotations/src/dev/rollczi/litecommands/execute/Execute.java index 31c277c9c..516a2bf90 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/command/executor/Execute.java +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/execute/Execute.java @@ -1,4 +1,4 @@ -package dev.rollczi.litecommands.command.executor; +package dev.rollczi.litecommands.execute; import java.lang.annotation.Annotation; import java.lang.annotation.ElementType; diff --git a/litecommands-core/src/dev/rollczi/litecommands/command/executor/ExecuteAnnotationResolver.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/execute/ExecuteAnnotationResolver.java similarity index 80% rename from litecommands-core/src/dev/rollczi/litecommands/command/executor/ExecuteAnnotationResolver.java rename to litecommands-core-annotations/src/dev/rollczi/litecommands/execute/ExecuteAnnotationResolver.java index 5d267ef6f..dedbc3185 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/command/executor/ExecuteAnnotationResolver.java +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/execute/ExecuteAnnotationResolver.java @@ -1,9 +1,9 @@ -package dev.rollczi.litecommands.command.executor; +package dev.rollczi.litecommands.execute; import dev.rollczi.litecommands.annotation.processor.AnnotationInvoker; import dev.rollczi.litecommands.annotation.processor.AnnotationProcessor; +import dev.rollczi.litecommands.command.CommandExecutorProvider; import dev.rollczi.litecommands.command.builder.CommandBuilder; -import dev.rollczi.litecommands.command.builder.CommandBuilderExecutor; import dev.rollczi.litecommands.util.LiteCommandsUtil; import java.util.Arrays; @@ -15,19 +15,19 @@ public AnnotationInvoker process(AnnotationInvoker invoker) { return invoker.onExecutorStructure(Execute.class, (annotation, builder, executorBuilder) -> resolve(annotation, builder, executorBuilder)); } - private CommandBuilder resolve(Execute annotation, CommandBuilder context, CommandBuilderExecutor executorBuilder) { + private CommandBuilder resolve(Execute annotation, CommandBuilder context, CommandExecutorProvider executorProvider) { boolean isNotEmpty = LiteCommandsUtil.checkConsistent(annotation.name(), annotation.aliases()); if (isNotEmpty) { context.getRealRoute().appendChild(CommandBuilder.create() .routeName(annotation.name()) .routeAliases(Arrays.asList(annotation.aliases())) - .applyOnRoute(builder -> builder.appendExecutor(executorBuilder))); + .applyOnRoute(builder -> builder.appendExecutor(executorProvider))); return context; } - context.getRealRoute().appendExecutor(executorBuilder); + context.getRealRoute().appendExecutor(executorProvider); return context; } diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/flag/Flag.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/flag/Flag.java new file mode 100644 index 000000000..2b26d33e0 --- /dev/null +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/flag/Flag.java @@ -0,0 +1,14 @@ +package dev.rollczi.litecommands.flag; + +import java.lang.annotation.ElementType; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; +import java.lang.annotation.Target; + +@Target({ ElementType.PARAMETER }) +@Retention(RetentionPolicy.RUNTIME) +public @interface Flag { + + String value(); + +} diff --git a/litecommands-core/src/dev/rollczi/litecommands/flag/FlagArgumentFactory.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/flag/FlagArgumentFactory.java similarity index 80% rename from litecommands-core/src/dev/rollczi/litecommands/flag/FlagArgumentFactory.java rename to litecommands-core-annotations/src/dev/rollczi/litecommands/flag/FlagArgumentFactory.java index a0b8fe86d..d2bb537c3 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/flag/FlagArgumentFactory.java +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/flag/FlagArgumentFactory.java @@ -2,7 +2,7 @@ import dev.rollczi.litecommands.argument.Argument; import dev.rollczi.litecommands.annotation.AnnotationHolder; -import dev.rollczi.litecommands.argument.ArgumentFactory; +import dev.rollczi.litecommands.annotation.ArgumentFactory; import dev.rollczi.litecommands.wrapper.WrapFormat; public class FlagArgumentFactory implements ArgumentFactory { @@ -18,8 +18,9 @@ public Argument create(AnnotationHolder holder) { } AnnotationHolder flagHolder = (AnnotationHolder) holder; + Flag flag = holder.getAnnotation(); - return (Argument) new FlagArgument(flagHolder); + return (Argument) new FlagArgument(() -> flag.value(), flagHolder.getFormat()); } } diff --git a/litecommands-core/src/dev/rollczi/litecommands/inject/Inject.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/inject/Inject.java similarity index 100% rename from litecommands-core/src/dev/rollczi/litecommands/inject/Inject.java rename to litecommands-core-annotations/src/dev/rollczi/litecommands/inject/Inject.java diff --git a/litecommands-core/src/dev/rollczi/litecommands/inject/Injector.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/inject/Injector.java similarity index 100% rename from litecommands-core/src/dev/rollczi/litecommands/inject/Injector.java rename to litecommands-core-annotations/src/dev/rollczi/litecommands/inject/Injector.java diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/join/Join.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/join/Join.java new file mode 100644 index 000000000..b8b4b981b --- /dev/null +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/join/Join.java @@ -0,0 +1,19 @@ +package dev.rollczi.litecommands.join; + +import dev.rollczi.litecommands.argument.ArgumentKey; + +import java.lang.annotation.Annotation; +import java.lang.annotation.ElementType; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; +import java.lang.annotation.Target; + +@Target({ ElementType.PARAMETER }) +@Retention(RetentionPolicy.RUNTIME) +public @interface Join { + + String separator() default " "; + + int limit() default Integer.MAX_VALUE; + +} diff --git a/litecommands-core/src/dev/rollczi/litecommands/join/JoinArgumentFactory.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/join/JoinArgumentFactory.java similarity index 57% rename from litecommands-core/src/dev/rollczi/litecommands/join/JoinArgumentFactory.java rename to litecommands-core-annotations/src/dev/rollczi/litecommands/join/JoinArgumentFactory.java index 202b6853e..c1c77f59c 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/join/JoinArgumentFactory.java +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/join/JoinArgumentFactory.java @@ -2,13 +2,14 @@ import dev.rollczi.litecommands.argument.Argument; import dev.rollczi.litecommands.annotation.AnnotationHolder; -import dev.rollczi.litecommands.argument.ArgumentFactory; +import dev.rollczi.litecommands.annotation.ArgumentFactory; public class JoinArgumentFactory implements ArgumentFactory { @Override public Argument create(AnnotationHolder holder) { - return new JoinArgument<>(holder); + Join annotation = holder.getAnnotation(); + return new JoinArgument<>(() -> holder.getName(), holder.getFormat(), annotation.separator(), annotation.limit()); } } diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/meta/MarkMeta.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/meta/MarkMeta.java new file mode 100644 index 000000000..9cbf08323 --- /dev/null +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/meta/MarkMeta.java @@ -0,0 +1,17 @@ +package dev.rollczi.litecommands.meta; + +import java.lang.annotation.ElementType; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; +import java.lang.annotation.Target; + +@Target({ElementType.PARAMETER}) +@Retention(RetentionPolicy.RUNTIME) +public @interface MarkMeta { + + String key(); + + String value(); + +} + diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/meta/MarkMetaAnnotationResolver.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/meta/MarkMetaAnnotationResolver.java new file mode 100644 index 000000000..5506e1cca --- /dev/null +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/meta/MarkMetaAnnotationResolver.java @@ -0,0 +1,14 @@ +package dev.rollczi.litecommands.meta; + +import dev.rollczi.litecommands.annotation.processor.AnnotationInvoker; +import dev.rollczi.litecommands.annotation.processor.AnnotationProcessor; + +public class MarkMetaAnnotationResolver implements AnnotationProcessor { + + @Override + public AnnotationInvoker process(AnnotationInvoker invoker) { + return invoker.on(MarkMeta.class, (annotation, metaHolder) -> { + metaHolder.meta().put(MetaKey.of(annotation.key(), String.class), annotation.value()); + }); + } +} diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/permission/Permission.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/permission/Permission.java new file mode 100644 index 000000000..80ab051e3 --- /dev/null +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/permission/Permission.java @@ -0,0 +1,17 @@ +package dev.rollczi.litecommands.permission; + +import java.lang.annotation.ElementType; +import java.lang.annotation.Repeatable; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; +import java.lang.annotation.Target; + +@Target({ ElementType.TYPE, ElementType.METHOD }) +@Retention(RetentionPolicy.RUNTIME) +@Repeatable(Permissions.class) +public @interface Permission { + + String[] value(); + +} + diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/permission/PermissionAnnotationResolver.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/permission/PermissionAnnotationResolver.java new file mode 100644 index 000000000..bbcbcf027 --- /dev/null +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/permission/PermissionAnnotationResolver.java @@ -0,0 +1,18 @@ +package dev.rollczi.litecommands.permission; + +import dev.rollczi.litecommands.annotation.processor.AnnotationInvoker; +import dev.rollczi.litecommands.annotation.processor.AnnotationProcessor; +import dev.rollczi.litecommands.meta.Meta; + +public class PermissionAnnotationResolver implements AnnotationProcessor { + + @Override + public AnnotationInvoker process(AnnotationInvoker invoker) { + return invoker.on(Permission.class, (annotation, metaHolder) -> { + metaHolder.meta().listEditor(Meta.PERMISSIONS) + .addAll(annotation.value()) + .apply(); + }); + } + +} diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/permission/Permissions.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/permission/Permissions.java new file mode 100644 index 000000000..cc671b8ac --- /dev/null +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/permission/Permissions.java @@ -0,0 +1,19 @@ +package dev.rollczi.litecommands.permission; + +import dev.rollczi.litecommands.annotation.processor.AnnotationInvoker; +import dev.rollczi.litecommands.annotation.processor.AnnotationProcessor; +import dev.rollczi.litecommands.meta.Meta; + +import java.lang.annotation.ElementType; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; +import java.lang.annotation.Target; + +@Target({ElementType.TYPE, ElementType.METHOD}) +@Retention(RetentionPolicy.RUNTIME) +public @interface Permissions { + + Permission[] value(); + +} + diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/permission/PermissionsAnnotationResolver.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/permission/PermissionsAnnotationResolver.java new file mode 100644 index 000000000..3cbd24a87 --- /dev/null +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/permission/PermissionsAnnotationResolver.java @@ -0,0 +1,22 @@ +package dev.rollczi.litecommands.permission; + +import dev.rollczi.litecommands.annotation.processor.AnnotationInvoker; +import dev.rollczi.litecommands.annotation.processor.AnnotationProcessor; +import dev.rollczi.litecommands.meta.Meta; + +public class PermissionsAnnotationResolver implements AnnotationProcessor { + + @Override + public AnnotationInvoker process(AnnotationInvoker invoker) { + return invoker.on(Permissions.class, (annotation, metaHolder) -> { + Meta meta = metaHolder.meta(); + + for (Permission permissionAnnotation : annotation.value()) { + meta.listEditor(Meta.PERMISSIONS) + .addAll(permissionAnnotation.value()) + .apply(); + } + }); + } + +} diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/LiteCommand.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/LiteCommand.java index 001d85d1b..1ed05fc52 100644 --- a/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/LiteCommand.java +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/LiteCommand.java @@ -1,120 +1,97 @@ package dev.rollczi.litecommands.programmatic; -import dev.rollczi.litecommands.annotation.AnnotationHolder; -import dev.rollczi.litecommands.argument.Arg; -import dev.rollczi.litecommands.command.Command; -import dev.rollczi.litecommands.command.executor.Execute; -import dev.rollczi.litecommands.context.Context; -import dev.rollczi.litecommands.flag.Flag; -import dev.rollczi.litecommands.join.Join; -import dev.rollczi.litecommands.permission.Permission; +import dev.rollczi.litecommands.argument.Argument; +import dev.rollczi.litecommands.argument.SimpleArgument; +import dev.rollczi.litecommands.command.builder.CommandBuilder; +import dev.rollczi.litecommands.command.executor.CommandExecutor; +import dev.rollczi.litecommands.command.executor.LiteContext; +import dev.rollczi.litecommands.flag.FlagArgument; +import dev.rollczi.litecommands.join.JoinArgument; +import dev.rollczi.litecommands.meta.Meta; +import dev.rollczi.litecommands.meta.MetaKey; +import dev.rollczi.litecommands.requirement.ContextRequirement; +import dev.rollczi.litecommands.scheduler.SchedulerPollType; import dev.rollczi.litecommands.wrapper.WrapFormat; -import org.jetbrains.annotations.Nullable; -import java.lang.annotation.Annotation; -import java.util.HashMap; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.Collections; import java.util.List; -import java.util.Map; import java.util.Optional; -import java.util.Set; import java.util.function.Consumer; public class LiteCommand { - private final Map, Annotation> annotations = new HashMap<>(); - private final Map> requirements = new HashMap<>(); - private Consumer> executor = command -> {}; + protected final String name; + protected final List aliases; + protected final Meta meta = Meta.create(); - public LiteCommand(String name) { - this.name(name); - this.putExecutor(); - } + protected Consumer> executor = liteContext -> {}; + protected final List> arguments = new ArrayList<>(); + protected final List> contextRequirements = new ArrayList<>(); - public LiteCommand(String name, String... aliases) { - this.name(name); - this.aliases(aliases); - this.putExecutor(); - } + protected final List> subCommands = new ArrayList<>(); - @Nullable - @SuppressWarnings("unchecked") - A getAnnotation(Class annotationType) { - return (A) annotations.get(annotationType); + public LiteCommand(String name, List aliases) { + this.name = name; + this.aliases = aliases; } - @SuppressWarnings("unchecked") - List> getRequirements(Class annotationType) { - return requirements.values().stream() - .filter(holder -> holder.getAnnotation().annotationType().equals(annotationType)) - .map(holder -> (AnnotationHolder) holder) - .toList(); + public LiteCommand(String name) { + this(name, Collections.emptyList()); } - Set getRequirements() { - return requirements.keySet(); + public LiteCommand(String name, String... aliases) { + this(name, Arrays.asList(aliases)); } - private LiteCommand putAnnotation(Annotation annotation) { - annotations.put(annotation.annotationType(), annotation); + public LiteCommand argument(String name, Class type) { + this.arguments.add(new SimpleArgument<>(() -> name, WrapFormat.notWrapped(type))); return this; } - public LiteCommand name(String name) { - Command.Mock command = getAnnotation(Command.Mock.class); - String[] aliases = new String[0]; - - if (command != null) { - aliases = command.aliases(); - } - - return this.putAnnotation(new Command.Mock(name, aliases)); - } - - public LiteCommand aliases(String... aliases) { - Command.Mock command = getAnnotation(Command.Mock.class); - String name = ""; - - if (command != null) { - name = command.name(); - } - - return this.putAnnotation(new Command.Mock(name, aliases)); - } - - private LiteCommand putExecutor() { - return this.putAnnotation(new Execute.Mock("", new String[0])); + public LiteCommand argument(Argument argument) { + this.arguments.add(argument); + return this; } - public LiteCommand permission(String... permissions) { - return this.putAnnotation(new Permission.Mock(permissions)); + public LiteCommand argumentOptional(String name, Class type) { + this.arguments.add(new SimpleArgument<>(() -> name, WrapFormat.of(type, Optional.class))); + return this; } - public LiteCommand argument(String name, Class type) { - return this.argument(name, WrapFormat.notWrapped(type)); + public LiteCommand argumentFlag(String name) { + this.arguments.add(new FlagArgument(() -> name, WrapFormat.notWrapped(boolean.class))); + return this; } - public LiteCommand argumentOptional(String name, Class type) { - return this.argument(name, WrapFormat.of(type, Optional.class)); + public LiteCommand argumentJoin(String name) { + this.arguments.add(new JoinArgument<>(() -> name, WrapFormat.notWrapped(String.class))); + return this; } - public LiteCommand argument(String name, WrapFormat wrapFormat) { - return this.requirement(new Arg.Mock(name), name, wrapFormat); + public LiteCommand argumentJoin(String name, String separator, int limit) { + this.arguments.add(new JoinArgument<>(() -> name, WrapFormat.notWrapped(String.class), separator, limit)); + return this; } - public LiteCommand argumentFlag(String name) { - return this.requirement(new Flag.Mock(name), name, WrapFormat.notWrapped(Boolean.class)); + public LiteCommand context(String name, Class type) { + this.contextRequirements.add(ContextRequirement.of(() -> name, type)); + return this; } - public LiteCommand argumentJoin(String name) { - return this.requirement(new Join.Mock(" ", Integer.MAX_VALUE), name, WrapFormat.notWrapped(String.class)); + public LiteCommand permissions(String... permissions) { + this.meta.listEditor(Meta.PERMISSIONS).addAll(permissions).apply(); + return this; } - public LiteCommand argumentJoin(String name, String separator, int limit) { - return this.requirement(new Join.Mock(separator, limit), name, WrapFormat.notWrapped(String.class)); + public LiteCommand async() { + return this.meta(Meta.POLL_TYPE, SchedulerPollType.ASYNC); } - public LiteCommand context(String name, Class type) { - return this.requirement(new Context.Mock(), name, WrapFormat.notWrapped(type)); + public LiteCommand meta(MetaKey key, T value) { + this.meta.put(key, value); + return this; } public LiteCommand onExecute(Consumer> executor) { @@ -122,15 +99,33 @@ public LiteCommand onExecute(Consumer> executor) { return this; } - private LiteCommand requirement(A annotation, String name, WrapFormat wrapFormat) { - AnnotationHolder holder = AnnotationHolder.of(annotation, wrapFormat, () -> name); + protected void execute(LiteContext liteContext) { + this.executor.accept(liteContext); + } - this.requirements.put(name, holder); - return this.putAnnotation(annotation); + @SafeVarargs + public final LiteCommand subCommands(LiteCommand... subCommands) { + this.subCommands.addAll(Arrays.asList(subCommands)); + return this; } - protected void execute(LiteContext liteContext) { - this.executor.accept(liteContext); + CommandBuilder toRoute() { + CommandBuilder builder = CommandBuilder.create() + .routeName(name) + .routeAliases(aliases) + .applyMeta(meta -> meta.apply(this.meta)) + .appendExecutor(root -> CommandExecutor.builder(root) + .executor(liteContext -> execute(liteContext)) + .arguments(arguments) + .contextRequirements(contextRequirements) + .build() + ); + + for (LiteCommand subCommand : subCommands) { + builder.appendChild(subCommand.toRoute()); + } + + return builder; } } diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/LiteCommandsProgrammatic.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/LiteCommandsProgrammatic.java index 0f0358865..ccc5296c4 100644 --- a/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/LiteCommandsProgrammatic.java +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/LiteCommandsProgrammatic.java @@ -1,9 +1,9 @@ package dev.rollczi.litecommands.programmatic; -import dev.rollczi.litecommands.annotation.processor.AnnotationProcessorService; import dev.rollczi.litecommands.builder.LiteCommandsInternalBuilderApi; import dev.rollczi.litecommands.builder.LiteCommandsProvider; import dev.rollczi.litecommands.command.builder.CommandBuilder; +import dev.rollczi.litecommands.command.builder.CommandBuilderProvider; import java.util.ArrayList; import java.util.Arrays; @@ -19,19 +19,6 @@ public LiteCommandsProgrammatic(Collection> commands) { this.commands.addAll(commands); } - @Override - public List> provide(LiteCommandsInternalBuilderApi builder) { - builder.getWrapperRegistry(); - AnnotationProcessorService annotationProcessorService = builder.getAnnotationProcessorRegistry(); - - ProgrammaticSourceProcessor processor = new ProgrammaticSourceProcessor<>(annotationProcessorService); - - return commands.stream() - .map(liteCommand -> processor.processBuilder(liteCommand)) - .map(senderCommandBuilder -> builder.getEditorService().edit(senderCommandBuilder)) - .collect(Collectors.toList()); - } - @SafeVarargs public static LiteCommandsProgrammatic of(LiteCommand... commands) { return new LiteCommandsProgrammatic<>(Arrays.asList(commands)); @@ -41,4 +28,11 @@ public static LiteCommandsProgrammatic of(Collection(commands); } + @Override + public List> provide(LiteCommandsInternalBuilderApi builder) { + return commands.stream() + .map(liteCommand -> liteCommand.toRoute()) + .collect(Collectors.toList()); + } + } \ No newline at end of file diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/ProgrammaticCommandExecutor.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/ProgrammaticCommandExecutor.java deleted file mode 100644 index 8cf2ed6b8..000000000 --- a/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/ProgrammaticCommandExecutor.java +++ /dev/null @@ -1,63 +0,0 @@ -package dev.rollczi.litecommands.programmatic; - -import dev.rollczi.litecommands.command.CommandRoute; -import dev.rollczi.litecommands.command.executor.CommandExecuteResult; -import dev.rollczi.litecommands.command.executor.CommandExecutor; -import dev.rollczi.litecommands.command.executor.CommandExecutorMatchResult; -import dev.rollczi.litecommands.meta.Meta; -import dev.rollczi.litecommands.meta.MetaHolder; -import dev.rollczi.litecommands.requirement.Requirement; -import dev.rollczi.litecommands.requirement.RequirementsResult; -import org.jetbrains.annotations.Nullable; - -import java.util.Collections; -import java.util.List; - -class ProgrammaticCommandExecutor implements CommandExecutor { - - private final CommandRoute parent; - private final List> requirements; - private final LiteCommand liteCommand; - private final Meta meta = Meta.create(); - - public ProgrammaticCommandExecutor(CommandRoute parent, List> requirements, LiteCommand liteCommand) { - this.parent = parent; - this.requirements = requirements; - this.liteCommand = liteCommand; - } - - @Override - public CommandRoute getParent() { - return this.parent; - } - - @Override - public List> getRequirements() { - return Collections.unmodifiableList(this.requirements); - } - - @Override - public CommandExecutorMatchResult match(RequirementsResult result) { - for (String requirement : liteCommand.getRequirements()) { - if (!result.has(requirement)) { - return CommandExecutorMatchResult.failed(new IllegalStateException("Missing requirement " + requirement)); - } - } - - return CommandExecutorMatchResult.success(() -> { - liteCommand.execute(new LiteContext<>(result)); - return CommandExecuteResult.success(this, null); - }); - } - - @Override - public Meta meta() { - return this.meta; - } - - @Override - public @Nullable MetaHolder parentMeta() { - return this.parent; - } - -} diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/ProgrammaticExecutorStructureInvoker.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/ProgrammaticExecutorStructureInvoker.java deleted file mode 100644 index 5f34820b2..000000000 --- a/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/ProgrammaticExecutorStructureInvoker.java +++ /dev/null @@ -1,40 +0,0 @@ -package dev.rollczi.litecommands.programmatic; - -import dev.rollczi.litecommands.annotation.processor.AnnotationInvoker; -import dev.rollczi.litecommands.annotation.processor.AnnotationProcessor; -import dev.rollczi.litecommands.command.builder.CommandBuilder; -import dev.rollczi.litecommands.command.builder.CommandBuilderExecutor; - -import java.lang.annotation.Annotation; - -class ProgrammaticExecutorStructureInvoker implements AnnotationInvoker { - - private final LiteCommand liteCommand; - private CommandBuilder commandBuilder; - private final CommandBuilderExecutor executorBuilder; - - ProgrammaticExecutorStructureInvoker(LiteCommand liteCommand, CommandBuilder commandBuilder, CommandBuilderExecutor executorBuilder) { - this.liteCommand = liteCommand; - this.commandBuilder = commandBuilder; - this.executorBuilder = executorBuilder; - } - - @Override - public AnnotationInvoker onExecutorStructure(Class annotationType, AnnotationProcessor.StructureExecutorListener listener) { - A annotation = liteCommand.getAnnotation(annotationType); - - if (annotation == null) { - return this; - } - - executorBuilder.setExecutorFactory((parent, requirements) -> new ProgrammaticCommandExecutor<>(parent, requirements, liteCommand)); - commandBuilder = listener.call(annotation, commandBuilder, executorBuilder); - return this; - } - - @Override - public CommandBuilder getResult() { - return commandBuilder; - } - -} diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/ProgrammaticRequirementInvoker.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/ProgrammaticRequirementInvoker.java deleted file mode 100644 index 80fb19cd0..000000000 --- a/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/ProgrammaticRequirementInvoker.java +++ /dev/null @@ -1,38 +0,0 @@ -package dev.rollczi.litecommands.programmatic; - -import dev.rollczi.litecommands.annotation.AnnotationHolder; -import dev.rollczi.litecommands.annotation.processor.AnnotationInvoker; -import dev.rollczi.litecommands.annotation.processor.AnnotationProcessor; -import dev.rollczi.litecommands.command.builder.CommandBuilder; -import dev.rollczi.litecommands.command.builder.CommandBuilderExecutor; - -import java.lang.annotation.Annotation; - -class ProgrammaticRequirementInvoker implements AnnotationInvoker { - - private final LiteCommand liteCommand; - private CommandBuilder commandBuilder; - private final CommandBuilderExecutor executorBuilder; - - public ProgrammaticRequirementInvoker(LiteCommand liteCommand, CommandBuilder commandBuilder, CommandBuilderExecutor executorBuilder) { - this.liteCommand = liteCommand; - this.commandBuilder = commandBuilder; - this.executorBuilder = executorBuilder; - } - - @Override - public AnnotationInvoker onRequirement(Class annotationType, AnnotationProcessor.RequirementListener listener) { - for (AnnotationHolder requirement : liteCommand.getRequirements(annotationType)) { - commandBuilder = listener.call(requirement, commandBuilder, executorBuilder); - } - - return this; - } - - @Override - public CommandBuilder getResult() { - return commandBuilder; - } - -} - diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/ProgrammaticSourceProcessor.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/ProgrammaticSourceProcessor.java deleted file mode 100644 index 6a2d3e4dd..000000000 --- a/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/ProgrammaticSourceProcessor.java +++ /dev/null @@ -1,39 +0,0 @@ -package dev.rollczi.litecommands.programmatic; - -import dev.rollczi.litecommands.annotation.processor.SourceProcessor; -import dev.rollczi.litecommands.annotation.processor.AnnotationProcessorService; -import dev.rollczi.litecommands.command.builder.CommandBuilder; -import dev.rollczi.litecommands.command.builder.CommandBuilderExecutor; - -class ProgrammaticSourceProcessor implements SourceProcessor> { - - private final AnnotationProcessorService annotationProcessorService; - - public ProgrammaticSourceProcessor( - AnnotationProcessorService annotationProcessorService) { - this.annotationProcessorService = annotationProcessorService; - } - - @Override - public CommandBuilder processBuilder(LiteCommand source) { - CommandBuilder context = CommandBuilder.create(); - - ProgrammaticStructureInvoker classInvoker = new ProgrammaticStructureInvoker<>(source, context); - context = annotationProcessorService.process(classInvoker); - - CommandBuilderExecutor executorBuilder = new CommandBuilderExecutor<>(context); - ProgrammaticExecutorStructureInvoker methodInvoker = new ProgrammaticExecutorStructureInvoker<>(source, context, executorBuilder); - - context = annotationProcessorService.process(methodInvoker); - - if (!executorBuilder.buildable()) { - return context; - } - - ProgrammaticRequirementInvoker requirementInvoker = new ProgrammaticRequirementInvoker<>(source, context, executorBuilder); - context = annotationProcessorService.process(requirementInvoker); //TODO zrobić return value flow - - return context; - } - -} diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/ProgrammaticStructureInvoker.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/ProgrammaticStructureInvoker.java deleted file mode 100644 index 22e43c1db..000000000 --- a/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/ProgrammaticStructureInvoker.java +++ /dev/null @@ -1,48 +0,0 @@ -package dev.rollczi.litecommands.programmatic; - -import dev.rollczi.litecommands.annotation.processor.AnnotationInvoker; -import dev.rollczi.litecommands.annotation.processor.AnnotationProcessor; -import dev.rollczi.litecommands.command.builder.CommandBuilder; - -import java.lang.annotation.Annotation; - -class ProgrammaticStructureInvoker implements AnnotationInvoker { - - private final LiteCommand liteCommand; - private CommandBuilder commandBuilder; - - public ProgrammaticStructureInvoker(LiteCommand liteCommand, CommandBuilder commandBuilder) { - this.liteCommand = liteCommand; - this.commandBuilder = commandBuilder; - } - - @Override - public AnnotationInvoker on(Class annotationType, AnnotationProcessor.Listener listener) { - A annotation = liteCommand.getAnnotation(annotationType); - - if (annotation == null) { - return this; - } - - listener.call(annotation, commandBuilder); - return this; - } - - @Override - public AnnotationInvoker onStructure(Class annotationType, AnnotationProcessor.StructureListener listener) { - A annotation = liteCommand.getAnnotation(annotationType); - - if (annotation == null) { - return this; - } - - commandBuilder = listener.call(annotation, commandBuilder); - return this; - } - - @Override - public CommandBuilder getResult() { - return commandBuilder; - } - -} diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/validator/Validate.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/validator/Validate.java new file mode 100644 index 000000000..e7e5bbbd5 --- /dev/null +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/validator/Validate.java @@ -0,0 +1,15 @@ +package dev.rollczi.litecommands.validator; + +import java.lang.annotation.ElementType; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; +import java.lang.annotation.Target; + +@Target({ElementType.TYPE, ElementType.METHOD}) +@Retention(RetentionPolicy.RUNTIME) +public @interface Validate { + + Class>[] value(); + +} + diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/validator/ValidateAnnotationResolver.java b/litecommands-core-annotations/src/dev/rollczi/litecommands/validator/ValidateAnnotationResolver.java new file mode 100644 index 000000000..18f515a11 --- /dev/null +++ b/litecommands-core-annotations/src/dev/rollczi/litecommands/validator/ValidateAnnotationResolver.java @@ -0,0 +1,17 @@ +package dev.rollczi.litecommands.validator; + +import dev.rollczi.litecommands.annotation.processor.AnnotationInvoker; +import dev.rollczi.litecommands.annotation.processor.AnnotationProcessor; +import dev.rollczi.litecommands.meta.Meta; + +public class ValidateAnnotationResolver implements AnnotationProcessor { + + @Override + public AnnotationInvoker process(AnnotationInvoker invoker) { + return invoker.on(Validate.class, (annotation, metaHolder) -> { + metaHolder.meta().listEditor(Meta.VALIDATORS) + .addAll(annotation.value()) + .apply(); + }); + } +} diff --git a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/ExampleUnitTest.java b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/ExampleUnitTest.java index 9ed7508ac..e5de26109 100644 --- a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/ExampleUnitTest.java +++ b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/ExampleUnitTest.java @@ -3,7 +3,7 @@ import dev.rollczi.litecommands.argument.Arg; import dev.rollczi.litecommands.command.Command; import dev.rollczi.litecommands.context.Context; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import dev.rollczi.litecommands.scope.Scope; import dev.rollczi.litecommands.unit.TestSender; import org.junit.jupiter.api.Test; diff --git a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/argument/ArgumentResolverAnnotationTest.java b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/argument/ArgumentResolverAnnotationTest.java index 3a41d4ce9..58af709ea 100644 --- a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/argument/ArgumentResolverAnnotationTest.java +++ b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/argument/ArgumentResolverAnnotationTest.java @@ -3,14 +3,13 @@ import dev.rollczi.litecommands.annotations.LiteConfig; import dev.rollczi.litecommands.annotations.LiteTestSpec; import dev.rollczi.litecommands.argument.Arg; +import dev.rollczi.litecommands.argument.Argument; import dev.rollczi.litecommands.command.Command; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import dev.rollczi.litecommands.suggestion.SuggestionResult; import dev.rollczi.litecommands.command.executor.CommandExecutor; import dev.rollczi.litecommands.command.CommandManager; import dev.rollczi.litecommands.command.CommandRoute; -import dev.rollczi.litecommands.requirement.ArgumentRequirement; -import dev.rollczi.litecommands.requirement.Requirement; import dev.rollczi.litecommands.unit.TestSender; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; @@ -19,7 +18,6 @@ import java.util.List; import static org.junit.jupiter.api.Assertions.assertEquals; -import static org.junit.jupiter.api.Assertions.assertInstanceOf; class ArgumentResolverAnnotationTest extends LiteTestSpec { @@ -45,15 +43,15 @@ void test() { .stream().findFirst() .orElseThrow(() -> new RuntimeException("Executor not found")); - List> requirements = executor.getRequirements(); + List> requirements = executor.getArguments(); - ArgumentRequirement first = assertInstanceOf(ArgumentRequirement.class, requirements.get(0)); - ArgumentRequirement second = assertInstanceOf(ArgumentRequirement.class, requirements.get(1)); - ArgumentRequirement third = assertInstanceOf(ArgumentRequirement.class, requirements.get(2)); + Argument first = requirements.get(0); + Argument second = requirements.get(1); + Argument third = requirements.get(2); - assertEquals("arg0", first.getArgument().getName()); - assertEquals("arg1", second.getArgument().getName()); // @ArgumentResolverInfo deprecated - assertEquals("other", third.getArgument().getName()); + assertEquals("arg0", first.getName()); + assertEquals("arg1", second.getName()); // @ArgumentResolverInfo deprecated + assertEquals("other", third.getName()); } } diff --git a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/argument/MultiArgumentsTest.java b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/argument/MultiArgumentsTest.java index 8a2094414..9ef34aa75 100644 --- a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/argument/MultiArgumentsTest.java +++ b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/argument/MultiArgumentsTest.java @@ -3,7 +3,7 @@ import dev.rollczi.litecommands.annotations.LiteConfig; import dev.rollczi.litecommands.annotations.LiteTestSpec; import dev.rollczi.litecommands.argument.Arg; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import dev.rollczi.litecommands.command.Command; import dev.rollczi.litecommands.argument.Argument; import dev.rollczi.litecommands.argument.parser.ParseResult; diff --git a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/argument/SimpleArgumentTest.java b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/argument/SimpleArgumentTest.java deleted file mode 100644 index 31cfde3d7..000000000 --- a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/argument/SimpleArgumentTest.java +++ /dev/null @@ -1,58 +0,0 @@ -package dev.rollczi.litecommands.annotations.argument; - -import dev.rollczi.litecommands.annotation.AnnotationHolder; -import dev.rollczi.litecommands.argument.Arg; -import dev.rollczi.litecommands.argument.SimpleArgument; -import dev.rollczi.litecommands.wrapper.WrapFormat; -import org.junit.jupiter.api.BeforeAll; -import org.junit.jupiter.api.Test; - -import java.lang.reflect.Method; -import java.lang.reflect.Parameter; - -import static org.junit.jupiter.api.Assertions.assertEquals; -import static org.junit.jupiter.api.Assertions.assertFalse; -import static org.junit.jupiter.api.Assertions.assertNotNull; - -class SimpleArgumentTest { - - static class TestClass { - void testMethod(@Arg String arg0) {} - } - - private static SimpleArgument simpleArgument; - - @BeforeAll - static void setUp() throws NoSuchMethodException { - Method method = TestClass.class.getDeclaredMethod("testMethod", String.class); - Parameter parameter = method.getParameters()[0]; - - simpleArgument = new SimpleArgument( - AnnotationHolder.of( - parameter.getAnnotation(Arg.class), - WrapFormat.notWrapped(String.class), - () -> parameter.getName() - ) - ) {}; - } - - @Test - void testGetName() { - assertEquals("arg0", simpleArgument.getName()); - } - - @Test - void testGetAnnotation() { - assertNotNull(simpleArgument.getAnnotation()); - } - - @Test - void testGetWrapperFormat() { - WrapFormat wrapFormat = simpleArgument.getWrapperFormat(); - - assertNotNull(wrapFormat); - assertEquals(String.class, wrapFormat.getParsedType()); - assertFalse(wrapFormat.hasOutType()); - } - -} \ No newline at end of file diff --git a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/argument/flag/FlagArgumentTest.java b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/argument/flag/FlagArgumentTest.java index 4d599f823..d00d5cc6d 100644 --- a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/argument/flag/FlagArgumentTest.java +++ b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/argument/flag/FlagArgumentTest.java @@ -3,7 +3,7 @@ import dev.rollczi.litecommands.annotations.LiteTestSpec; import dev.rollczi.litecommands.argument.Arg; import dev.rollczi.litecommands.command.Command; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import dev.rollczi.litecommands.invalidusage.InvalidUsage; import dev.rollczi.litecommands.flag.Flag; import org.junit.jupiter.api.DisplayName; diff --git a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/argument/join/JoinArgumentTest.java b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/argument/join/JoinArgumentTest.java index a693dd894..b19a21bbf 100644 --- a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/argument/join/JoinArgumentTest.java +++ b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/argument/join/JoinArgumentTest.java @@ -3,7 +3,7 @@ import dev.rollczi.litecommands.annotations.LiteTestSpec; import dev.rollczi.litecommands.join.Join; import dev.rollczi.litecommands.command.Command; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import org.junit.jupiter.api.Test; class JoinArgumentTest extends LiteTestSpec { diff --git a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/async/AsyncCommandTest.java b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/async/AsyncCommandTest.java index 45c985ec1..49447ff27 100644 --- a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/async/AsyncCommandTest.java +++ b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/async/AsyncCommandTest.java @@ -6,7 +6,7 @@ import dev.rollczi.litecommands.command.Command; import dev.rollczi.litecommands.async.Async; import dev.rollczi.litecommands.context.Context; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import dev.rollczi.litecommands.argument.Argument; import dev.rollczi.litecommands.argument.parser.ParseResult; import dev.rollczi.litecommands.argument.resolver.ArgumentResolver; @@ -26,28 +26,34 @@ class AsyncCommandTest extends LiteTestSpec { static LiteConfig config = builder -> builder - .scheduler(new SchedulerExecutorPoolImpl("test", 1)) - .context(Date.class, invocation -> ContextResult.ok(() -> { - try { - Thread.sleep(800); - } - catch (InterruptedException e) { - throw new RuntimeException(e); - } - - return new Date(); - })) - .argument(SomeClass.class, new ThrowingArgumentResolver()); - - static class SomeClass {} + .scheduler(new SchedulerExecutorPoolImpl("test", 1)) + .context(Date.class, invocation -> ContextResult.ok(() -> { + try { + Thread.sleep(800); + } catch (InterruptedException e) { + throw new RuntimeException(e); + } + + return new Date(); + })) + .argumentParser(String.class, new StringArgumentResolver()) + .argument(SomeClass.class, new ThrowingArgumentResolver()); + + static class SomeClass { + } static class ThrowingArgumentResolver extends ArgumentResolver { - @Override protected ParseResult parse(Invocation invocation, Argument context, String argument) { throw new IllegalArgumentException(); } + } + static class StringArgumentResolver extends ArgumentResolver { + @Override + protected ParseResult parse(Invocation invocation, Argument context, String argument) { + return ParseResult.success(Thread.currentThread().getName()); + } } @Command(name = "test") @@ -66,13 +72,13 @@ public String testAsync() { @Execute(name = "async-args") public String testAsyncArgs(@Context Date date, @Arg String first, @Async @Arg String second) { - return Thread.currentThread().getName(); + return Thread.currentThread().getName() + " args [first=" + first + ", second=" + second + "]"; } @Async @Execute(name = "async-args-and-method") - public String testAsyncArgs2(@Context Date date, @Arg String first, @Async @Arg String second) { - return Thread.currentThread().getName(); + public String testAsyncArgs2(@Context Date date, @Async @Arg String first, @Arg String second) { + return Thread.currentThread().getName() + " args [first=" + first + ", second=" + second + "]"; } @Execute(name = "async-args-and-method-throwing") @@ -85,7 +91,7 @@ public String testAsyncArgs3(@Async @Arg SomeClass someClass) { @Test void testSync() { platform.execute("test sync") - .assertSuccess("scheduler-test-main"); + .assertSuccess("scheduler-test-main"); } @Test @@ -103,7 +109,7 @@ void testAsyncArgs() { .until(() -> result.isDone()); result.join() - .assertSuccess("scheduler-test-main"); + .assertSuccess("scheduler-test-main args [first=scheduler-test-main, second=scheduler-test-async-0]"); } @Test @@ -115,7 +121,7 @@ void testAsyncArgsAndMethod() { .until(() -> result.isDone()); result.join() - .assertSuccess("scheduler-test-async-0"); + .assertSuccess("scheduler-test-async-0 args [first=scheduler-test-async-0, second=scheduler-test-main]"); } @Test diff --git a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/dsl/ProgrammaticApiTest.java b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/dsl/ProgrammaticApiTest.java index 9757ee118..c06a3988c 100644 --- a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/dsl/ProgrammaticApiTest.java +++ b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/dsl/ProgrammaticApiTest.java @@ -21,7 +21,7 @@ public class ProgrammaticApiTest { TestPlatform testPlatform = LiteCommandsTestFactory.startPlatform(builder -> builder.commands(LiteCommandsProgrammatic.of( new LiteCommand("ban") - .permission(PERMISSION) + .permissions(PERMISSION) .argument("player", String.class) .onExecute(context -> { TestSender sender = context.invocation().sender(); diff --git a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/editor/AnnotationEditorServiceTest.java b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/editor/AnnotationEditorServiceTest.java index 71eede91e..b85a0397f 100644 --- a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/editor/AnnotationEditorServiceTest.java +++ b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/editor/AnnotationEditorServiceTest.java @@ -1,10 +1,10 @@ package dev.rollczi.litecommands.annotations.editor; import dev.rollczi.litecommands.command.Command; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import dev.rollczi.litecommands.command.builder.CommandBuilder; -import dev.rollczi.litecommands.editor.AnnotationEditorService; -import dev.rollczi.litecommands.editor.Edit; +import dev.rollczi.litecommands.edit.AnnotationEditorService; +import dev.rollczi.litecommands.edit.Edit; import dev.rollczi.litecommands.unit.TestSender; import org.junit.jupiter.api.Test; diff --git a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/exception/ExceptionHandleTest.java b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/exception/ExceptionHandleTest.java index 6c475ff54..87399a50c 100644 --- a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/exception/ExceptionHandleTest.java +++ b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/exception/ExceptionHandleTest.java @@ -3,7 +3,7 @@ import dev.rollczi.litecommands.annotations.LiteConfig; import dev.rollczi.litecommands.annotations.LiteTestSpec; import dev.rollczi.litecommands.command.Command; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; diff --git a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/invalid/InvalidHandlerTest.java b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/invalid/InvalidHandlerTest.java index a1eb11d82..23eb6fc43 100644 --- a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/invalid/InvalidHandlerTest.java +++ b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/invalid/InvalidHandlerTest.java @@ -4,7 +4,7 @@ import dev.rollczi.litecommands.annotations.LiteTestSpec; import dev.rollczi.litecommands.argument.Arg; import dev.rollczi.litecommands.command.Command; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import dev.rollczi.litecommands.invalidusage.InvalidUsage; import dev.rollczi.litecommands.unit.TestSender; import org.junit.jupiter.api.Test; diff --git a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/permission/ChildCommandPermissionHandleTest.java b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/permission/ChildCommandPermissionHandleTest.java index 7cbef7e76..6689e2677 100644 --- a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/permission/ChildCommandPermissionHandleTest.java +++ b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/permission/ChildCommandPermissionHandleTest.java @@ -2,7 +2,7 @@ import dev.rollczi.litecommands.annotations.LiteTestSpec; import dev.rollczi.litecommands.argument.Arg; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import dev.rollczi.litecommands.command.Command; import dev.rollczi.litecommands.permission.MissingPermissions; import dev.rollczi.litecommands.permission.Permission; diff --git a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/permission/DefaultMissingPermissionResultHandlerTest.java b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/permission/DefaultMissingPermissionResultHandlerTest.java index 2408e42f0..f1b1e19ab 100644 --- a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/permission/DefaultMissingPermissionResultHandlerTest.java +++ b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/permission/DefaultMissingPermissionResultHandlerTest.java @@ -3,7 +3,7 @@ import dev.rollczi.litecommands.annotations.LiteConfig; import dev.rollczi.litecommands.annotations.LiteTestSpec; import dev.rollczi.litecommands.command.Command; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import dev.rollczi.litecommands.message.LiteMessages; import dev.rollczi.litecommands.message.Message; import dev.rollczi.litecommands.permission.Permission; diff --git a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/permission/MissingPermissionResultHandlerTest.java b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/permission/MissingPermissionResultHandlerTest.java index 0624625a5..d2ba1aec5 100644 --- a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/permission/MissingPermissionResultHandlerTest.java +++ b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/permission/MissingPermissionResultHandlerTest.java @@ -4,7 +4,7 @@ import dev.rollczi.litecommands.annotations.LiteTestSpec; import dev.rollczi.litecommands.argument.Arg; import dev.rollczi.litecommands.command.Command; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import dev.rollczi.litecommands.permission.Permission; import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.Test; diff --git a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/permission/PermissionAnnotationTest.java b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/permission/PermissionAnnotationTest.java index 1a0824943..36e125ce5 100644 --- a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/permission/PermissionAnnotationTest.java +++ b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/permission/PermissionAnnotationTest.java @@ -1,7 +1,7 @@ package dev.rollczi.litecommands.annotations.permission; import dev.rollczi.litecommands.annotations.LiteTestSpec; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import dev.rollczi.litecommands.permission.MissingPermissions; import dev.rollczi.litecommands.permission.Permission; import org.junit.jupiter.api.Test; diff --git a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/route/RootCommandTest.java b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/route/RootCommandTest.java index 13a21545d..35540a983 100644 --- a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/route/RootCommandTest.java +++ b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/route/RootCommandTest.java @@ -3,7 +3,7 @@ import dev.rollczi.litecommands.annotations.LiteTestSpec; import dev.rollczi.litecommands.argument.Arg; import dev.rollczi.litecommands.command.RootCommand; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import dev.rollczi.litecommands.permission.Permission; import org.junit.jupiter.api.Test; diff --git a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/schematic/SchematicTest.java b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/schematic/SchematicTest.java index e1c368f9a..f1c64606d 100644 --- a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/schematic/SchematicTest.java +++ b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/schematic/SchematicTest.java @@ -5,7 +5,7 @@ import dev.rollczi.litecommands.flag.Flag; import dev.rollczi.litecommands.async.Async; import dev.rollczi.litecommands.command.Command; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import dev.rollczi.litecommands.permission.Permission; import dev.rollczi.litecommands.invalidusage.InvalidUsage; import dev.rollczi.litecommands.unit.TestPlatformSender; diff --git a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/validator/CustomValidatorTest.java b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/validator/CustomValidatorTest.java index a3844f698..51395caef 100644 --- a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/validator/CustomValidatorTest.java +++ b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/validator/CustomValidatorTest.java @@ -2,7 +2,7 @@ import dev.rollczi.litecommands.annotations.LiteConfig; import dev.rollczi.litecommands.annotations.LiteTestSpec; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import dev.rollczi.litecommands.command.Command; import dev.rollczi.litecommands.flow.Flow; import dev.rollczi.litecommands.invocation.Invocation; diff --git a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/wrapper/OptionalWrapperTest.java b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/wrapper/OptionalWrapperTest.java index 704a211fa..01dbeb08f 100644 --- a/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/wrapper/OptionalWrapperTest.java +++ b/litecommands-core-annotations/test/dev/rollczi/litecommands/annotations/wrapper/OptionalWrapperTest.java @@ -2,7 +2,7 @@ import dev.rollczi.litecommands.annotations.LiteTestSpec; import dev.rollczi.litecommands.argument.Arg; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import dev.rollczi.litecommands.command.Command; import org.junit.jupiter.api.Test; diff --git a/litecommands-core/src/dev/rollczi/litecommands/LiteCommandsFactory.java b/litecommands-core/src/dev/rollczi/litecommands/LiteCommandsFactory.java index b93231dbe..3bb834642 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/LiteCommandsFactory.java +++ b/litecommands-core/src/dev/rollczi/litecommands/LiteCommandsFactory.java @@ -1,41 +1,23 @@ package dev.rollczi.litecommands; -import dev.rollczi.litecommands.argument.parser.ParserRegistry; import dev.rollczi.litecommands.argument.resolver.std.NumberArgumentResolver; import dev.rollczi.litecommands.argument.resolver.std.StringArgumentResolver; import dev.rollczi.litecommands.builder.LiteCommandsBaseBuilder; import dev.rollczi.litecommands.builder.LiteCommandsBuilder; -import dev.rollczi.litecommands.context.ContextRegistry; import dev.rollczi.litecommands.context.ContextResult; +import dev.rollczi.litecommands.flag.FlagArgument; import dev.rollczi.litecommands.invocation.Invocation; +import dev.rollczi.litecommands.join.JoinArgument; import dev.rollczi.litecommands.permission.MissingPermissionResultHandler; import dev.rollczi.litecommands.permission.MissingPermissionValidator; import dev.rollczi.litecommands.permission.MissingPermissions; import dev.rollczi.litecommands.platform.Platform; import dev.rollczi.litecommands.platform.PlatformSender; import dev.rollczi.litecommands.platform.PlatformSettings; -import dev.rollczi.litecommands.requirement.RequirementProcessor; -import dev.rollczi.litecommands.argument.Arg; -import dev.rollczi.litecommands.argument.ArgArgumentFactory; -import dev.rollczi.litecommands.async.AsyncAnnotationResolver; -import dev.rollczi.litecommands.command.CommandAnnotationProcessor; -import dev.rollczi.litecommands.command.RootCommandAnnotationProcessor; -import dev.rollczi.litecommands.description.DescriptionAnnotationResolver; -import dev.rollczi.litecommands.command.executor.ExecuteAnnotationResolver; -import dev.rollczi.litecommands.flag.Flag; -import dev.rollczi.litecommands.flag.FlagArgumentFactory; import dev.rollczi.litecommands.flag.FlagArgumentResolver; -import dev.rollczi.litecommands.join.Join; -import dev.rollczi.litecommands.join.JoinArgumentFactory; import dev.rollczi.litecommands.join.JoinArgumentResolver; -import dev.rollczi.litecommands.meta.MarkMeta; -import dev.rollczi.litecommands.permission.Permission; -import dev.rollczi.litecommands.permission.Permissions; -import dev.rollczi.litecommands.validator.Validate; -import dev.rollczi.litecommands.context.Context; import dev.rollczi.litecommands.scheduler.Scheduler; import dev.rollczi.litecommands.scope.Scope; -import dev.rollczi.litecommands.wrapper.WrapperRegistry; import dev.rollczi.litecommands.wrapper.std.CompletableFutureWrapper; import dev.rollczi.litecommands.wrapper.std.OptionWrapper; import dev.rollczi.litecommands.wrapper.std.OptionalWrapper; @@ -47,9 +29,6 @@ private LiteCommandsFactory() { public static > LiteCommandsBuilder builder(Class senderClass, Platform platform) { return new LiteCommandsBaseBuilder(senderClass, platform).selfProcessor((builder, pattern) -> { - WrapperRegistry wrapperRegistry = pattern.getWrapperRegistry(); - ParserRegistry parserRegistry = pattern.getParserRegistry(); - ContextRegistry contextRegistry = pattern.getContextRegistry(); Scheduler scheduler = pattern.getScheduler(); builder @@ -74,23 +53,9 @@ public static ()) - .argument(boolean.class, Flag.ARGUMENT_KEY, new FlagArgumentResolver<>()) - .argument(Boolean.class, Flag.ARGUMENT_KEY, new FlagArgumentResolver<>()) - - .annotationProcessor(new CommandAnnotationProcessor<>()) - .annotationProcessor(new RootCommandAnnotationProcessor<>()) - .annotationProcessor(new MarkMeta.AnnotationResolver<>()) - .annotationProcessor(new DescriptionAnnotationResolver<>()) - .annotationProcessor(new AsyncAnnotationResolver<>()) - .annotationProcessor(new Permission.AnnotationResolver<>()) - .annotationProcessor(new Permissions.AnnotationResolver<>()) - .annotationProcessor(new Validate.AnnotationResolver<>()) - .annotationProcessor(new ExecuteAnnotationResolver<>()) - .annotationProcessor(new RequirementProcessor<>(wrapperRegistry, parserRegistry, Flag.class, new FlagArgumentFactory())) - .annotationProcessor(new RequirementProcessor<>(wrapperRegistry, parserRegistry, Arg.class, new ArgArgumentFactory())) - .annotationProcessor(new RequirementProcessor<>(wrapperRegistry, parserRegistry, Join.class, new JoinArgumentFactory())) - .annotationProcessor(new RequirementProcessor<>(contextRegistry, wrapperRegistry, Context.class)) + .argument(String.class, JoinArgument.KEY, new JoinArgumentResolver<>()) + .argument(boolean.class, FlagArgument.KEY, new FlagArgumentResolver<>()) + .argument(Boolean.class, FlagArgument.KEY, new FlagArgumentResolver<>()) .wrapper(new OptionWrapper()) .wrapper(new OptionalWrapper()) diff --git a/litecommands-core/src/dev/rollczi/litecommands/annotation/processor/AnnotationProcessorService.java b/litecommands-core/src/dev/rollczi/litecommands/annotation/processor/AnnotationProcessorService.java deleted file mode 100644 index c6e67617b..000000000 --- a/litecommands-core/src/dev/rollczi/litecommands/annotation/processor/AnnotationProcessorService.java +++ /dev/null @@ -1,25 +0,0 @@ -package dev.rollczi.litecommands.annotation.processor; - -import dev.rollczi.litecommands.command.builder.CommandBuilder; - -import java.util.ArrayList; -import java.util.List; - -public class AnnotationProcessorService { - - private final List> annotationProcessors = new ArrayList<>(); - - public > AnnotationProcessorService register(A processor) { - annotationProcessors.add(processor); - return this; - } - - public CommandBuilder process(AnnotationInvoker invoker) { - for (AnnotationProcessor processor : annotationProcessors) { - invoker = processor.process(invoker); - } - - return invoker.getResult(); - } - -} diff --git a/litecommands-core/src/dev/rollczi/litecommands/annotation/processor/SourceProcessor.java b/litecommands-core/src/dev/rollczi/litecommands/annotation/processor/SourceProcessor.java deleted file mode 100644 index 1c6ec5435..000000000 --- a/litecommands-core/src/dev/rollczi/litecommands/annotation/processor/SourceProcessor.java +++ /dev/null @@ -1,9 +0,0 @@ -package dev.rollczi.litecommands.annotation.processor; - -import dev.rollczi.litecommands.command.builder.CommandBuilder; - -public interface SourceProcessor { - - CommandBuilder processBuilder(SOURCE source); - -} diff --git a/litecommands-core/src/dev/rollczi/litecommands/argument/Arg.java b/litecommands-core/src/dev/rollczi/litecommands/argument/Arg.java deleted file mode 100644 index e95671476..000000000 --- a/litecommands-core/src/dev/rollczi/litecommands/argument/Arg.java +++ /dev/null @@ -1,34 +0,0 @@ -package dev.rollczi.litecommands.argument; - -import java.lang.annotation.ElementType; -import java.lang.annotation.Retention; -import java.lang.annotation.RetentionPolicy; -import java.lang.annotation.Target; - -@Target({ ElementType.PARAMETER }) -@Retention(RetentionPolicy.RUNTIME) -public @interface Arg { - - String value() default ""; - - class Mock implements Arg { - - private final String value; - - public Mock(String value) { - this.value = value; - } - - @Override - public String value() { - return value; - } - - @Override - public Class annotationType() { - return Arg.class; - } - - } - -} diff --git a/litecommands-core/src/dev/rollczi/litecommands/argument/Argument.java b/litecommands-core/src/dev/rollczi/litecommands/argument/Argument.java index dc51de827..954046fce 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/argument/Argument.java +++ b/litecommands-core/src/dev/rollczi/litecommands/argument/Argument.java @@ -1,20 +1,16 @@ package dev.rollczi.litecommands.argument; -import dev.rollczi.litecommands.annotation.AnnotationHolder; +import dev.rollczi.litecommands.requirement.Requirement; import dev.rollczi.litecommands.wrapper.WrapFormat; import java.util.Optional; -public interface Argument { +public interface Argument extends Requirement { - @Deprecated String getName(); - @Deprecated WrapFormat getWrapperFormat(); - AnnotationHolder getAnnotationHolder(); - default Optional defaultValue() { return Optional.empty(); } @@ -27,4 +23,8 @@ default ArgumentKey toKey() { return ArgumentKey.typed(this.getClass()); } + static Argument of(String name, WrapFormat format) { + return new SimpleArgument<>(() -> name, format); + } + } \ No newline at end of file diff --git a/litecommands-core/src/dev/rollczi/litecommands/argument/SimpleArgument.java b/litecommands-core/src/dev/rollczi/litecommands/argument/SimpleArgument.java index cd49038a9..661a4dce7 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/argument/SimpleArgument.java +++ b/litecommands-core/src/dev/rollczi/litecommands/argument/SimpleArgument.java @@ -1,35 +1,41 @@ package dev.rollczi.litecommands.argument; -import dev.rollczi.litecommands.annotation.AnnotationHolder; +import dev.rollczi.litecommands.meta.Meta; +import dev.rollczi.litecommands.meta.MetaHolder; import dev.rollczi.litecommands.wrapper.WrapFormat; +import org.jetbrains.annotations.Nullable; -import java.lang.annotation.Annotation; +import java.util.function.Supplier; -public class SimpleArgument implements Argument { +public class SimpleArgument implements Argument { - private final AnnotationHolder holder; + private final Supplier name; + private final WrapFormat wrapperFormat; + private final Meta meta = Meta.create(); - public SimpleArgument(AnnotationHolder holder) { - this.holder = holder; + public SimpleArgument(Supplier name, WrapFormat wrapperFormat) { + this.name = name; + this.wrapperFormat = wrapperFormat; } - public A getAnnotation() { - return holder.getAnnotation(); + @Override + public String getName() { + return name.get(); } @Override - public AnnotationHolder getAnnotationHolder() { - return holder; + public WrapFormat getWrapperFormat() { + return this.wrapperFormat; } @Override - public WrapFormat getWrapperFormat() { - return holder.getFormat(); + public Meta meta() { + return meta; } @Override - public String getName() { - return this.holder.getName(); + public @Nullable MetaHolder parentMeta() { + return null; } } diff --git a/litecommands-core/src/dev/rollczi/litecommands/argument/resolver/AnnotationArgumentResolver.java b/litecommands-core/src/dev/rollczi/litecommands/argument/resolver/TypedArgumentResolver.java similarity index 79% rename from litecommands-core/src/dev/rollczi/litecommands/argument/resolver/AnnotationArgumentResolver.java rename to litecommands-core/src/dev/rollczi/litecommands/argument/resolver/TypedArgumentResolver.java index fc2cffd39..046c26037 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/argument/resolver/AnnotationArgumentResolver.java +++ b/litecommands-core/src/dev/rollczi/litecommands/argument/resolver/TypedArgumentResolver.java @@ -6,14 +6,14 @@ import dev.rollczi.litecommands.argument.suggester.TypedSuggester; @SuppressWarnings("rawtypes") -public abstract class AnnotationArgumentResolver> implements +public abstract class TypedArgumentResolver> implements TypedParser, TypedSuggester { private final Class argumentType; - protected AnnotationArgumentResolver(Class argumentType) { + protected TypedArgumentResolver(Class argumentType) { this.argumentType = argumentType; } diff --git a/litecommands-core/src/dev/rollczi/litecommands/argument/resolver/std/StringArgumentResolver.java b/litecommands-core/src/dev/rollczi/litecommands/argument/resolver/std/StringArgumentResolver.java index b7ea6a6b7..819dee0de 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/argument/resolver/std/StringArgumentResolver.java +++ b/litecommands-core/src/dev/rollczi/litecommands/argument/resolver/std/StringArgumentResolver.java @@ -14,11 +14,6 @@ protected ParseResult parse(Invocation invocation, Argument invocation, Argument context, String argument) { - return true; - } - @Override public SuggestionResult suggest(Invocation invocation, Argument objectStringArgument, SuggestionContext context) { return SuggestionResult.of("text"); diff --git a/litecommands-core/src/dev/rollczi/litecommands/builder/LiteCommandsBaseBuilder.java b/litecommands-core/src/dev/rollczi/litecommands/builder/LiteCommandsBaseBuilder.java index a0ae4046f..0048ca9a5 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/builder/LiteCommandsBaseBuilder.java +++ b/litecommands-core/src/dev/rollczi/litecommands/builder/LiteCommandsBaseBuilder.java @@ -26,8 +26,6 @@ import dev.rollczi.litecommands.permission.MissingPermissions; import dev.rollczi.litecommands.permission.MissingPermissionsHandler; import dev.rollczi.litecommands.platform.PlatformSettingsConfigurator; -import dev.rollczi.litecommands.annotation.processor.AnnotationProcessor; -import dev.rollczi.litecommands.annotation.processor.AnnotationProcessorService; import dev.rollczi.litecommands.scheduler.Scheduler; import dev.rollczi.litecommands.scheduler.SchedulerSameThreadImpl; import dev.rollczi.litecommands.schematic.SchematicFormat; @@ -82,10 +80,9 @@ public class LiteCommandsBaseBuilder commandBuilderCollector = new CommandBuilderCollector<>(); protected final MessageRegistry messageRegistry = new MessageRegistry(); protected final WrapperRegistry wrapperRegistry = new WrapperRegistry(); - protected final AnnotationProcessorService annotationProcessorService = new AnnotationProcessorService<>(); protected Scheduler scheduler = new SchedulerSameThreadImpl(); - protected SchematicGenerator schematicGenerator = SchematicGenerator.from(SchematicFormat.angleBrackets(), validatorService); + protected SchematicGenerator schematicGenerator = SchematicGenerator.from(SchematicFormat.angleBrackets(), validatorService, wrapperRegistry); /** * Constructor for {@link LiteCommandsBaseBuilder} @@ -318,7 +315,7 @@ public LiteCommandsBuilder schematicGenerator(SchematicGenerator schematicGenerator(SchematicFormat format) { - this.schematicGenerator = SchematicGenerator.from(format, validatorService); + this.schematicGenerator = SchematicGenerator.from(format, validatorService, wrapperRegistry); return this; } @@ -328,12 +325,6 @@ public LiteCommandsBuilder wrapper(Wrapper wrapper) { return this; } - @Override - public LiteCommandsBuilder annotationProcessor(AnnotationProcessor annotationProcessor) { - this.annotationProcessorService.register(annotationProcessor); - return this; - } - @Override public LiteCommandsBuilder selfProcessor(LiteBuilderProcessor processor) { processor.process(this, this); @@ -380,7 +371,7 @@ public LiteCommands build(boolean register) { processor.process(this, this); } - CommandExecuteService commandExecuteService = new CommandExecuteService<>(validatorService, resultHandleService, exceptionHandleService, scheduler, schematicGenerator); + CommandExecuteService commandExecuteService = new CommandExecuteService<>(validatorService, resultHandleService, exceptionHandleService, scheduler, schematicGenerator, parserRegistry, contextRegistry, wrapperRegistry); SuggestionService suggestionService = new SuggestionService<>(parserRegistry, suggesterRegistry, validatorService); CommandManager commandManager = new CommandManager<>(this.platform, commandExecuteService, suggestionService); @@ -497,10 +488,4 @@ public WrapperRegistry getWrapperRegistry() { return this.wrapperRegistry; } - @Override - @ApiStatus.Internal - public AnnotationProcessorService getAnnotationProcessorRegistry() { - return this.annotationProcessorService; - } - } diff --git a/litecommands-core/src/dev/rollczi/litecommands/builder/LiteCommandsBuilder.java b/litecommands-core/src/dev/rollczi/litecommands/builder/LiteCommandsBuilder.java index 04ab483b0..af15d91a6 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/builder/LiteCommandsBuilder.java +++ b/litecommands-core/src/dev/rollczi/litecommands/builder/LiteCommandsBuilder.java @@ -19,7 +19,6 @@ import dev.rollczi.litecommands.platform.Platform; import dev.rollczi.litecommands.platform.PlatformSettings; import dev.rollczi.litecommands.platform.PlatformSettingsConfigurator; -import dev.rollczi.litecommands.annotation.processor.AnnotationProcessor; import dev.rollczi.litecommands.scheduler.Scheduler; import dev.rollczi.litecommands.schematic.SchematicFormat; import dev.rollczi.litecommands.schematic.SchematicGenerator; @@ -191,8 +190,6 @@ default LiteCommandsBuilder validatorMarked(Validator schematicGenerator(SchematicFormat format); - LiteCommandsBuilder annotationProcessor(AnnotationProcessor annotationProcessor); - LiteCommandsBuilder selfProcessor(LiteBuilderProcessor processor); LiteCommandsBuilder preProcessor(LiteBuilderProcessor preProcessor); diff --git a/litecommands-core/src/dev/rollczi/litecommands/builder/LiteCommandsInternalBuilderApi.java b/litecommands-core/src/dev/rollczi/litecommands/builder/LiteCommandsInternalBuilderApi.java index 3327ed4c4..892e367ee 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/builder/LiteCommandsInternalBuilderApi.java +++ b/litecommands-core/src/dev/rollczi/litecommands/builder/LiteCommandsInternalBuilderApi.java @@ -10,7 +10,6 @@ import dev.rollczi.litecommands.message.MessageRegistry; import dev.rollczi.litecommands.platform.PlatformSettings; import dev.rollczi.litecommands.platform.Platform; -import dev.rollczi.litecommands.annotation.processor.AnnotationProcessorService; import dev.rollczi.litecommands.scheduler.Scheduler; import dev.rollczi.litecommands.argument.suggester.SuggesterRegistry; import dev.rollczi.litecommands.validator.ValidatorService; @@ -62,6 +61,4 @@ public interface LiteCommandsInternalBuilderApi getAnnotationProcessorRegistry(); } diff --git a/litecommands-core/src/dev/rollczi/litecommands/builder/LiteCommandsProvider.java b/litecommands-core/src/dev/rollczi/litecommands/builder/LiteCommandsProvider.java index f4bf4b574..cc070c1dd 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/builder/LiteCommandsProvider.java +++ b/litecommands-core/src/dev/rollczi/litecommands/builder/LiteCommandsProvider.java @@ -5,6 +5,7 @@ import java.util.List; +@Deprecated public interface LiteCommandsProvider { List> provide(LiteCommandsInternalBuilderApi builder); diff --git a/litecommands-core/src/dev/rollczi/litecommands/command/CommandExecutorProvider.java b/litecommands-core/src/dev/rollczi/litecommands/command/CommandExecutorProvider.java new file mode 100644 index 000000000..71b4baa4e --- /dev/null +++ b/litecommands-core/src/dev/rollczi/litecommands/command/CommandExecutorProvider.java @@ -0,0 +1,9 @@ +package dev.rollczi.litecommands.command; + +import dev.rollczi.litecommands.command.executor.CommandExecutor; + +public interface CommandExecutorProvider { + + CommandExecutor provide(CommandRoute parent); + +} diff --git a/litecommands-core/src/dev/rollczi/litecommands/command/CommandProvider.java b/litecommands-core/src/dev/rollczi/litecommands/command/CommandProvider.java new file mode 100644 index 000000000..03bba9de5 --- /dev/null +++ b/litecommands-core/src/dev/rollczi/litecommands/command/CommandProvider.java @@ -0,0 +1,8 @@ +package dev.rollczi.litecommands.command; + +@FunctionalInterface +public interface CommandProvider { + + CommandRoute provide(CommandRoute root); + +} diff --git a/litecommands-core/src/dev/rollczi/litecommands/command/CommandRoute.java b/litecommands-core/src/dev/rollczi/litecommands/command/CommandRoute.java index aed669df6..a6bc817e0 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/command/CommandRoute.java +++ b/litecommands-core/src/dev/rollczi/litecommands/command/CommandRoute.java @@ -1,8 +1,8 @@ package dev.rollczi.litecommands.command; +import dev.rollczi.litecommands.argument.Argument; import dev.rollczi.litecommands.command.executor.CommandExecutor; import dev.rollczi.litecommands.meta.Meta; -import dev.rollczi.litecommands.requirement.Requirement; import dev.rollczi.litecommands.scope.Scopeable; import java.util.List; diff --git a/litecommands-core/src/dev/rollczi/litecommands/command/builder/CommandBuilder.java b/litecommands-core/src/dev/rollczi/litecommands/command/builder/CommandBuilder.java index fc1c7e1eb..8babfd2da 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/command/builder/CommandBuilder.java +++ b/litecommands-core/src/dev/rollczi/litecommands/command/builder/CommandBuilder.java @@ -1,5 +1,6 @@ package dev.rollczi.litecommands.command.builder; +import dev.rollczi.litecommands.command.CommandExecutorProvider; import dev.rollczi.litecommands.command.CommandRoute; import dev.rollczi.litecommands.meta.Meta; import dev.rollczi.litecommands.meta.MetaHolder; @@ -54,10 +55,9 @@ public interface CommandBuilder extends Scopeable, MetaHolder { Optional> getChild(String test); - @NotNull - CommandBuilder appendExecutor(CommandBuilderExecutor executor); + CommandBuilder appendExecutor(CommandExecutorProvider executor); - Collection> executors(); + Collection> executors(); CommandBuilder applyMeta(UnaryOperator operator); diff --git a/litecommands-core/src/dev/rollczi/litecommands/command/builder/CommandBuilderBase.java b/litecommands-core/src/dev/rollczi/litecommands/command/builder/CommandBuilderBase.java index b66721214..2ebc4aaa3 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/command/builder/CommandBuilderBase.java +++ b/litecommands-core/src/dev/rollczi/litecommands/command/builder/CommandBuilderBase.java @@ -1,8 +1,8 @@ package dev.rollczi.litecommands.command.builder; +import dev.rollczi.litecommands.command.CommandExecutorProvider; import dev.rollczi.litecommands.command.CommandRoute; import dev.rollczi.litecommands.meta.Meta; -import dev.rollczi.litecommands.meta.MetaCollector; import dev.rollczi.litecommands.meta.MetaHolder; import org.jetbrains.annotations.ApiStatus; import org.jetbrains.annotations.NotNull; @@ -23,7 +23,7 @@ abstract class CommandBuilderBase implements CommandBuilder { protected @Nullable String name; protected final List aliases = new ArrayList<>(); protected final Map> children = new HashMap<>(); - protected final List> executors = new ArrayList<>(); + protected final List> executors = new ArrayList<>(); protected boolean enabled = true; protected Meta meta = Meta.create(); @@ -160,13 +160,13 @@ public Optional> getChild(String test) { } @Override - public @NotNull CommandBuilder appendExecutor(CommandBuilderExecutor executor) { + public @NotNull CommandBuilder appendExecutor(CommandExecutorProvider executor) { this.executors.add(executor); return this; } @Override - public Collection> executors() { + public Collection> executors() { return Collections.unmodifiableCollection(this.executors); } @@ -297,12 +297,8 @@ public Collection> build(CommandRoute parent) { route.meta().apply(this.meta); - for (CommandBuilderExecutor executor : this.executors) { - if (!executor.buildable()) { - continue; - } - - route.appendExecutor(executor.build(route)); + for (CommandExecutorProvider executor : this.executors) { + route.appendExecutor(executor.provide(route)); } for (CommandBuilder child : this.children()) { @@ -322,7 +318,7 @@ public Collection> build(CommandRoute parent) { public void meagre(CommandBuilder context) { this.aliases.addAll(context.aliases()); - for (CommandBuilderExecutor executor : context.executors()) { + for (CommandExecutorProvider executor : context.executors()) { this.appendExecutor(executor); } diff --git a/litecommands-core/src/dev/rollczi/litecommands/command/builder/CommandBuilderExecutor.java b/litecommands-core/src/dev/rollczi/litecommands/command/builder/CommandBuilderExecutor.java deleted file mode 100644 index fa65acb62..000000000 --- a/litecommands-core/src/dev/rollczi/litecommands/command/builder/CommandBuilderExecutor.java +++ /dev/null @@ -1,71 +0,0 @@ -package dev.rollczi.litecommands.command.builder; - -import dev.rollczi.litecommands.command.CommandRoute; -import dev.rollczi.litecommands.command.executor.CommandExecutor; -import dev.rollczi.litecommands.command.executor.CommandExecutorFactory; -import dev.rollczi.litecommands.requirement.Requirement; -import dev.rollczi.litecommands.meta.Meta; -import dev.rollczi.litecommands.meta.MetaHolder; -import org.jetbrains.annotations.Nullable; - -import java.util.ArrayList; -import java.util.Collections; -import java.util.List; -import java.util.function.UnaryOperator; - -public class CommandBuilderExecutor implements MetaHolder { - - private final MetaHolder parent; - private Meta meta = Meta.create(); - - private CommandExecutorFactory executorFactory; - private final List> requirements = new ArrayList<>(); - - public CommandBuilderExecutor(MetaHolder parent) { - this.parent = parent; - } - - public CommandBuilderExecutor(MetaHolder parent, CommandExecutorFactory executorFactory) { - this.parent = parent; - this.executorFactory = executorFactory; - } - - public void setExecutorFactory(CommandExecutorFactory factory) { - this.executorFactory = factory; - } - - public CommandBuilderExecutor applyMeta(UnaryOperator operator) { - this.meta = operator.apply(this.meta); - return this; - } - - public boolean buildable() { - return this.executorFactory != null; - } - - public CommandExecutor build(CommandRoute parent) { - CommandExecutor executor = this.executorFactory.create(parent, Collections.unmodifiableList(this.requirements)); - executor.meta().apply(this.meta); - - return executor; - } - - @Override - public Meta meta() { - return this.meta; - } - - @Override - public @Nullable MetaHolder parentMeta() { - return this.parent; - } - - public void addRequirement(Requirement requirement) { - this.requirements.add(requirement); - } - - public int getRequirementsCount() { - return this.requirements.size(); - } - -} diff --git a/litecommands-core/src/dev/rollczi/litecommands/command/builder/CommandBuilderRootImpl.java b/litecommands-core/src/dev/rollczi/litecommands/command/builder/CommandBuilderRootImpl.java index 8d814fb34..04c63c657 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/command/builder/CommandBuilderRootImpl.java +++ b/litecommands-core/src/dev/rollczi/litecommands/command/builder/CommandBuilderRootImpl.java @@ -1,6 +1,6 @@ package dev.rollczi.litecommands.command.builder; -import dev.rollczi.litecommands.meta.MetaCollector; +import dev.rollczi.litecommands.command.CommandExecutorProvider; import dev.rollczi.litecommands.meta.MetaHolder; import dev.rollczi.litecommands.util.StringUtil; import dev.rollczi.litecommands.command.CommandRoute; @@ -124,12 +124,12 @@ public Optional> getChild(String test) { } @Override - public @NotNull CommandBuilder appendExecutor(CommandBuilderExecutor executor) { + public CommandBuilder appendExecutor(CommandExecutorProvider executor) { throw new UnsupportedOperationException("Cannot append executor to root command"); } @Override - public List> executors() { + public Collection> executors() { throw new UnsupportedOperationException("Cannot get executors from root command"); } diff --git a/litecommands-core/src/dev/rollczi/litecommands/command/executor/AbstractCommandExecutor.java b/litecommands-core/src/dev/rollczi/litecommands/command/executor/AbstractCommandExecutor.java index 71185fb53..15c379396 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/command/executor/AbstractCommandExecutor.java +++ b/litecommands-core/src/dev/rollczi/litecommands/command/executor/AbstractCommandExecutor.java @@ -1,7 +1,9 @@ package dev.rollczi.litecommands.command.executor; +import dev.rollczi.litecommands.argument.Argument; import dev.rollczi.litecommands.command.CommandRoute; import dev.rollczi.litecommands.requirement.Requirement; +import dev.rollczi.litecommands.requirement.ContextRequirement; import dev.rollczi.litecommands.meta.Meta; import dev.rollczi.litecommands.meta.MetaHolder; @@ -9,16 +11,19 @@ import java.util.Collection; import java.util.Collections; import java.util.List; +import java.util.stream.Collectors; public abstract class AbstractCommandExecutor implements CommandExecutor { protected final CommandRoute parent; - protected final List> requirements = new ArrayList<>(); + protected final List> arguments = new ArrayList<>(); + protected final List> contextRequirements = new ArrayList<>(); protected final Meta meta = Meta.create(); - protected AbstractCommandExecutor(CommandRoute parent, Collection> requirements) { + protected AbstractCommandExecutor(CommandRoute parent, Collection> arguments, Collection> contextRequirements) { this.parent = parent; - this.requirements.addAll(requirements); + this.arguments.addAll(arguments); + this.contextRequirements.addAll(contextRequirements); } @Override @@ -37,8 +42,13 @@ public CommandRoute getParent() { } @Override - public List> getRequirements() { - return Collections.unmodifiableList(requirements); + public List> getArguments() { + return Collections.unmodifiableList(arguments); + } + + @Override + public List> getContextRequirements() { + return Collections.unmodifiableList(contextRequirements); } } diff --git a/litecommands-core/src/dev/rollczi/litecommands/command/executor/CommandExecuteService.java b/litecommands-core/src/dev/rollczi/litecommands/command/executor/CommandExecuteService.java index a33bf0787..d82c53065 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/command/executor/CommandExecuteService.java +++ b/litecommands-core/src/dev/rollczi/litecommands/command/executor/CommandExecuteService.java @@ -1,7 +1,15 @@ package dev.rollczi.litecommands.command.executor; +import dev.rollczi.litecommands.argument.Argument; +import dev.rollczi.litecommands.argument.parser.ParseResult; +import dev.rollczi.litecommands.argument.parser.ParserRegistry; +import dev.rollczi.litecommands.argument.parser.ParserSet; import dev.rollczi.litecommands.argument.parser.input.ParseableInputMatcher; import dev.rollczi.litecommands.command.CommandRoute; +import dev.rollczi.litecommands.context.ContextRegistry; +import dev.rollczi.litecommands.context.ContextResult; +import dev.rollczi.litecommands.requirement.ContextRequirement; +import dev.rollczi.litecommands.requirement.Requirement; import dev.rollczi.litecommands.requirement.RequirementsResult; import dev.rollczi.litecommands.LiteCommandsException; import dev.rollczi.litecommands.handler.result.ResultHandleService; @@ -11,7 +19,6 @@ import dev.rollczi.litecommands.schematic.SchematicGenerator; import dev.rollczi.litecommands.schematic.SchematicInput; import dev.rollczi.litecommands.shared.FailedReason; -import dev.rollczi.litecommands.requirement.Requirement; import dev.rollczi.litecommands.requirement.RequirementResult; import dev.rollczi.litecommands.requirement.RequirementMatch; import dev.rollczi.litecommands.handler.exception.ExceptionHandleService; @@ -25,6 +32,9 @@ import dev.rollczi.litecommands.scheduler.SchedulerPollType; import dev.rollczi.litecommands.validator.ValidatorService; import dev.rollczi.litecommands.wrapper.Wrap; +import dev.rollczi.litecommands.wrapper.WrapFormat; +import dev.rollczi.litecommands.wrapper.Wrapper; +import dev.rollczi.litecommands.wrapper.WrapperRegistry; import org.jetbrains.annotations.Nullable; import java.util.ListIterator; @@ -41,13 +51,19 @@ public class CommandExecuteService { private final ExceptionHandleService exceptionHandleService; private final Scheduler scheduler; private final SchematicGenerator schematicGenerator; + private final ParserRegistry parserRegistry; + private final ContextRegistry contextRegistry; + private final WrapperRegistry wrapperRegistry; - public CommandExecuteService(ValidatorService validatorService, ResultHandleService resultResolver, ExceptionHandleService exceptionHandleService, Scheduler scheduler, SchematicGenerator schematicGenerator) { + public CommandExecuteService(ValidatorService validatorService, ResultHandleService resultResolver, ExceptionHandleService exceptionHandleService, Scheduler scheduler, SchematicGenerator schematicGenerator, ParserRegistry parserRegistry, ContextRegistry contextRegistry, WrapperRegistry wrapperRegistry) { this.validatorService = validatorService; this.resultResolver = resultResolver; this.exceptionHandleService = exceptionHandleService; this.scheduler = scheduler; this.schematicGenerator = schematicGenerator; + this.parserRegistry = parserRegistry; + this.contextRegistry = contextRegistry; + this.wrapperRegistry = wrapperRegistry; } public CompletableFuture execute(Invocation invocation, ParseableInputMatcher matcher, CommandRoute commandRoute) { @@ -196,10 +212,14 @@ private > CompletableFuture invocation, MATCHER matcher ) { - ScheduledChain.Builder> builder = ScheduledChain.builder(); + ScheduledChain.Builder, RequirementResult> builder = ScheduledChain.builder(); - for (Requirement requirement : executor.getRequirements()) { - builder.link(new ScheduledRequirement(requirement, invocation, matcher)); + for (Argument argument : executor.getArguments()) { + builder.link(new ScheduledRequirement<>(argument, () -> matchArgument(argument, invocation, matcher))); + } + + for (ContextRequirement contextRequirement : executor.getContextRequirements()) { + builder.link(new ScheduledRequirement<>(contextRequirement, () -> matchContext(contextRequirement, invocation))); } return builder.build((scheduledRequirement, requirementResult) -> { @@ -223,7 +243,7 @@ private > CompletableFuture restulrBuilder = RequirementsResult.builder(invocation); - for (RequirementMatch, ?> success : result.getSuccess()) { + for (RequirementMatch, ?> success : result.getSuccess()) { restulrBuilder.add(success.getRequirement().getName(), success); } @@ -232,17 +252,18 @@ private > CompletableFuture, T> RequirementMatch toMatch(R requirement, Wrap wrap) { + private , T> RequirementMatch toMatch(R requirement, Wrap wrap) { return new RequirementMatch<>(requirement, (Wrap) wrap); } - private class ScheduledRequirement implements ScheduledChainLink> { - private final Requirement requirement; + private static class ScheduledRequirement implements ScheduledChainLink> { + + private final Requirement requirement; private final Supplier> match; - public > ScheduledRequirement(Requirement requirement, Invocation invocation, MATCHER matcher) { + public ScheduledRequirement(Requirement requirement, Supplier> match) { this.requirement = requirement; - this.match = () -> requirement.match(invocation, matcher); + this.match = match; } @Override @@ -256,4 +277,38 @@ public SchedulerPollType type() { } } + private > RequirementResult matchArgument(Argument argument, Invocation invocation, MATCHER matcher) { + WrapFormat wrapFormat = argument.getWrapperFormat(); + ParserSet parserSet = parserRegistry.getParserSet(wrapFormat.getParsedType(), argument.toKey()); + ParseResult result = matcher.nextArgument(invocation, argument, parserSet); + Wrapper wrapper = wrapperRegistry.getWrappedExpectedFactory(wrapFormat); + + if (result.isSuccessful()) { + PARSED successfulResult = result.getSuccessfulResult(); + + return RequirementResult.success(wrapper.create(successfulResult, wrapFormat)); + } + + FailedReason failedReason = result.getFailedReason(); + + if (failedReason.getReason() == InvalidUsage.Cause.MISSING_ARGUMENT && wrapper.canCreateEmpty()) { + return RequirementResult.success(wrapper.createEmpty(wrapFormat)); + } + + return RequirementResult.failure(failedReason); + } + + + private RequirementResult matchContext(ContextRequirement contextRequirement, Invocation invocation) { + WrapFormat wrapFormat = contextRequirement.getWrapperFormat(); + ContextResult result = contextRegistry.provideContext(wrapFormat.getParsedType(), invocation); + Wrapper wrapper = wrapperRegistry.getWrappedExpectedFactory(wrapFormat); + + if (result.hasResult()) { + return RequirementResult.success(wrapper.create(result.getResult(), wrapFormat)); + } + + return RequirementResult.failure(result.getError()); + } + } diff --git a/litecommands-core/src/dev/rollczi/litecommands/command/executor/CommandExecutor.java b/litecommands-core/src/dev/rollczi/litecommands/command/executor/CommandExecutor.java index 46654f627..cbba8ffc8 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/command/executor/CommandExecutor.java +++ b/litecommands-core/src/dev/rollczi/litecommands/command/executor/CommandExecutor.java @@ -1,7 +1,9 @@ package dev.rollczi.litecommands.command.executor; +import dev.rollczi.litecommands.argument.Argument; import dev.rollczi.litecommands.command.CommandNode; -import dev.rollczi.litecommands.requirement.Requirement; +import dev.rollczi.litecommands.command.CommandRoute; +import dev.rollczi.litecommands.requirement.ContextRequirement; import dev.rollczi.litecommands.requirement.RequirementsResult; import dev.rollczi.litecommands.scope.Scopeable; @@ -11,8 +13,9 @@ public interface CommandExecutor extends Scopeable, CommandNode { - @Deprecated - List> getRequirements(); + List> getArguments(); + + List> getContextRequirements(); CommandExecutorMatchResult match(RequirementsResult result); @@ -21,4 +24,8 @@ default Collection names() { return Collections.emptySet(); } + static CommandExecutorBuilder builder(CommandRoute parent) { + return new CommandExecutorBuilder<>(parent); + } + } diff --git a/litecommands-core/src/dev/rollczi/litecommands/command/executor/CommandExecutorBuilder.java b/litecommands-core/src/dev/rollczi/litecommands/command/executor/CommandExecutorBuilder.java new file mode 100644 index 000000000..414aef012 --- /dev/null +++ b/litecommands-core/src/dev/rollczi/litecommands/command/executor/CommandExecutorBuilder.java @@ -0,0 +1,97 @@ +package dev.rollczi.litecommands.command.executor; + +import dev.rollczi.litecommands.argument.Argument; +import dev.rollczi.litecommands.command.CommandRoute; +import dev.rollczi.litecommands.requirement.ContextRequirement; +import dev.rollczi.litecommands.requirement.RequirementsResult; + +import java.util.ArrayList; +import java.util.List; +import java.util.function.Consumer; + +public class CommandExecutorBuilder { + + private final CommandRoute parent; + private final List> arguments = new ArrayList<>(); + private final List> contextRequirements = new ArrayList<>(); + private Consumer> executor; + + public CommandExecutorBuilder(CommandRoute parent) { + this.parent = parent; + } + + public CommandExecutorBuilder argument(Argument argument) { + this.arguments.add(argument); + return this; + } + + public boolean canBuild() { + return executor != null; + } + + public CommandExecutorBuilder arguments(Iterable> arguments) { + arguments.forEach(this::argument); + return this; + } + + public CommandExecutorBuilder contextRequirement(ContextRequirement contextRequirement) { + this.contextRequirements.add(contextRequirement); + return this; + } + + public CommandExecutorBuilder contextRequirements(Iterable> contextRequirements) { + contextRequirements.forEach(this::contextRequirement); + return this; + } + + public CommandExecutorBuilder executor(Consumer> executor) { + this.executor = executor; + return this; + } + + public CommandExecutor build() { + return new SimpleCommandExecutor<>(parent, executor, arguments, contextRequirements); + } + + private static class SimpleCommandExecutor extends AbstractCommandExecutor implements CommandExecutor { + + private final List> arguments; + private final List> contextRequirements; + private final Consumer> executor; + + private SimpleCommandExecutor(CommandRoute parent, Consumer> executor, List> arguments, List> contextRequirements) { + super(parent, arguments, contextRequirements); + this.arguments = arguments; + this.contextRequirements = contextRequirements; + this.executor = executor; + } + + @Override + public CommandExecutorMatchResult match(RequirementsResult result) { + for (Argument requirement : arguments) { + if (!result.has(requirement.getName())) { + return CommandExecutorMatchResult.failed(new IllegalStateException("Missing requirement " + requirement.getName())); + } + } + + for (ContextRequirement requirement : contextRequirements) { + if (!result.has(requirement.getName())) { + return CommandExecutorMatchResult.failed(new IllegalStateException("Missing requirement " + requirement.getName())); + } + } + + return CommandExecutorMatchResult.success(() -> { + try { + executor.accept(new LiteContext<>(result)); + + return CommandExecuteResult.success(this, null); + } + catch (Exception exception) { + return CommandExecuteResult.failed(this, exception); + } + }); + } + + } + +} diff --git a/litecommands-core/src/dev/rollczi/litecommands/command/executor/CommandExecutorFactory.java b/litecommands-core/src/dev/rollczi/litecommands/command/executor/CommandExecutorFactory.java index ffbfbea2d..9015084e1 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/command/executor/CommandExecutorFactory.java +++ b/litecommands-core/src/dev/rollczi/litecommands/command/executor/CommandExecutorFactory.java @@ -8,6 +8,6 @@ @FunctionalInterface public interface CommandExecutorFactory { - CommandExecutor create(CommandRoute parent, List> requirements); + CommandExecutor create(CommandRoute parent, List> requirements); } diff --git a/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/LiteContext.java b/litecommands-core/src/dev/rollczi/litecommands/command/executor/LiteContext.java similarity index 95% rename from litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/LiteContext.java rename to litecommands-core/src/dev/rollczi/litecommands/command/executor/LiteContext.java index 076fe8d8a..256c33031 100644 --- a/litecommands-core-annotations/src/dev/rollczi/litecommands/programmatic/LiteContext.java +++ b/litecommands-core/src/dev/rollczi/litecommands/command/executor/LiteContext.java @@ -1,4 +1,4 @@ -package dev.rollczi.litecommands.programmatic; +package dev.rollczi.litecommands.command.executor; import dev.rollczi.litecommands.invocation.Invocation; import dev.rollczi.litecommands.requirement.RequirementMatch; @@ -43,7 +43,7 @@ public Invocation invocation() { @SuppressWarnings("unchecked") private OUT get(String name, WrapFormat format) { - RequirementMatch match = result.get(name); + RequirementMatch match = result.get(name); if (match == null) { throw new IllegalArgumentException("Argument with name '" + name + "' not found"); diff --git a/litecommands-core/src/dev/rollczi/litecommands/context/LegacyContextProvider.java b/litecommands-core/src/dev/rollczi/litecommands/context/LegacyContextProvider.java index 40c646a0c..9c19f3f07 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/context/LegacyContextProvider.java +++ b/litecommands-core/src/dev/rollczi/litecommands/context/LegacyContextProvider.java @@ -3,6 +3,7 @@ import dev.rollczi.litecommands.invocation.Invocation; import panda.std.Result; +@Deprecated public interface LegacyContextProvider extends ContextProvider { Result provideLegacy(Invocation invocation); diff --git a/litecommands-core/src/dev/rollczi/litecommands/flag/Flag.java b/litecommands-core/src/dev/rollczi/litecommands/flag/Flag.java deleted file mode 100644 index c6f2c3490..000000000 --- a/litecommands-core/src/dev/rollczi/litecommands/flag/Flag.java +++ /dev/null @@ -1,38 +0,0 @@ -package dev.rollczi.litecommands.flag; - -import dev.rollczi.litecommands.argument.ArgumentKey; - -import java.lang.annotation.Annotation; -import java.lang.annotation.ElementType; -import java.lang.annotation.Retention; -import java.lang.annotation.RetentionPolicy; -import java.lang.annotation.Target; - -@Target({ ElementType.PARAMETER }) -@Retention(RetentionPolicy.RUNTIME) -public @interface Flag { - - String value(); - - ArgumentKey ARGUMENT_KEY = ArgumentKey.typed(FlagArgument.class); - - class Mock implements Flag { - - private final String value; - - public Mock(String value) { - this.value = value; - } - - @Override - public String value() { - return value; - } - - @Override - public Class annotationType() { - return Flag.class; - } - } - -} diff --git a/litecommands-core/src/dev/rollczi/litecommands/flag/FlagArgument.java b/litecommands-core/src/dev/rollczi/litecommands/flag/FlagArgument.java index df4832b5f..af0fb6249 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/flag/FlagArgument.java +++ b/litecommands-core/src/dev/rollczi/litecommands/flag/FlagArgument.java @@ -1,24 +1,23 @@ package dev.rollczi.litecommands.flag; -import dev.rollczi.litecommands.annotation.AnnotationHolder; +import dev.rollczi.litecommands.argument.ArgumentKey; import dev.rollczi.litecommands.argument.SimpleArgument; +import dev.rollczi.litecommands.wrapper.WrapFormat; import java.util.Optional; +import java.util.function.Supplier; -class FlagArgument extends SimpleArgument { +public class FlagArgument extends SimpleArgument { - FlagArgument(AnnotationHolder holder) { - super(holder); - } + public static final ArgumentKey KEY = ArgumentKey.typed(FlagArgument.class); - @Override - public String getName() { - return getAnnotation().value(); + public FlagArgument(Supplier stringSupplier, WrapFormat parsedType) { + super(stringSupplier, parsedType); } @Override public Optional defaultValue() { - return Optional.of(Boolean.FALSE); + return Optional.of(false); } } diff --git a/litecommands-core/src/dev/rollczi/litecommands/flag/FlagArgumentResolver.java b/litecommands-core/src/dev/rollczi/litecommands/flag/FlagArgumentResolver.java index 6bd0a532d..1c0634799 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/flag/FlagArgumentResolver.java +++ b/litecommands-core/src/dev/rollczi/litecommands/flag/FlagArgumentResolver.java @@ -1,14 +1,14 @@ package dev.rollczi.litecommands.flag; import dev.rollczi.litecommands.argument.parser.ParseResult; -import dev.rollczi.litecommands.argument.resolver.AnnotationArgumentResolver; +import dev.rollczi.litecommands.argument.resolver.TypedArgumentResolver; import dev.rollczi.litecommands.suggestion.SuggestionContext; import dev.rollczi.litecommands.suggestion.SuggestionResult; import dev.rollczi.litecommands.input.raw.RawInput; import dev.rollczi.litecommands.invocation.Invocation; import dev.rollczi.litecommands.range.Range; -public class FlagArgumentResolver extends AnnotationArgumentResolver { +public class FlagArgumentResolver extends TypedArgumentResolver { public FlagArgumentResolver() { super(FlagArgument.class); @@ -16,8 +16,7 @@ public FlagArgumentResolver() { @Override public ParseResult parseTyped(Invocation invocation, FlagArgument argument, RawInput rawInput) { - Flag flag = argument.getAnnotation(); - String key = flag.value(); + String key = argument.getName(); if (!rawInput.hasNext()) { return ParseResult.success(false); @@ -38,7 +37,7 @@ public Range getTypedRange(FlagArgument argument) { @Override public SuggestionResult suggestTyped(Invocation invocation, FlagArgument argument, SuggestionContext context) { - return SuggestionResult.of(argument.getAnnotation().value()); + return SuggestionResult.of(argument.getName()); } } diff --git a/litecommands-core/src/dev/rollczi/litecommands/join/Join.java b/litecommands-core/src/dev/rollczi/litecommands/join/Join.java deleted file mode 100644 index f48552e96..000000000 --- a/litecommands-core/src/dev/rollczi/litecommands/join/Join.java +++ /dev/null @@ -1,45 +0,0 @@ -package dev.rollczi.litecommands.join; - -import dev.rollczi.litecommands.argument.ArgumentKey; - -import java.lang.annotation.Annotation; -import java.lang.annotation.ElementType; -import java.lang.annotation.Retention; -import java.lang.annotation.RetentionPolicy; -import java.lang.annotation.Target; - -@Target({ ElementType.PARAMETER }) -@Retention(RetentionPolicy.RUNTIME) -public @interface Join { - - String separator() default " "; - - int limit() default Integer.MAX_VALUE; - - ArgumentKey ARGUMENT_KEY = ArgumentKey.typed(JoinArgument.class); - - class Mock implements Join { - private final String separator; - private final int limit; - - public Mock(String separator, int limit) { - this.separator = separator; - this.limit = limit; - } - - @Override - public String separator() { - return separator; - } - - @Override - public int limit() { - return limit; - } - - @Override - public Class annotationType() { - return Join.class; - } - } -} diff --git a/litecommands-core/src/dev/rollczi/litecommands/join/JoinArgument.java b/litecommands-core/src/dev/rollczi/litecommands/join/JoinArgument.java index d16a4d49c..b7fc05f02 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/join/JoinArgument.java +++ b/litecommands-core/src/dev/rollczi/litecommands/join/JoinArgument.java @@ -1,12 +1,37 @@ package dev.rollczi.litecommands.join; -import dev.rollczi.litecommands.annotation.AnnotationHolder; +import dev.rollczi.litecommands.argument.ArgumentKey; import dev.rollczi.litecommands.argument.SimpleArgument; +import dev.rollczi.litecommands.wrapper.WrapFormat; -class JoinArgument extends SimpleArgument { +import java.util.function.Supplier; - public JoinArgument(AnnotationHolder holder) { - super(holder); +public class JoinArgument extends SimpleArgument { + + public static final String DEFAULT_SEPARATOR = " "; + public static final int DEFAULT_LIMIT = -1; + + public static final ArgumentKey KEY = ArgumentKey.typed(JoinArgument.class); + + private final String separator; + private final int limit; + + public JoinArgument(Supplier name, WrapFormat wrapperFormat, String separator, int limit) { + super(name, wrapperFormat); + this.separator = separator; + this.limit = limit; + } + + public JoinArgument(Supplier name, WrapFormat wrapperFormat) { + this(name, wrapperFormat, DEFAULT_SEPARATOR, DEFAULT_LIMIT); + } + + public String getSeparator() { + return separator; + } + + public int getLimit() { + return limit; } } diff --git a/litecommands-core/src/dev/rollczi/litecommands/join/JoinArgumentResolver.java b/litecommands-core/src/dev/rollczi/litecommands/join/JoinArgumentResolver.java index 1e766da51..f24195c90 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/join/JoinArgumentResolver.java +++ b/litecommands-core/src/dev/rollczi/litecommands/join/JoinArgumentResolver.java @@ -1,7 +1,7 @@ package dev.rollczi.litecommands.join; import dev.rollczi.litecommands.argument.parser.ParseResult; -import dev.rollczi.litecommands.argument.resolver.AnnotationArgumentResolver; +import dev.rollczi.litecommands.argument.resolver.TypedArgumentResolver; import dev.rollczi.litecommands.suggestion.SuggestionContext; import dev.rollczi.litecommands.suggestion.SuggestionResult; import dev.rollczi.litecommands.input.raw.RawInput; @@ -12,7 +12,7 @@ import java.util.ArrayList; import java.util.List; -public class JoinArgumentResolver extends AnnotationArgumentResolver> { +public class JoinArgumentResolver extends TypedArgumentResolver> { public JoinArgumentResolver() { super(JoinArgument.class); @@ -20,9 +20,7 @@ public JoinArgumentResolver() { @Override public ParseResult parseTyped(Invocation invocation, JoinArgument argument, RawInput rawInput) { - Join join = argument.getAnnotation(); - - int limit = join.limit(); + int limit = argument.getLimit(); List values = new ArrayList<>(); if (!rawInput.hasNext()) { @@ -33,12 +31,12 @@ public ParseResult parseTyped(Invocation invocation, JoinArgumen values.add(rawInput.next()); } - return ParseResult.success(String.join(join.separator(), values)); + return ParseResult.success(String.join(argument.getSeparator(), values)); } @Override public Range getTypedRange(JoinArgument argument) { - return Range.range(1, argument.getAnnotation().limit()); + return Range.range(1, argument.getLimit()); } @Override @@ -46,5 +44,4 @@ public SuggestionResult suggestTyped(Invocation invocation, JoinArgument return SuggestionResult.of("Simple text..."); } - } diff --git a/litecommands-core/src/dev/rollczi/litecommands/meta/MarkMeta.java b/litecommands-core/src/dev/rollczi/litecommands/meta/MarkMeta.java deleted file mode 100644 index 85e863178..000000000 --- a/litecommands-core/src/dev/rollczi/litecommands/meta/MarkMeta.java +++ /dev/null @@ -1,29 +0,0 @@ -package dev.rollczi.litecommands.meta; - -import dev.rollczi.litecommands.annotation.processor.AnnotationInvoker; -import dev.rollczi.litecommands.annotation.processor.AnnotationProcessor; - -import java.lang.annotation.ElementType; -import java.lang.annotation.Retention; -import java.lang.annotation.RetentionPolicy; -import java.lang.annotation.Target; - -@Target({ElementType.PARAMETER}) -@Retention(RetentionPolicy.RUNTIME) -public @interface MarkMeta { - - String key(); - - String value(); - - class AnnotationResolver implements AnnotationProcessor { - - @Override - public AnnotationInvoker process(AnnotationInvoker invoker) { - return invoker.on(MarkMeta.class, (annotation, metaHolder) -> { - metaHolder.meta().put(MetaKey.of(annotation.key(), String.class), annotation.value()); - }); - } - } -} - diff --git a/litecommands-core/src/dev/rollczi/litecommands/meta/MetaListEditor.java b/litecommands-core/src/dev/rollczi/litecommands/meta/MetaListEditor.java index fc6f3b46c..24b301886 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/meta/MetaListEditor.java +++ b/litecommands-core/src/dev/rollczi/litecommands/meta/MetaListEditor.java @@ -1,5 +1,7 @@ package dev.rollczi.litecommands.meta; +import org.jetbrains.annotations.CheckReturnValue; + import java.util.ArrayList; import java.util.Collections; import java.util.List; @@ -16,27 +18,32 @@ public class MetaListEditor { this.mutableList.addAll(list); } + @CheckReturnValue public MetaListEditor add(E element) { this.mutableList.add(element); return this; } + @CheckReturnValue public MetaListEditor remove(E element) { this.mutableList.remove(element); return this; } + @CheckReturnValue public MetaListEditor clear() { this.mutableList.clear(); return this; } @SafeVarargs + @CheckReturnValue public final MetaListEditor addAll(E... value) { Collections.addAll(this.mutableList, value); return this; } + @CheckReturnValue public MetaListEditor addAll(Iterable value) { value.forEach(this.mutableList::add); return this; diff --git a/litecommands-core/src/dev/rollczi/litecommands/permission/Permission.java b/litecommands-core/src/dev/rollczi/litecommands/permission/Permission.java deleted file mode 100644 index 6ae87faf0..000000000 --- a/litecommands-core/src/dev/rollczi/litecommands/permission/Permission.java +++ /dev/null @@ -1,52 +0,0 @@ -package dev.rollczi.litecommands.permission; - -import dev.rollczi.litecommands.annotation.processor.AnnotationInvoker; -import dev.rollczi.litecommands.annotation.processor.AnnotationProcessor; -import dev.rollczi.litecommands.meta.Meta; - -import java.lang.annotation.ElementType; -import java.lang.annotation.Repeatable; -import java.lang.annotation.Retention; -import java.lang.annotation.RetentionPolicy; -import java.lang.annotation.Target; - -@Target({ ElementType.TYPE, ElementType.METHOD }) -@Retention(RetentionPolicy.RUNTIME) -@Repeatable(Permissions.class) -public @interface Permission { - - String[] value(); - - class AnnotationResolver implements AnnotationProcessor { - - @Override - public AnnotationInvoker process(AnnotationInvoker invoker) { - return invoker.on(Permission.class, (annotation, metaHolder) -> { - metaHolder.meta().listEditor(Meta.PERMISSIONS) - .addAll(annotation.value()) - .apply(); - }); - } - } - - class Mock implements Permission { - - private final String[] value; - - public Mock(String[] value) { - this.value = value; - } - - @Override - public String[] value() { - return value; - } - - @Override - public Class annotationType() { - return Permission.class; - } - } - -} - diff --git a/litecommands-core/src/dev/rollczi/litecommands/permission/Permissions.java b/litecommands-core/src/dev/rollczi/litecommands/permission/Permissions.java deleted file mode 100644 index c8a6c8513..000000000 --- a/litecommands-core/src/dev/rollczi/litecommands/permission/Permissions.java +++ /dev/null @@ -1,35 +0,0 @@ -package dev.rollczi.litecommands.permission; - -import dev.rollczi.litecommands.annotation.processor.AnnotationInvoker; -import dev.rollczi.litecommands.annotation.processor.AnnotationProcessor; -import dev.rollczi.litecommands.meta.Meta; - -import java.lang.annotation.ElementType; -import java.lang.annotation.Retention; -import java.lang.annotation.RetentionPolicy; -import java.lang.annotation.Target; - -@Target({ElementType.TYPE, ElementType.METHOD}) -@Retention(RetentionPolicy.RUNTIME) -public @interface Permissions { - - Permission[] value(); - - class AnnotationResolver implements AnnotationProcessor { - - @Override - public AnnotationInvoker process(AnnotationInvoker invoker) { - return invoker.on(Permissions.class, (annotation, metaHolder) -> { - Meta meta = metaHolder.meta(); - - for (Permission permissionAnnotation : annotation.value()) { - meta.listEditor(Meta.PERMISSIONS) - .addAll(permissionAnnotation.value()) - .apply(); - } - }); - } - - } -} - diff --git a/litecommands-core/src/dev/rollczi/litecommands/requirement/ArgumentRequirement.java b/litecommands-core/src/dev/rollczi/litecommands/requirement/ArgumentRequirement.java deleted file mode 100644 index 3bf1f184d..000000000 --- a/litecommands-core/src/dev/rollczi/litecommands/requirement/ArgumentRequirement.java +++ /dev/null @@ -1,12 +0,0 @@ -package dev.rollczi.litecommands.requirement; - -import dev.rollczi.litecommands.argument.Argument; -import dev.rollczi.litecommands.requirement.Requirement; - -public interface ArgumentRequirement extends Requirement { - - Argument getArgument(); - - boolean isWrapperOptional(); - -} diff --git a/litecommands-core/src/dev/rollczi/litecommands/requirement/ArgumentRequirementFactory.java b/litecommands-core/src/dev/rollczi/litecommands/requirement/ArgumentRequirementFactory.java deleted file mode 100644 index 227af8c20..000000000 --- a/litecommands-core/src/dev/rollczi/litecommands/requirement/ArgumentRequirementFactory.java +++ /dev/null @@ -1,48 +0,0 @@ -package dev.rollczi.litecommands.requirement; - -import dev.rollczi.litecommands.argument.Argument; -import dev.rollczi.litecommands.argument.ArgumentFactory; -import dev.rollczi.litecommands.argument.SimpleArgument; -import dev.rollczi.litecommands.argument.parser.ParserRegistry; -import dev.rollczi.litecommands.argument.parser.ParserSet; -import dev.rollczi.litecommands.annotation.AnnotationHolder; -import dev.rollczi.litecommands.wrapper.WrapFormat; -import dev.rollczi.litecommands.wrapper.Wrapper; -import dev.rollczi.litecommands.wrapper.WrapperRegistry; - -import java.lang.annotation.Annotation; - -class ArgumentRequirementFactory implements RequirementFactory { - - private final WrapperRegistry wrapperRegistry; - private final ParserRegistry parserRegistry; - private final ArgumentFactory argumentFactory; - - public ArgumentRequirementFactory(WrapperRegistry wrapperRegistry, ParserRegistry parserRegistry, ArgumentFactory argumentFactory) { - this.parserRegistry = parserRegistry; - this.wrapperRegistry = wrapperRegistry; - this.argumentFactory = argumentFactory; - } - - public ArgumentRequirementFactory(WrapperRegistry wrapperRegistry, ParserRegistry parserRegistry) { - this(wrapperRegistry, parserRegistry, new DefaultArgumentFactory<>()); - } - - @Override - public Requirement create(AnnotationHolder holder) { - WrapFormat wrapFormat = holder.getFormat(); - Argument argument = argumentFactory.create(holder); - Wrapper wrapper = wrapperRegistry.getWrappedExpectedFactory(wrapFormat); - ParserSet parserSet = parserRegistry.getParserSet(wrapFormat.getParsedType(), argument.toKey()); - - return new ArgumentRequirementImpl<>(argument, wrapper, parserSet); - } - - private static final class DefaultArgumentFactory implements ArgumentFactory { - @Override - public Argument create(AnnotationHolder holder) { - return new SimpleArgument<>(holder); - } - } - -} diff --git a/litecommands-core/src/dev/rollczi/litecommands/requirement/ArgumentRequirementImpl.java b/litecommands-core/src/dev/rollczi/litecommands/requirement/ArgumentRequirementImpl.java deleted file mode 100644 index 0f9c22ed7..000000000 --- a/litecommands-core/src/dev/rollczi/litecommands/requirement/ArgumentRequirementImpl.java +++ /dev/null @@ -1,80 +0,0 @@ -package dev.rollczi.litecommands.requirement; - -import dev.rollczi.litecommands.argument.Argument; -import dev.rollczi.litecommands.argument.parser.ParseResult; -import dev.rollczi.litecommands.argument.parser.ParserSet; -import dev.rollczi.litecommands.argument.parser.input.ParseableInputMatcher; -import dev.rollczi.litecommands.invalidusage.InvalidUsage; -import dev.rollczi.litecommands.invocation.Invocation; -import dev.rollczi.litecommands.meta.Meta; -import dev.rollczi.litecommands.meta.MetaHolder; -import dev.rollczi.litecommands.annotation.AnnotationHolder; -import dev.rollczi.litecommands.shared.FailedReason; -import dev.rollczi.litecommands.wrapper.WrapFormat; -import dev.rollczi.litecommands.wrapper.Wrapper; -import org.jetbrains.annotations.Nullable; - -class ArgumentRequirementImpl implements ArgumentRequirement { - - private final Argument argument; - private final Wrapper wrapper; - private final ParserSet parserSet; - private final Meta meta = Meta.create(); - - public ArgumentRequirementImpl(Argument argument, Wrapper wrapper, ParserSet parserSet) { - this.argument = argument; - this.wrapper = wrapper; - this.parserSet = parserSet; - } - - @Override - public String getName() { - return argument.getAnnotationHolder().getName(); - } - - @Override - public AnnotationHolder getAnnotationHolder() { - return argument.getAnnotationHolder(); - } - - @Override - public > RequirementResult match(Invocation invocation, MATCHER matcher) { - ParseResult result = matcher.nextArgument(invocation, argument, parserSet); - WrapFormat wrapFormat = argument.getAnnotationHolder().getFormat(); - - if (result.isSuccessful()) { - PARSED successfulResult = result.getSuccessfulResult(); - - return RequirementResult.success(wrapper.create(successfulResult, wrapFormat)); - } - - FailedReason failedReason = result.getFailedReason(); - - if (failedReason.getReason() == InvalidUsage.Cause.MISSING_ARGUMENT && wrapper.canCreateEmpty()) { - return RequirementResult.success(wrapper.createEmpty(wrapFormat)); - } - - return RequirementResult.failure(failedReason); - } - - @Override - public Argument getArgument() { - return argument; - } - - @Override - public boolean isWrapperOptional() { - return wrapper.canCreateEmpty(); - } - - @Override - public Meta meta() { - return this.meta; - } - - @Override - public @Nullable MetaHolder parentMeta() { - return null; - } - -} diff --git a/litecommands-core/src/dev/rollczi/litecommands/requirement/ContextRequirement.java b/litecommands-core/src/dev/rollczi/litecommands/requirement/ContextRequirement.java index 64820a62c..7778fd172 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/requirement/ContextRequirement.java +++ b/litecommands-core/src/dev/rollczi/litecommands/requirement/ContextRequirement.java @@ -1,7 +1,17 @@ package dev.rollczi.litecommands.requirement; -import dev.rollczi.litecommands.requirement.Requirement; +import dev.rollczi.litecommands.wrapper.WrapFormat; -public interface ContextRequirement extends Requirement { +import java.util.function.Supplier; + +public interface ContextRequirement extends Requirement { + + static ContextRequirement of(Supplier name, Class type) { + return new ContextRequirementImpl<>(name, WrapFormat.notWrapped(type)); + } + + static ContextRequirement of(Supplier name, WrapFormat format) { + return new ContextRequirementImpl<>(name, format); + } } diff --git a/litecommands-core/src/dev/rollczi/litecommands/requirement/ContextRequirementFactory.java b/litecommands-core/src/dev/rollczi/litecommands/requirement/ContextRequirementFactory.java deleted file mode 100644 index 222ed74d6..000000000 --- a/litecommands-core/src/dev/rollczi/litecommands/requirement/ContextRequirementFactory.java +++ /dev/null @@ -1,28 +0,0 @@ -package dev.rollczi.litecommands.requirement; - -import dev.rollczi.litecommands.context.ContextRegistry; -import dev.rollczi.litecommands.annotation.AnnotationHolder; -import dev.rollczi.litecommands.wrapper.Wrapper; -import dev.rollczi.litecommands.wrapper.WrapperRegistry; -import dev.rollczi.litecommands.wrapper.WrapFormat; - -import java.lang.annotation.Annotation; - -class ContextRequirementFactory implements RequirementFactory { - - private final ContextRegistry contextRegistry; - private final WrapperRegistry wrapperRegistry; - - public ContextRequirementFactory(ContextRegistry contextRegistry, WrapperRegistry wrapperRegistry) { - this.contextRegistry = contextRegistry; - this.wrapperRegistry = wrapperRegistry; - } - - @Override - public Requirement create(AnnotationHolder holder) { - WrapFormat wrapFormat = holder.getFormat(); - Wrapper wrapper = wrapperRegistry.getWrappedExpectedFactory(wrapFormat); - return new ContextRequirementImpl<>(this.contextRegistry, holder, wrapper); - } - -} diff --git a/litecommands-core/src/dev/rollczi/litecommands/requirement/ContextRequirementImpl.java b/litecommands-core/src/dev/rollczi/litecommands/requirement/ContextRequirementImpl.java index bcc4fac81..cb8257b18 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/requirement/ContextRequirementImpl.java +++ b/litecommands-core/src/dev/rollczi/litecommands/requirement/ContextRequirementImpl.java @@ -1,51 +1,32 @@ package dev.rollczi.litecommands.requirement; -import dev.rollczi.litecommands.argument.parser.input.ParseableInputMatcher; -import dev.rollczi.litecommands.context.ContextRegistry; -import dev.rollczi.litecommands.context.ContextResult; -import dev.rollczi.litecommands.invocation.Invocation; import dev.rollczi.litecommands.meta.Meta; import dev.rollczi.litecommands.meta.MetaHolder; -import dev.rollczi.litecommands.annotation.AnnotationHolder; import dev.rollczi.litecommands.wrapper.WrapFormat; -import dev.rollczi.litecommands.wrapper.Wrapper; import org.jetbrains.annotations.Nullable; -import java.lang.annotation.Annotation; +import java.util.function.Supplier; -class ContextRequirementImpl implements ContextRequirement { +class ContextRequirementImpl implements ContextRequirement { - private final ContextRegistry contextRegistry; - private final AnnotationHolder holder; - private final Wrapper wrapper; + private final Supplier name; + private final WrapFormat format; private final Meta meta = Meta.create(); - ContextRequirementImpl(ContextRegistry contextRegistry, AnnotationHolder holder, Wrapper wrapper) { - this.contextRegistry = contextRegistry; - this.holder = holder; - this.wrapper = wrapper; + ContextRequirementImpl(Supplier name, WrapFormat format) { + this.name = name; + this.format = format; } + @Override public String getName() { - return this.holder.getName(); + return name.get(); } @Override - public AnnotationHolder getAnnotationHolder() { - return holder; - } - - @Override - public > RequirementResult match(Invocation invocation, CONTEXT matcher) { - WrapFormat wrapFormat = holder.getFormat(); - ContextResult result = contextRegistry.provideContext(wrapFormat.getParsedType(), invocation); - - if (result.hasResult()) { - return RequirementResult.success(wrapper.create(result.getResult(), wrapFormat)); - } - - return RequirementResult.failure(result.getError()); + public WrapFormat getWrapperFormat() { + return format; } @Override @@ -57,4 +38,5 @@ public Meta meta() { public @Nullable MetaHolder parentMeta() { return null; } + } diff --git a/litecommands-core/src/dev/rollczi/litecommands/requirement/Requirement.java b/litecommands-core/src/dev/rollczi/litecommands/requirement/Requirement.java index 9ea578c58..0f81b0c80 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/requirement/Requirement.java +++ b/litecommands-core/src/dev/rollczi/litecommands/requirement/Requirement.java @@ -1,19 +1,12 @@ package dev.rollczi.litecommands.requirement; -import dev.rollczi.litecommands.argument.parser.input.ParseableInputMatcher; -import dev.rollczi.litecommands.invocation.Invocation; import dev.rollczi.litecommands.meta.MetaHolder; -import dev.rollczi.litecommands.annotation.AnnotationHolder; +import dev.rollczi.litecommands.wrapper.WrapFormat; -public interface Requirement extends MetaHolder { +public interface Requirement extends MetaHolder { String getName(); - AnnotationHolder getAnnotationHolder(); - - > RequirementResult match( - Invocation invocation, - MATCHER matcher - ); + WrapFormat getWrapperFormat(); } diff --git a/litecommands-core/src/dev/rollczi/litecommands/requirement/RequirementFactory.java b/litecommands-core/src/dev/rollczi/litecommands/requirement/RequirementFactory.java deleted file mode 100644 index 496fad35c..000000000 --- a/litecommands-core/src/dev/rollczi/litecommands/requirement/RequirementFactory.java +++ /dev/null @@ -1,11 +0,0 @@ -package dev.rollczi.litecommands.requirement; - -import dev.rollczi.litecommands.annotation.AnnotationHolder; - -import java.lang.annotation.Annotation; - -public interface RequirementFactory { - - Requirement create(AnnotationHolder holder); - -} diff --git a/litecommands-core/src/dev/rollczi/litecommands/requirement/RequirementFactoryRegistry.java b/litecommands-core/src/dev/rollczi/litecommands/requirement/RequirementFactoryRegistry.java deleted file mode 100644 index c7f0defef..000000000 --- a/litecommands-core/src/dev/rollczi/litecommands/requirement/RequirementFactoryRegistry.java +++ /dev/null @@ -1,29 +0,0 @@ -package dev.rollczi.litecommands.requirement; - -import dev.rollczi.litecommands.annotation.AnnotationHolder; - -import java.lang.annotation.Annotation; -import java.util.HashMap; -import java.util.Map; - -public class RequirementFactoryRegistry { - - private final Map, RequirementFactory> annotations = new HashMap<>(); - - public void registerFactory(Class type, RequirementFactory argumentFactory) { - annotations.put(type, argumentFactory); - } - - @SuppressWarnings("unchecked") - public Requirement create(AnnotationHolder holder) { - A annotation = holder.getAnnotation(); - RequirementFactory factory = (RequirementFactory) annotations.get(annotation.annotationType()); - - if (factory == null) { - throw new IllegalArgumentException("Argument factory for annotation " + annotation.annotationType().getName() + " not found"); - } - - return factory.create(holder); - } - -} diff --git a/litecommands-core/src/dev/rollczi/litecommands/requirement/RequirementMatch.java b/litecommands-core/src/dev/rollczi/litecommands/requirement/RequirementMatch.java index 108fa7adb..b32d976de 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/requirement/RequirementMatch.java +++ b/litecommands-core/src/dev/rollczi/litecommands/requirement/RequirementMatch.java @@ -2,7 +2,7 @@ import dev.rollczi.litecommands.wrapper.Wrap; -public class RequirementMatch, T> { +public class RequirementMatch, T> { private final REQUIREMENT requirement; private final Wrap result; diff --git a/litecommands-core/src/dev/rollczi/litecommands/requirement/RequirementProcessor.java b/litecommands-core/src/dev/rollczi/litecommands/requirement/RequirementProcessor.java deleted file mode 100644 index 0fc453293..000000000 --- a/litecommands-core/src/dev/rollczi/litecommands/requirement/RequirementProcessor.java +++ /dev/null @@ -1,37 +0,0 @@ -package dev.rollczi.litecommands.requirement; - -import dev.rollczi.litecommands.annotation.processor.AnnotationInvoker; -import dev.rollczi.litecommands.annotation.processor.AnnotationProcessor; -import dev.rollczi.litecommands.argument.parser.ParserRegistry; -import dev.rollczi.litecommands.context.ContextRegistry; -import dev.rollczi.litecommands.argument.ArgumentFactory; -import dev.rollczi.litecommands.wrapper.WrapperRegistry; - -import java.lang.annotation.Annotation; - -public class RequirementProcessor implements AnnotationProcessor { - - private final RequirementFactory requirementFactory; - private final Class annotationClass; - - public RequirementProcessor(WrapperRegistry wrapperRegistry, ParserRegistry parserRegistry, Class annotationClass, ArgumentFactory argumentFactory) { - this.requirementFactory = new ArgumentRequirementFactory<>(wrapperRegistry, parserRegistry, argumentFactory); - this.annotationClass = annotationClass; - } - - public RequirementProcessor(ContextRegistry contextRegistry, WrapperRegistry wrapperRegistry, Class annotationClass) { - this.requirementFactory = new ContextRequirementFactory<>(contextRegistry, wrapperRegistry); - this.annotationClass = annotationClass; - } - - @Override - public AnnotationInvoker process(AnnotationInvoker invoker) { - return invoker.onRequirement(annotationClass, (holder, builder, executorBuilder) -> { - Requirement requirement = requirementFactory.create(holder); - executorBuilder.addRequirement(requirement); - - return builder; - }); - } - -} diff --git a/litecommands-core/src/dev/rollczi/litecommands/requirement/RequirementsResult.java b/litecommands-core/src/dev/rollczi/litecommands/requirement/RequirementsResult.java index b9bb5a72b..2bd38b45d 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/requirement/RequirementsResult.java +++ b/litecommands-core/src/dev/rollczi/litecommands/requirement/RequirementsResult.java @@ -8,9 +8,9 @@ public class RequirementsResult { private final Invocation invocation; - private final Map> matches; + private final Map> matches; - private RequirementsResult(Invocation invocation, Map> matches) { + private RequirementsResult(Invocation invocation, Map> matches) { this.invocation = invocation; this.matches = matches; } @@ -19,7 +19,7 @@ public boolean has(String name) { return matches.containsKey(name); } - public RequirementMatch get(String name) { + public RequirementMatch get(String name) { return matches.get(name); } @@ -34,13 +34,13 @@ public static Builder builder(Invocation invocation) { public static class Builder { private final Invocation invocation; - private final Map> matches = new HashMap<>(); + private final Map> matches = new HashMap<>(); public Builder(Invocation invocation) { this.invocation = invocation; } - public Builder add(String name, RequirementMatch match) { + public Builder add(String name, RequirementMatch match) { if (matches.containsKey(name)) { throw new IllegalArgumentException("Requirement match with name '" + name + "' already exists"); } diff --git a/litecommands-core/src/dev/rollczi/litecommands/schematic/SchematicGenerator.java b/litecommands-core/src/dev/rollczi/litecommands/schematic/SchematicGenerator.java index ea6741273..f988aee6d 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/schematic/SchematicGenerator.java +++ b/litecommands-core/src/dev/rollczi/litecommands/schematic/SchematicGenerator.java @@ -1,13 +1,14 @@ package dev.rollczi.litecommands.schematic; import dev.rollczi.litecommands.validator.ValidatorService; +import dev.rollczi.litecommands.wrapper.WrapperRegistry; public interface SchematicGenerator { Schematic generate(SchematicInput schematicInput); - static SchematicGenerator from(SchematicFormat format, ValidatorService validatorService) { - return new SchematicGeneratorSimpleImpl<>(format, validatorService); + static SchematicGenerator from(SchematicFormat format, ValidatorService validatorService, WrapperRegistry wrapperRegistry) { + return new SchematicGeneratorSimpleImpl<>(format, validatorService, wrapperRegistry); } } diff --git a/litecommands-core/src/dev/rollczi/litecommands/schematic/SchematicGeneratorSimpleImpl.java b/litecommands-core/src/dev/rollczi/litecommands/schematic/SchematicGeneratorSimpleImpl.java index e37f23b6e..36846bd06 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/schematic/SchematicGeneratorSimpleImpl.java +++ b/litecommands-core/src/dev/rollczi/litecommands/schematic/SchematicGeneratorSimpleImpl.java @@ -1,10 +1,11 @@ package dev.rollczi.litecommands.schematic; +import dev.rollczi.litecommands.argument.Argument; import dev.rollczi.litecommands.command.CommandRoute; import dev.rollczi.litecommands.command.executor.CommandExecutor; -import dev.rollczi.litecommands.requirement.ArgumentRequirement; import dev.rollczi.litecommands.invocation.Invocation; import dev.rollczi.litecommands.validator.ValidatorService; +import dev.rollczi.litecommands.wrapper.WrapperRegistry; import java.util.List; import java.util.stream.Collectors; @@ -16,10 +17,12 @@ class SchematicGeneratorSimpleImpl implements SchematicGenerator private final SchematicFormat format; private final ValidatorService validatorService; + private final WrapperRegistry wrapperRegistry; - public SchematicGeneratorSimpleImpl(SchematicFormat format, ValidatorService validatorService) { + public SchematicGeneratorSimpleImpl(SchematicFormat format, ValidatorService validatorService, WrapperRegistry wrapperRegistry) { this.format = format; this.validatorService = validatorService; + this.wrapperRegistry = wrapperRegistry; } @Override @@ -56,11 +59,13 @@ private Stream generateRoute(String base, Invocation invocation, } private String generateExecutor(CommandExecutor executor) { - return executor.getRequirements().stream() - .filter(requirement -> requirement instanceof ArgumentRequirement) - .map(requirement -> (ArgumentRequirement) requirement) - .map(requirement -> String.format(requirement.isWrapperOptional() || requirement.getArgument().hasDefaultValue() ? format.optionalArgumentFormat() : format.argumentFormat(), requirement.getArgument().getName())) + return executor.getArguments().stream() + .map(argument -> String.format(this.isOptional(argument) ? format.optionalArgumentFormat() : format.argumentFormat(), argument.getName())) .collect(Collectors.joining(SEPARATOR)); } + private boolean isOptional(Argument argument) { + return wrapperRegistry.getWrappedExpectedFactory(argument.getWrapperFormat()).canCreateEmpty() || argument.hasDefaultValue(); + } + } diff --git a/litecommands-core/src/dev/rollczi/litecommands/suggestion/SuggestionService.java b/litecommands-core/src/dev/rollczi/litecommands/suggestion/SuggestionService.java index 355c3df25..1f6ee2229 100644 --- a/litecommands-core/src/dev/rollczi/litecommands/suggestion/SuggestionService.java +++ b/litecommands-core/src/dev/rollczi/litecommands/suggestion/SuggestionService.java @@ -9,8 +9,6 @@ import dev.rollczi.litecommands.argument.parser.ParserSet; import dev.rollczi.litecommands.command.executor.CommandExecutor; import dev.rollczi.litecommands.command.CommandRoute; -import dev.rollczi.litecommands.requirement.ArgumentRequirement; -import dev.rollczi.litecommands.requirement.Requirement; import dev.rollczi.litecommands.flow.Flow; import dev.rollczi.litecommands.invocation.Invocation; import dev.rollczi.litecommands.validator.ValidatorService; @@ -84,12 +82,8 @@ public > SuggestionResult sugges ) { SuggestionResult collector = SuggestionResult.empty(); - for (Requirement requirement : executor.getRequirements()) { - if (!(requirement instanceof ArgumentRequirement)) { - continue; - } - - SuggestionInputResult result = suggestRequirement(invocation, matcher, (ArgumentRequirement) requirement); + for (Argument argument : executor.getArguments()) { + SuggestionInputResult result = suggestArgument(invocation, matcher, argument); collector.addAll(result.getResult()); switch (result.getCause()) { @@ -102,16 +96,6 @@ public > SuggestionResult sugges return collector; } - private > SuggestionInputResult suggestRequirement( - Invocation invocation, - MATCHER matcher, - ArgumentRequirement requirement - ) { - Argument argument = requirement.getArgument(); - - return suggestArgument(invocation, matcher, argument); - } - private > SuggestionInputResult suggestArgument( Invocation invocation, MATCHER matcher, diff --git a/litecommands-core/src/dev/rollczi/litecommands/validator/Validate.java b/litecommands-core/src/dev/rollczi/litecommands/validator/Validate.java deleted file mode 100644 index 71e63c208..000000000 --- a/litecommands-core/src/dev/rollczi/litecommands/validator/Validate.java +++ /dev/null @@ -1,31 +0,0 @@ -package dev.rollczi.litecommands.validator; - -import dev.rollczi.litecommands.annotation.processor.AnnotationInvoker; -import dev.rollczi.litecommands.annotation.processor.AnnotationProcessor; -import dev.rollczi.litecommands.meta.Meta; - -import java.lang.annotation.ElementType; -import java.lang.annotation.Retention; -import java.lang.annotation.RetentionPolicy; -import java.lang.annotation.Target; - -@Target({ElementType.TYPE, ElementType.METHOD}) -@Retention(RetentionPolicy.RUNTIME) -public @interface Validate { - - Class>[] value(); - - class AnnotationResolver implements AnnotationProcessor { - - @Override - public AnnotationInvoker process(AnnotationInvoker invoker) { - return invoker.on(Validate.class, (annotation, metaHolder) -> { - metaHolder.meta().listEditor(Meta.VALIDATORS) - .addAll(annotation.value()) - .apply(); - }); - } - } - -} - diff --git a/litecommands-core/test/dev/rollczi/litecommands/permission/MissingPermissionValidatorTest.java b/litecommands-core/test/dev/rollczi/litecommands/permission/MissingPermissionValidatorTest.java index e22a0ff73..2af1cf602 100644 --- a/litecommands-core/test/dev/rollczi/litecommands/permission/MissingPermissionValidatorTest.java +++ b/litecommands-core/test/dev/rollczi/litecommands/permission/MissingPermissionValidatorTest.java @@ -3,7 +3,6 @@ import dev.rollczi.litecommands.command.executor.CommandExecutor; import dev.rollczi.litecommands.command.CommandRoute; import dev.rollczi.litecommands.command.builder.CommandBuilder; -import dev.rollczi.litecommands.command.builder.CommandBuilderExecutor; import dev.rollczi.litecommands.flow.Flow; import dev.rollczi.litecommands.invocation.Invocation; import dev.rollczi.litecommands.meta.Meta; @@ -38,14 +37,9 @@ void test() { .add("permission.test") .apply() ) - .appendChild("sub", childContext -> { - CommandBuilderExecutor builder = new CommandBuilderExecutor(childContext, (parent, requirementList) -> new TestExecutor<>(parent)) - .applyMeta(meta -> meta.listEditor(Meta.PERMISSIONS).add("permission.sub.execute").apply()); - - return childContext - .applyMeta(meta -> meta.put(Meta.PERMISSIONS, Arrays.asList("permission.sub"))) - .appendExecutor(builder); - })); + .appendChild("sub", childContext -> childContext + .applyMeta(meta -> meta.listEditor(Meta.PERMISSIONS).add("permission.sub").apply()) + .appendExecutor(parent -> new TestExecutor<>(parent).onMeta(meta -> meta.listEditor(Meta.PERMISSIONS).add("permission.sub.execute").apply())))); CommandRoute sub = assertPresent(test.getChild("sub")); CommandExecutor executor = sub.getExecutors().get(0); diff --git a/litecommands-core/test/dev/rollczi/litecommands/requirement/MethodCommandExecutorFactoryTest.java b/litecommands-core/test/dev/rollczi/litecommands/requirement/MethodCommandExecutorFactoryTest.java deleted file mode 100644 index 84ff70dfa..000000000 --- a/litecommands-core/test/dev/rollczi/litecommands/requirement/MethodCommandExecutorFactoryTest.java +++ /dev/null @@ -1,52 +0,0 @@ -package dev.rollczi.litecommands.requirement; - -import dev.rollczi.litecommands.annotation.AnnotationHolder; -import dev.rollczi.litecommands.requirement.RequirementFactory; -import dev.rollczi.litecommands.requirement.RequirementFactoryRegistry; -import dev.rollczi.litecommands.argument.Arg; -import dev.rollczi.litecommands.argument.ArgArgumentFactory; -import dev.rollczi.litecommands.context.Context; -import dev.rollczi.litecommands.command.executor.Execute; -import dev.rollczi.litecommands.argument.ArgumentKey; -import dev.rollczi.litecommands.argument.parser.ParserRegistry; -import dev.rollczi.litecommands.argument.parser.ParserRegistryImpl; -import dev.rollczi.litecommands.argument.resolver.std.NumberArgumentResolver; -import dev.rollczi.litecommands.argument.resolver.std.StringArgumentResolver; -import dev.rollczi.litecommands.context.ContextRegistry; -import dev.rollczi.litecommands.context.ContextResult; -import dev.rollczi.litecommands.invocation.Invocation; -import dev.rollczi.litecommands.requirement.RequirementProcessor; -import dev.rollczi.litecommands.unit.TestSender; -import dev.rollczi.litecommands.wrapper.WrapFormat; -import dev.rollczi.litecommands.wrapper.WrapperRegistry; -import org.junit.jupiter.api.BeforeAll; -import org.junit.jupiter.api.Test; - -import static org.junit.jupiter.api.Assertions.assertEquals; - -class MethodCommandExecutorFactoryTest { - - static final ContextRegistry CONTEXT_REGISTRY = new ContextRegistry<>(); - static final ParserRegistry PARSER_REGISTRY = new ParserRegistryImpl<>(); - static final WrapperRegistry WRAPPER_REGISTRY = new WrapperRegistry(); - static final RequirementFactoryRegistry REQUIREMENT_FACTORY_REGISTRY = new RequirementFactoryRegistry<>(); - - @BeforeAll - static void beforeAll() { - CONTEXT_REGISTRY.registerProvider(Invocation.class, invocation -> ContextResult.ok(() -> invocation)); // Do not use short method reference here (it will cause bad return type in method reference on Java 8) - PARSER_REGISTRY.registerParser(String.class, ArgumentKey.of(), new StringArgumentResolver<>()); - PARSER_REGISTRY.registerParser(int.class, ArgumentKey.of(), NumberArgumentResolver.ofInteger()); - - REQUIREMENT_FACTORY_REGISTRY.registerFactory(Context.class, new ContextRequirementFactory<>(CONTEXT_REGISTRY, WRAPPER_REGISTRY)); - REQUIREMENT_FACTORY_REGISTRY.registerFactory(Arg.class, new ArgumentRequirementFactory<>(WRAPPER_REGISTRY, PARSER_REGISTRY, new ArgArgumentFactory())); - } - - @Test - void testCreateMethodOfExecuteFactory() { - AnnotationHolder holder = AnnotationHolder.of(new Arg.Mock("name"), WrapFormat.notWrapped(String.class), () -> "name"); - Requirement requirement = REQUIREMENT_FACTORY_REGISTRY.create(holder); - - assertEquals("name", requirement.getName()); - } - -} \ No newline at end of file diff --git a/litecommands-core/test/dev/rollczi/litecommands/schematic/SchematicGeneratorTest.java b/litecommands-core/test/dev/rollczi/litecommands/schematic/SchematicGeneratorTest.java index d32b01b60..aa5e42d27 100644 --- a/litecommands-core/test/dev/rollczi/litecommands/schematic/SchematicGeneratorTest.java +++ b/litecommands-core/test/dev/rollczi/litecommands/schematic/SchematicGeneratorTest.java @@ -8,6 +8,7 @@ import dev.rollczi.litecommands.unit.TestExecutor; import dev.rollczi.litecommands.unit.TestUtil; import dev.rollczi.litecommands.validator.ValidatorService; +import dev.rollczi.litecommands.wrapper.WrapperRegistry; import org.junit.jupiter.api.BeforeAll; import org.junit.jupiter.api.Test; @@ -19,8 +20,9 @@ @SuppressWarnings({"rawtypes", "unchecked"}) class SchematicGeneratorTest { + static WrapperRegistry wrapperRegistry = new WrapperRegistry(); static ValidatorService validatorService = new ValidatorService(); - static SchematicGenerator schematicGenerator = SchematicGenerator.from(SchematicFormat.angleBrackets(), validatorService); + static SchematicGenerator schematicGenerator = SchematicGenerator.from(SchematicFormat.angleBrackets(), validatorService, wrapperRegistry); @BeforeAll static void beforeAll() { diff --git a/litecommands-jda/src/dev/rollczi/litecommands/jda/JDACommandTranslator.java b/litecommands-jda/src/dev/rollczi/litecommands/jda/JDACommandTranslator.java index b40b7e255..86be09112 100644 --- a/litecommands-jda/src/dev/rollczi/litecommands/jda/JDACommandTranslator.java +++ b/litecommands-jda/src/dev/rollczi/litecommands/jda/JDACommandTranslator.java @@ -4,12 +4,11 @@ import dev.rollczi.litecommands.command.executor.CommandExecutor; import dev.rollczi.litecommands.command.CommandRoute; import dev.rollczi.litecommands.input.Input; -import dev.rollczi.litecommands.requirement.ArgumentRequirement; -import dev.rollczi.litecommands.requirement.Requirement; import dev.rollczi.litecommands.invocation.Invocation; import dev.rollczi.litecommands.invocation.InvocationContext; import dev.rollczi.litecommands.meta.Meta; import dev.rollczi.litecommands.shared.Preconditions; +import dev.rollczi.litecommands.wrapper.WrapperRegistry; import net.dv8tion.jda.api.entities.Guild; import net.dv8tion.jda.api.entities.Member; import net.dv8tion.jda.api.entities.User; @@ -33,9 +32,15 @@ class JDACommandTranslator { + private final WrapperRegistry wrapperRegistry; + private final Map, JDAType> jdaSupportedTypes = new HashMap<>(); private final Map, JDATypeOverlay> jdaTypeOverlays = new HashMap<>(); + JDACommandTranslator(WrapperRegistry wrapperRegistry) { + this.wrapperRegistry = wrapperRegistry; + } + JDACommandTranslator type(Class type, OptionType optionType, JDATypeMapper mapper) { jdaSupportedTypes.put(type, new JDAType<>(type, optionType, mapper)); return this; @@ -116,15 +121,10 @@ private void translateExecutor(CommandRoute route, TranslateExe CommandExecutor executor = executors.get(0); - for (Requirement requirement : executor.getRequirements()) { - if (!(requirement instanceof ArgumentRequirement argumentRequirement)) { - continue; - } - - Argument argument = argumentRequirement.getArgument(); + for (Argument argument : executor.getArguments()) { String argumentName = argument.getName(); String description = /*argument.getDescription();*/ "test"; //TODO: Add description to Argument - boolean isRequired = !argumentRequirement.isWrapperOptional(); + boolean isRequired = !wrapperRegistry.getWrappedExpectedFactory(argument.getWrapperFormat()).canCreateEmpty(); Class parsedType = argument.getWrapperFormat().getParsedType(); if (jdaSupportedTypes.containsKey(parsedType)) { diff --git a/litecommands-jda/src/dev/rollczi/litecommands/jda/JDAPlatform.java b/litecommands-jda/src/dev/rollczi/litecommands/jda/JDAPlatform.java index c860fb12e..9ee17fe12 100644 --- a/litecommands-jda/src/dev/rollczi/litecommands/jda/JDAPlatform.java +++ b/litecommands-jda/src/dev/rollczi/litecommands/jda/JDAPlatform.java @@ -24,7 +24,6 @@ class JDAPlatform extends AbstractPlatform { private final JDA jda; - private final JDACommandTranslator translator; private final Map, JDACommandRecord> commands = new HashMap<>(); private record JDACommandRecord( @@ -33,16 +32,15 @@ private record JDACommandRecord( PlatformSuggestionListener suggestionHook ) {} - JDAPlatform(LiteJDASettings settings, JDA jda, JDACommandTranslator translator) { + JDAPlatform(LiteJDASettings settings, JDA jda) { super(settings); this.jda = jda; - this.translator = translator; this.jda.addEventListener(new SlashCommandController()); } @Override protected void hook(CommandRoute commandRoute, PlatformInvocationListener invocationHook, PlatformSuggestionListener suggestionHook) { - JDACommandTranslator.JDALiteCommand translated = translator.translate(commandRoute.getName(), commandRoute); + JDACommandTranslator.JDALiteCommand translated = settings.translator().translate(commandRoute.getName(), commandRoute); for (String name : commandRoute.names()) { this.jda.upsertCommand(translated.jdaCommandData().setName(name)) @@ -89,8 +87,8 @@ public void onSlashCommandInteraction(SlashCommandInteractionEvent event) { } PlatformInvocationListener invocationHook = commandRecord.invocationHook(); - JDAParseableInput arguments = translator.translateArguments(commandRecord.command(), event); - Invocation invocation = translator.translateInvocation(commandRoute, arguments, event); + JDAParseableInput arguments = settings.translator().translateArguments(commandRecord.command(), event); + Invocation invocation = settings.translator().translateInvocation(commandRoute, arguments, event); invocationHook.execute(invocation, arguments); } @@ -111,8 +109,8 @@ public void onCommandAutoCompleteInteraction(CommandAutoCompleteInteractionEvent throw new IllegalStateException("Command record not found for command: " + commandRoute.getName()); } - JDASuggestionInput arguments = translator.translateSuggestions(event); - Invocation invocation = translator.translateInvocation(commandRoute, arguments, event); + JDASuggestionInput arguments = settings.translator().translateSuggestions(event); + Invocation invocation = settings.translator().translateInvocation(commandRoute, arguments, event); SuggestionResult result = commandRecord.suggestionHook().suggest(invocation, arguments); List choiceList = result.getSuggestions().stream() .filter(suggestion -> !suggestion.multilevel().isEmpty()) diff --git a/litecommands-jda/src/dev/rollczi/litecommands/jda/LiteJDAFactory.java b/litecommands-jda/src/dev/rollczi/litecommands/jda/LiteJDAFactory.java index a9a74124e..36545704b 100644 --- a/litecommands-jda/src/dev/rollczi/litecommands/jda/LiteJDAFactory.java +++ b/litecommands-jda/src/dev/rollczi/litecommands/jda/LiteJDAFactory.java @@ -4,6 +4,7 @@ import dev.rollczi.litecommands.builder.LiteCommandsBuilder; import dev.rollczi.litecommands.context.ContextResult; import dev.rollczi.litecommands.invocation.Invocation; +import dev.rollczi.litecommands.wrapper.WrapperRegistry; import net.dv8tion.jda.api.JDA; import net.dv8tion.jda.api.entities.Guild; import net.dv8tion.jda.api.entities.IMentionable; @@ -23,27 +24,10 @@ private LiteJDAFactory() { } public static LiteCommandsBuilder builder(JDA jda) { - JDACommandTranslator translator = new JDACommandTranslator() - .type(String.class, OptionType.STRING, option -> option.getAsString()) - .type(Long.class, OptionType.INTEGER, option -> option.getAsLong()) - .type(long.class, OptionType.INTEGER, option -> option.getAsLong()) - .type(Integer.class, OptionType.INTEGER, option -> option.getAsInt()) - .type(int.class, OptionType.INTEGER, option -> option.getAsInt()) - .type(Boolean.class, OptionType.BOOLEAN, option -> option.getAsBoolean()) - .type(boolean.class, OptionType.BOOLEAN, option -> option.getAsBoolean()) - .type(User.class, OptionType.USER, option -> option.getAsUser()) - .type(double.class, OptionType.NUMBER, option -> option.getAsDouble()) - .type(Attachment.class, OptionType.ATTACHMENT, option -> option.getAsAttachment()) - .type(Role.class, OptionType.ROLE, option -> option.getAsRole()) - .type(IMentionable.class, OptionType.MENTIONABLE, option -> option.getAsMentionable()) - .type(Channel.class, OptionType.CHANNEL, option -> option.getAsChannel()) - - .typeOverlay(Float.class, OptionType.NUMBER, option -> option.getAsString()) - .typeOverlay(float.class, OptionType.NUMBER, option -> option.getAsString()) - .typeOverlay(Member.class, OptionType.USER, option -> option.getAsString()) // TODO: Add raw member parer - ; + JDAPlatform platform = new JDAPlatform(new LiteJDASettings(), jda); - return LiteCommandsFactory.builder(User.class, new JDAPlatform(new LiteJDASettings(), jda, translator)) + return LiteCommandsFactory.builder(User.class, platform).selfProcessor((builder, pattern) -> builder + .settings(settings -> settings.translator(createTranslator(pattern.getWrapperRegistry()))) .bind(JDA.class, () -> jda) .result(String.class, new StringHandler()) .result(RestAction.class, new RestActionHandler()) @@ -52,6 +36,28 @@ private LiteJDAFactory() { .context(MessageChannelUnion.class, invocation -> from(invocation, MessageChannelUnion.class)) .context(Member.class, invocation -> from(invocation, Member.class)) .context(SlashCommandInteractionEvent.class, invocation -> from(invocation, SlashCommandInteractionEvent.class)) + ); + } + + private static JDACommandTranslator createTranslator(WrapperRegistry wrapperRegistry) { + return new JDACommandTranslator(wrapperRegistry) + .type(String.class, OptionType.STRING, option -> option.getAsString()) + .type(Long.class, OptionType.INTEGER, option -> option.getAsLong()) + .type(long.class, OptionType.INTEGER, option -> option.getAsLong()) + .type(Integer.class, OptionType.INTEGER, option -> option.getAsInt()) + .type(int.class, OptionType.INTEGER, option -> option.getAsInt()) + .type(Boolean.class, OptionType.BOOLEAN, option -> option.getAsBoolean()) + .type(boolean.class, OptionType.BOOLEAN, option -> option.getAsBoolean()) + .type(User.class, OptionType.USER, option -> option.getAsUser()) + .type(double.class, OptionType.NUMBER, option -> option.getAsDouble()) + .type(Attachment.class, OptionType.ATTACHMENT, option -> option.getAsAttachment()) + .type(Role.class, OptionType.ROLE, option -> option.getAsRole()) + .type(IMentionable.class, OptionType.MENTIONABLE, option -> option.getAsMentionable()) + .type(Channel.class, OptionType.CHANNEL, option -> option.getAsChannel()) + + .typeOverlay(Float.class, OptionType.NUMBER, option -> option.getAsString()) + .typeOverlay(float.class, OptionType.NUMBER, option -> option.getAsString()) + .typeOverlay(Member.class, OptionType.USER, option -> option.getAsString()) // TODO: Add raw member parer ; } diff --git a/litecommands-jda/src/dev/rollczi/litecommands/jda/LiteJDASettings.java b/litecommands-jda/src/dev/rollczi/litecommands/jda/LiteJDASettings.java index 338a7c5fd..051a87464 100644 --- a/litecommands-jda/src/dev/rollczi/litecommands/jda/LiteJDASettings.java +++ b/litecommands-jda/src/dev/rollczi/litecommands/jda/LiteJDASettings.java @@ -3,4 +3,16 @@ import dev.rollczi.litecommands.platform.PlatformSettings; public class LiteJDASettings implements PlatformSettings { + + private JDACommandTranslator translator; + + JDACommandTranslator translator() { + return translator; + } + + LiteJDASettings translator(JDACommandTranslator translator) { + this.translator = translator; + return this; + } + } diff --git a/litecommands-jda/test/dev/rollczi/litecommands/jda/JDACommandTranslatorTest.java b/litecommands-jda/test/dev/rollczi/litecommands/jda/JDACommandTranslatorTest.java index 0c95991ae..d7e8e0a57 100644 --- a/litecommands-jda/test/dev/rollczi/litecommands/jda/JDACommandTranslatorTest.java +++ b/litecommands-jda/test/dev/rollczi/litecommands/jda/JDACommandTranslatorTest.java @@ -2,10 +2,10 @@ import dev.rollczi.litecommands.argument.parser.ParseResult; import dev.rollczi.litecommands.command.CommandRoute; -import dev.rollczi.litecommands.command.executor.CommandExecutorFactory; import dev.rollczi.litecommands.meta.Meta; import dev.rollczi.litecommands.unit.TestExecutor; import dev.rollczi.litecommands.unit.TestSender; +import dev.rollczi.litecommands.wrapper.WrapperRegistry; import net.dv8tion.jda.api.interactions.commands.OptionType; import net.dv8tion.jda.api.interactions.commands.build.OptionData; import net.dv8tion.jda.api.interactions.commands.build.SlashCommandData; @@ -19,7 +19,7 @@ class JDACommandTranslatorTest { - final JDACommandTranslator translator = new JDACommandTranslator() + final JDACommandTranslator translator = new JDACommandTranslator(new WrapperRegistry()) .type(String.class, OptionType.STRING, option -> option.getAsString()) .type(Integer.class, OptionType.INTEGER, option -> option.getAsInt()); diff --git a/litecommands-minestom/test/dev/rollczi/litecommands/minestom/MinestomIntegrationTest.java b/litecommands-minestom/test/dev/rollczi/litecommands/minestom/MinestomIntegrationTest.java index 41c34b8b0..51f88fd29 100644 --- a/litecommands-minestom/test/dev/rollczi/litecommands/minestom/MinestomIntegrationTest.java +++ b/litecommands-minestom/test/dev/rollczi/litecommands/minestom/MinestomIntegrationTest.java @@ -2,7 +2,7 @@ import dev.rollczi.litecommands.argument.Arg; import dev.rollczi.litecommands.context.Context; -import dev.rollczi.litecommands.command.executor.Execute; +import dev.rollczi.litecommands.execute.Execute; import dev.rollczi.litecommands.command.Command; import dev.rollczi.litecommands.minestom.test.RegisterCommand; import net.minestom.server.entity.Player; diff --git a/litecommands-unit/src/dev/rollczi/litecommands/unit/TestExecutor.java b/litecommands-unit/src/dev/rollczi/litecommands/unit/TestExecutor.java index a1ca12dd9..0f4d13311 100644 --- a/litecommands-unit/src/dev/rollczi/litecommands/unit/TestExecutor.java +++ b/litecommands-unit/src/dev/rollczi/litecommands/unit/TestExecutor.java @@ -1,49 +1,31 @@ package dev.rollczi.litecommands.unit; -import dev.rollczi.litecommands.argument.Argument; +import dev.rollczi.litecommands.argument.SimpleArgument; import dev.rollczi.litecommands.argument.parser.ParseResult; -import dev.rollczi.litecommands.argument.parser.Parser; -import dev.rollczi.litecommands.argument.parser.ParserSet; -import dev.rollczi.litecommands.argument.parser.RawInputParser; -import dev.rollczi.litecommands.argument.parser.input.ParseableInputMatcher; import dev.rollczi.litecommands.command.CommandRoute; +import dev.rollczi.litecommands.meta.Meta; import dev.rollczi.litecommands.requirement.RequirementsResult; -import dev.rollczi.litecommands.input.raw.RawInput; import dev.rollczi.litecommands.command.executor.CommandExecuteResult; -import dev.rollczi.litecommands.requirement.ArgumentRequirement; -import dev.rollczi.litecommands.requirement.Requirement; import dev.rollczi.litecommands.command.executor.AbstractCommandExecutor; import dev.rollczi.litecommands.command.executor.CommandExecutorMatchResult; -import dev.rollczi.litecommands.requirement.RequirementResult; import dev.rollczi.litecommands.invocation.Invocation; -import dev.rollczi.litecommands.meta.Meta; -import dev.rollczi.litecommands.meta.MetaHolder; -import dev.rollczi.litecommands.range.Range; -import dev.rollczi.litecommands.annotation.AnnotationHolder; -import dev.rollczi.litecommands.argument.Arg; -import dev.rollczi.litecommands.wrapper.Wrap; -import dev.rollczi.litecommands.wrapper.Wrapper; import dev.rollczi.litecommands.wrapper.WrapFormat; -import dev.rollczi.litecommands.wrapper.std.ValueWrapper; -import org.jetbrains.annotations.Nullable; -import java.lang.annotation.Annotation; -import java.util.Collection; import java.util.Collections; -import java.util.Optional; import java.util.function.BiFunction; +import java.util.function.UnaryOperator; public class TestExecutor extends AbstractCommandExecutor { private final Object result; public TestExecutor(CommandRoute parent, Object result) { - super(parent, Collections.emptyList()); + super(parent, Collections.emptyList(), Collections.emptyList()); this.result = result; } public TestExecutor(CommandRoute parent) { - super(parent, Collections.emptyList()); + super(parent, Collections.emptyList(), Collections.emptyList()); this.result = null; } @@ -51,24 +33,8 @@ public TestExecutor withStringArg(String name) { return withArg(name, String.class, (invocation, input) -> ParseResult.success(input)); } - @SuppressWarnings("unchecked") public TestExecutor withArg(String name, Class type, BiFunction, String, ParseResult> parser) { - requirements.add(new TestArgumentRequirement<>(new TestArgument<>(name, type), new ValueWrapper(), new ParserSet() { - @Override - public Optional> getParser(Class inType) { - if (inType != RawInput.class) { - return Optional.empty(); - } - - return Optional.of((Parser) new SimpleRawInputParser<>(parser)); - } - - @Override - public Collection> getParsers() { - return Collections.emptyList(); - } - })); - + arguments.add(new SimpleArgument<>(() -> name, WrapFormat.notWrapped(type))); return this; } @@ -77,124 +43,9 @@ public CommandExecutorMatchResult match(RequirementsResult requirementsR return CommandExecutorMatchResult.success(() -> CommandExecuteResult.success(this, this.result)); } - private class TestArgumentRequirement implements ArgumentRequirement { - - private final Argument argument; - private final Wrapper wrapper; - private final ParserSet parserSet; - private final Meta meta = Meta.create(); - - public TestArgumentRequirement(Argument argument, Wrapper wrapper, ParserSet parserSet) { - this.argument = argument; - this.wrapper = wrapper; - this.parserSet = parserSet; - } - - @Override - public Argument getArgument() { - return this.argument; - } - - @Override - public boolean isWrapperOptional() { - return wrapper.canCreateEmpty(); - } - - @Override - public String getName() { - return argument.getName(); - } - - @Override - public AnnotationHolder getAnnotationHolder() { - return argument.getAnnotationHolder(); - } - - @Override - public > RequirementResult match(Invocation invocation, MATCHER matcher) { - ParseResult matchArgument = matcher.nextArgument(invocation, argument, parserSet); - - if (matchArgument.isFailed()) { - return RequirementResult.failure(matchArgument.getFailedReason()); - } - - return RequirementResult.success(new Wrap() { - @Override - public Object unwrap() { - return matchArgument.getSuccessfulResult(); - } - - @Override - public Class getParsedType() { - return argument.getWrapperFormat().getParsedType(); - } - }); - } - - @Override - public Meta meta() { - return meta; - } - - @Override - public @Nullable MetaHolder parentMeta() { - return null; - } - } - - private static class TestArgument implements Argument { - - private final String name; - private final WrapFormat wrapFormat; - - private TestArgument(String name, Class type) { - this.name = name; - this.wrapFormat = WrapFormat.notWrapped(type); - } - - @Override - public String getName() { - return this.name; - } - - @Override - public WrapFormat getWrapperFormat() { - return this.wrapFormat; - } - - @Override - public AnnotationHolder getAnnotationHolder() { - Arg arg = new Arg() { - @Override - public Class annotationType() { - return Arg.class; - } - - @Override - public String value() { - return name; - } - }; - - return AnnotationHolder.of(arg, wrapFormat, () -> name); - } + public TestExecutor onMeta(UnaryOperator operator) { + operator.apply(meta); + return this; } - private class SimpleRawInputParser implements RawInputParser { - private final BiFunction, String, ParseResult> parser; - - public SimpleRawInputParser(BiFunction, String, ParseResult> parser) { - this.parser = parser; - } - - @Override - public Range getRange(Argument argument) { - return Range.of(1); - } - - @Override - public ParseResult parse(Invocation invocation, Argument argument, RawInput input) { - return parser.apply(invocation, input.next()); - } - } }