# Overview

JackFredLib: Extra Command Source Data adds an attachment Minecraft's [`CommandSourceStack`](#user-content-fn-1)[^1] used when running commands. This allows you to attach extra context to advanced commands that redirect back into itself in the same vein as the position, entity, level, etcetera, and do advanced things such as repeatable arguments.&#x20;

For some examples, see [Where Is It's command with repeatable criteria](https://github.com/JackFred2/WhereIsIt/blob/6cddbea8d97e54367bba3f3d87277298d94d115a/src/main/java/red/jackf/whereisit/command/WhereIsCommand.java), or the [test mod's example for holding multiple strings or ints](https://github.com/JackFred2/JackFredLib/blob/b5256f195e14753bcae86cd12910427962c054e2/jackfredlib-testmod/src/main/java/red/jackf/jackfredlib/testmod/RepeatableArgumentsTest.java).

## Adding Extra Data

To start, you'll want to create a class to hold your data, attached to a `CommandSourceStack`:

```java
private static class MutliArgData implements ExtraSourceData<MutliArgData> {
    private final List<Integer> ints = new ArrayList<>();
    private final List<String> strs = new ArrayList<>();

    public MutliArgData() {
    }

    public MutliArgData(MutliArgData other) {
        this.ints.addAll(other.ints);
        this.strs.addAll(other.strs);
    }

    @Override
    public MutliArgData copy() {
        return new MutliArgData(this);
    }
}
```

{% hint style="warning" %}
When overriding the `copy` method, **it is critical that a deep copy is made**. This means that any mutable objects such as sublists must be copied along with all children.
{% endhint %}

Then when registering your command, you'll need to use the methods in `ESD` in the redirect lambda:

{% code fullWidth="true" %}

```java
private static final ExtraSourceData.Definition<MutliArgData> DEFINITION = new ExtraSourceData.Definition<>(
    ResourceLocation.fromNamespaceAndPath("jackfredlib-testmod", "repeated_args"),
    MutliArgData.class,
    MutliArgData::new
);

static void setup() {
    CommandRegistrationCallback.EVENT.register((dispatcher, registryAccess, environment) -> {
        LiteralCommandNode<CommandSourceStack> root = dispatcher.register(literal("repeatableArgs"));
        dispatcher.register(literal("repeatableArgs").then(
                    literal("int").then(
                            argument("int", IntegerArgumentType.integer())
                                    // getting or creating our data class and adding a value to it
                                    .redirect(root, ctx -> ESD.withCustom(ctx, DEFINITION, multiArg ->
                                            multiArg.ints.add(ctx.getArgument("int", Integer.class))
                                    ))
                    )).then(
                    literal("str").then(
                            argument("str", StringArgumentType.word())
                                    .redirect(root, ctx -> ESD.withCustom(ctx, DEFINITION, multiArg ->
                                            multiArg.strs.add(ctx.getArgument("str", String.class))
                                    ))
                    )).then(
                            literal("go").executes(ctx -> {
                                // getting our data
                                MultiArgData data = ESD.getCustom(ctx, DEFINITION);
                                List<Integer> ints = data.ints;
                                List<String> strs = data.strs;
                                
                                // do whatever
                                
                                return 0;
                            })
                    )
        );
    });
}
```

{% endcode %}

[^1]: Yarn: `ServerCommandSource`


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://docs.jackf.red/jackfredlib/jackfredlib-ecsd/overview.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
