diff --git a/Lanat/topics/Argument-types.md b/Lanat/topics/Argument-types.md index e2a03b9..80ce4d9 100644 --- a/Lanat/topics/Argument-types.md +++ b/Lanat/topics/Argument-types.md @@ -54,6 +54,14 @@ Lanat comes with a set of default argument types that you can use out of the box The user can specify any of the enum values by their names. The names are case-insensitive.

+ + +> In the enum class, one of the values may be annotated with @EnumArgumentType.Default, which will mark +> the value to be used when the user doesn't provide any. + +> If needed, you can change the name of an enum value that the user must provide by using the +> @EnumArgumentType.WithName annotation. + diff --git a/Lanat/topics/Type-inference.md b/Lanat/topics/Type-inference.md index 56124f0..1758305 100644 --- a/Lanat/topics/Type-inference.md +++ b/Lanat/topics/Type-inference.md @@ -97,4 +97,47 @@ not recommended as it can lead to confusion. Use the ``withPrimitive`` variants of the methods to register/unregister inferences for primitive types. > Note that in this example the inference ``Integer[].class`` has not been overridden, so it will still use the -> default inference made by Lanat. \ No newline at end of file +> default inference made by Lanat. + + + +## Predicate inferences + +Inferences can also be created based on a predicate. This is useful when you want to infer a type based on some condition, +rather than the exact type. + +```Java +ArgumentTypeInfer.register( + Record.class::isAssignableFrom, // predicate + MyCoolArgumentType::new, // type supplied when satisfied + "MyCoolArgumentType" // name of the inference +); +``` + +In this example, the `MyCoolArgumentType` will be used for any class that is a subclass of `Record`. + + + + +To unregister a predicate inference, you can use the name of the inference: + +```Java +ArgumentTypeInfer.unregister("MyCoolArgumentType"); +``` + + + + + +You can get a list of all defined predicate inferences by calling ``ArgumentTypeInfer#getPredicateInfers()``. + + + + +> Please note that while predicate inferences provide a finer control over the type inference process, they are slower +> to lookup than regular inferences. Only use them when necessary. +> {style="warning"} + +> Regular inferences have a higher priority than predicate inferences. If a regular inference is found for a type, a +> possibly matching predicate inference will be ignored. +> {style="note"} \ No newline at end of file diff --git a/Lanat/topics/Your-first-argument-parser.md b/Lanat/topics/Your-first-argument-parser.md index d05e382..6879947 100644 --- a/Lanat/topics/Your-first-argument-parser.md +++ b/Lanat/topics/Your-first-argument-parser.md @@ -40,6 +40,7 @@ Let's create an enum that will make our job easier when defining the operations. ````Java public enum Operation { + @EnumArgumentType.Default ADD, SUBTRACT, MULTIPLY, @@ -56,6 +57,10 @@ public enum Operation { } ```` +> Notice the `@EnumArgumentType.Default` annotation. This annotation makes the `ADD` operation the default value, which +> is what we want in this case. +> {style="note"} + ## Defining the Command template Now let's create a [Command template](Command-templates.md), which will define the structure of our command. @@ -91,59 +96,7 @@ public static void main(String[] args) { {style="note"} -## An issue in the way - -Attempting to run the program at this point will result in an error. - -````Console -Exception in thread "main" CommandTemplateException: Could not infer the argument type from the field 'op' with type 'Operation'. - at lanat.ArgumentBuilder.setTypeFromField(ArgumentBuilder.java:243) - at lanat.Command.lambda$from$10(Command.java:437) - at java.base/java.lang.Iterable.forEach(Iterable.java:75) - at lanat.Command.from(Command.java:437) - at lanat.Command.(Command.java:107) - at lanat.ArgumentParser.(ArgumentParser.java:54) - at lanat.ArgumentParser.from(ArgumentParser.java:75) - at lanat.ArgumentParser.parseFromInto(ArgumentParser.java:123) - at lanat.ArgumentParser.parseFromInto(ArgumentParser.java:143) - at MyProgram.main(MyProgram.java:40) -````` -{collapsible="true" collapsed-title="Exception: Could not infer the argument type from the field 'op' with type 'Operation'."} - -````Console -Could not infer the argument type from the field 'op' with type 'Operation'. -````` - - -Why does this occur? - -Well, this issue is being caused by the ``op`` argument. The ``op`` argument is an enum, and enums -cannot be automatically inferred by Lanat. We need to define the type of the argument manually. - -[Lanat can infer](Type-inference.md) the type of many different types of arguments, including primitive types, boxed -primitive types, and even some classes. Enums cannot be inferred as they are more complex types. - - -## Fixing the issue - -In order to fix this issue, let's head back to the ``MyProgram`` class and define the type of the -``op`` argument. In order to do this, we will define the -[``beforeInit``](Command-templates.md#the-beforeinit-method) static method. - -````Java -@InitDef -public static void beforeInit(CommandBuildContext ctx) { - ctx.argWithType("op", new EnumArgumentType<>(Operation.ADD)) - .onOk(value -> System.out.println("Operation explicitly set to " + value)); -} -```` - -As you can see, we not only defined the type of the argument, but we also added a callback that will -be called when the argument is successfully parsed. - -> The ``beforeInit`` method is called right before the command is initialized with all the arguments. -> It receives a ``CommandBuildContext`` instance, which can be used to alter the arguments before -> they are built. +## Result Running the program now will result in the following output: @@ -173,13 +126,8 @@ public class MyProgram extends CommandTemplate { @Argument.Define public Operation op; - @InitDef - public static void beforeInit(CommandBuildContext ctx) { - ctx.argWithType("op", new EnumArgumentType<>(Operation.ADD)) - .onOk(value -> System.out.println("Operation explicitly set to " + value)); - } - public enum Operation { + @EnumArgumentType.Default ADD, SUBTRACT, MULTIPLY, diff --git a/Lanat/v.list b/Lanat/v.list index 41f8ea5..45f0abc 100644 --- a/Lanat/v.list +++ b/Lanat/v.list @@ -2,7 +2,7 @@ - +