@@ -1,15 +1,15 @@
# The Command Service
# The Command Service
[Discord.Commands](xref:Discord.Commands) provides an A ttribute-based
[Discord.Commands](xref:Discord.Commands) provides an a ttribute-based
command parser.
command parser.
## Setup
## Setup
To use Commands, you must create a [Command Service] and a C ommand
To use Commands, you must create a [Command Service] and a c ommand
Handler.
Handler.
Included below is a very barebone Command H andler. You can extend your
C ommand Handler as much as you like; however, the below is the bare
Included below is a very barebone command h andler. You can extend your
c ommand Handler as much as you like; however, the below is the bare
minimum.
minimum.
The `CommandService` will optionally accept a [CommandServiceConfig],
The `CommandService` will optionally accept a [CommandServiceConfig],
@@ -39,7 +39,7 @@ Commands in different classes and have them automatically loaded.
Discord.Net's implementation of Modules is influenced heavily from
Discord.Net's implementation of Modules is influenced heavily from
ASP.NET Core's Controller pattern. This means that the lifetime of a
ASP.NET Core's Controller pattern. This means that the lifetime of a
module instance is only as long as the C ommand is being invoked.
module instance is only as long as the c ommand is being invoked.
> [!WARNING]
> [!WARNING]
> **Avoid using long-running code** in your modules wherever possible.
> **Avoid using long-running code** in your modules wherever possible.
@@ -67,37 +67,36 @@ By now, your module should look like this:
### Adding Commands
### Adding Commands
The next step to creating Commands is actually creating the C ommands.
The next step to creating commands is actually creating the c ommands.
To create a C ommand, add a method to your module of type `Task` or
To create a c ommand, add a method to your module of type `Task` or
`Task<RuntimeResult>` depending on your use.
`Task<RuntimeResult>` depending on your use.
Typically, you will want to mark this method as `async`, although it
Typically, you will want to mark this method as `async`, although it
is not required.
is not required.
Adding parameters to a Command is done by adding parameters to the
parent Task.
For example, to take an integer as an argument from the user, add `int
arg`; to take a user as an argument from the user, add `IUser user`.
Starting from 1.0, a Command can accept nearly any type of argument;
a full list of types that are parsed by default can be found in
the below section on [Type Readers](#type-readers).
Adding parameters to a command is done by adding parameters to the
parent Task. For example, to take an integer as an argument from
the user, add `int arg`; to take a user as an argument from the
user, add `IUser user`. Starting from 1.0, a command can accept
nearly any type of argument; a full list of types that are parsed
by default can be found in the below
section on [Type Readers](#type-readers).
Parameters, by default, are always required. To make a parameter
Parameters, by default, are always required. To make a parameter
optional, give it a default value. To accept a comma-separated list,
optional, give it a default value. To accept a comma-separated list,
set the parameter to `params Type[]`.
set the parameter to `params Type[]`.
Should a parameter include spaces, it **must** be wrapped in quotes.
For example, for a Command with a parameter `string food`, you would
execute it with `!favoritefood "Key Lime Pie"`.
If you would like a parameter to parse until the end of a Command,
flag the parameter with the [RemainderAttribute]. This will allow a
user to invoke a Command without wrapping a parameter in quotes.
Should a parameter include spaces, the parameter **must** be
wrapped in quotes. For example, for a command with a parameter
`string food`, you would execute it with
`!favoritefood "Key Lime Pie"`. If you would like a parameter to
parse until the end of a command, flag the parameter with the
[RemainderAttribute]. This will allow a user to invoke a command
without wrapping a parameter in quotes.
Finally, flag your Command with the [CommandAttribute]. (you must
specify a name for this C ommand, except for when it is part of a
Module Group - see below)
Finally, flag your command with the [CommandAttribute] (you must
specify a name for this c ommand, except for when it is part of a
[Module Group](#module-groups).
[RemainderAttribute]: xref:Discord.Commands.RemainderAttribute
[RemainderAttribute]: xref:Discord.Commands.RemainderAttribute
[CommandAttribute]: xref:Discord.Commands.CommandAttribute
[CommandAttribute]: xref:Discord.Commands.CommandAttribute
@@ -116,11 +115,10 @@ priority will be called first.
### Command Context
### Command Context
Every C ommand can access the execution context through the [Context]
Every c ommand can access the execution context through the [Context]
property on [ModuleBase]. `ICommandContext` allows you to access the
property on [ModuleBase]. `ICommandContext` allows you to access the
message, channel, guild, and user that the Command was invoked from,
as well as the underlying Discord client that the Command was invoked
from.
message, channel, guild, user, and the underlying Discord client
that the command was invoked from.
Different types of Contexts may be specified using the generic variant
Different types of Contexts may be specified using the generic variant
of [ModuleBase]. When using a [SocketCommandContext], for example, the
of [ModuleBase]. When using a [SocketCommandContext], for example, the
@@ -146,14 +144,13 @@ At this point, your module should look comparable to this example:
#### Loading Modules Automatically
#### Loading Modules Automatically
The Command Service can automatically discover all classes in an
The Command Service can automatically discover all classes in an
Assembly that inherit [ModuleBase] and load them.
Assembly that inherit [ModuleBase] and load them. Invoke
[CommandService.AddModulesAsync] to discover modules and
install them.
To opt a module out of auto-loading, flag it with
To opt a module out of auto-loading, flag it with
[DontAutoLoadAttribute].
[DontAutoLoadAttribute].
Invoke [CommandService.AddModulesAsync] to discover modules and
install them.
[DontAutoLoadAttribute]: xref:Discord.Commands.DontAutoLoadAttribute
[DontAutoLoadAttribute]: xref:Discord.Commands.DontAutoLoadAttribute
[CommandService.AddModulesAsync]: xref:Discord.Commands.CommandService.AddModulesAsync*
[CommandService.AddModulesAsync]: xref:Discord.Commands.CommandService.AddModulesAsync*
@@ -189,7 +186,7 @@ prefixed. To create a group, flag a module with the
Module groups also allow you to create **nameless Commands**, where
Module groups also allow you to create **nameless Commands**, where
the [CommandAttribute] is configured with no name. In this case, the
the [CommandAttribute] is configured with no name. In this case, the
C ommand will inherit the name of the group it belongs to.
c ommand will inherit the name of the group it belongs to.
### Submodules
### Submodules
@@ -211,20 +208,19 @@ DI when writing your modules.
### Setup
### Setup
First, you need to create an @System.IServiceProvider; you may create
your own one if you wish.
First, you need to create an @System.IServiceProvider.
Next, add the dependencies that your modules will use to the map.
Next, add the dependencies to the service collection that you wish
to use in the Modules.
Finally, pass the map into the `LoadAssembly` method. Your modules
will be automatically loaded with this dependency map.
Finally, pass the service collection into `AddModulesAsync`.
[!code-csharp[IServiceProvider Setup](samples/dependency_map_setup.cs)]
[!code-csharp[IServiceProvider Setup](samples/dependency_map_setup.cs)]
### Usage in Modules
### Usage in Modules
In the constructor of your Module, any parameters will be filled in by
In the constructor of your Module, any parameters will be filled in by
the @System.IServiceProvider that you've passed into `LoadAssembly` .
the @System.IServiceProvider that you've passed.
Any publicly settable properties will also be filled in the same
Any publicly settable properties will also be filled in the same
manner.
manner.