aboutsummaryrefslogtreecommitdiff
path: root/docs/pages/2-define-a-dispatcher.md
diff options
context:
space:
mode:
author魏曹先生 <1992414357@qq.com>2026-06-30 18:05:05 +0800
committer魏曹先生 <1992414357@qq.com>2026-06-30 18:05:05 +0800
commit13408e79b940e9a33ca593ed30d1b20c54e01234 (patch)
tree282549991a3f31791401ca2f3255b9318679d2e9 /docs/pages/2-define-a-dispatcher.md
parent29867ab5c0b40378a33318d989c809f90fc7d3aa (diff)
feat(docs): add Chinese and English documentation for Mingling tutorials
Add comprehensive documentation covering Declare a Dispatcher, Declare a Chain, Rendering Results, Multi-Command Program, Argument Parsing with Picker and Clap, Program Setup, Error Handling, Help Info, Resource System, Exit Code Control, Hook System, Testing, Completion, Structural Rendering, and Core Concepts
Diffstat (limited to 'docs/pages/2-define-a-dispatcher.md')
-rw-r--r--docs/pages/2-define-a-dispatcher.md103
1 files changed, 103 insertions, 0 deletions
diff --git a/docs/pages/2-define-a-dispatcher.md b/docs/pages/2-define-a-dispatcher.md
new file mode 100644
index 0000000..804ad1b
--- /dev/null
+++ b/docs/pages/2-define-a-dispatcher.md
@@ -0,0 +1,103 @@
+<h1 align="center">Declare a Dispatcher</h1>
+<p align="center">
+ Use the <code>dispatcher!</code> macro to declare commands and register them
+</p>
+
+Mingling's pipeline starts with a Dispatcher.
+
+Its job is simple: **match the user's input command, wrap the arguments into an Entry type**.
+
+## The `dispatcher!` Macro
+
+The `dispatcher!` macro generates two types at once:
+
+| Generated type | Purpose |
+| -------------- | -------------------------------------------------------------- |
+| `CMDType` | The dispatcher itself, needs to be registered to Program |
+| `EntryType` | The entry type, wraps `Vec<String>`, serves as input for Chain |
+
+The syntax is a fixed three-part pattern:
+
+```rust
+dispatcher!("command path", DispatcherType => EntryType);
+```
+
+Here's a concrete example:
+
+```rust
+dispatcher!("greet", CMDGreet => EntryGreet);
+```
+
+> [!NOTE]
+> The command name (`"greet"`) is auto-converted to kebab-case. Even if you write `"GreetUser"`, matching will use `greet-user`.
+
+## Registering with Program
+
+Once you have a dispatcher, you need to tell Program about it:
+
+```rust
+@@@ dispatcher!("greet", CMDGreet => EntryGreet);
+@@@ fn main() {
+@@@ let mut program = ThisProgram::new();
+// Register the dispatcher
+program.with_dispatcher(CMDGreet);
+@@@ }
+@@@ gen_program!();
+```
+
+> [!TIP]
+> If you have many commands, use `with_dispatchers` to register multiple at once: `program.with_dispatchers((CMDGreet, CMDAdd, CMDRemoteRm))`.
+
+## Multi-level Commands
+
+If your program has a hierarchy — e.g., `remote add`, `remote rm` — just separate the command name with dots:
+
+```rust
+dispatcher!("remote.add", CMDRemoteAdd => EntryRemoteAdd);
+dispatcher!("remote.rm", CMDRemoteRm => EntryRemoteRm);
+```
+
+When the user types `remote add` in the terminal, Mingling matches `remote` and `add` as two levels in sequence.
+
+## The Entry Type `EntryGreet`
+
+You might be curious about what's inside `EntryGreet`. It's essentially a struct wrapping `Vec<String>`:
+
+```rust
+// Illustration of code generated by the dispatcher! macro
+pub struct EntryGreet {
+ pub inner: Vec<String>,
+}
+```
+
+When the user types `greet Alice Bob` on the command line, `EntryGreet.inner` becomes `vec!["Alice", "Bob"]`.
+
+> [!IMPORTANT]
+> Entry's `inner` only contains **the remaining args after matching**.
+>
+> Take `remote add origin` as an example: `remote` and `add` are used for matching the command path, only `origin` goes into `EntryRemoteAdd.inner`.
+
+## Advanced: Implicit Declaration
+
+The above is the standard syntax. If you enable the `extra_macros` feature, you can be more concise:
+
+```rust
+// Features: ["extra_macros"]
+// Omit CMDType and EntryType, names are auto-derived
+ dispatcher!("greet");
+// dispatcher!("greet", CMDGreet => EntryGreet);
+```
+
+This syntax auto-generates `CMDGreet` and `EntryGreet`, with the same effect as the explicit declaration.
+
+But for the tutorial, we'll stick with explicit syntax — it's clearer and doesn't require extra features.
+
+See [Feature List](pages/other/features) for details.
+
+## Next Step
+
+Next we'll write a Chain to receive the Entry and handle the actual business logic.
+
+<p align="center" style="font-size: 0.85em; color: gray;">
+ Written by @Weicao-CatilGrass
+</p>