diff options
| author | 魏曹先生 <1992414357@qq.com> | 2026-06-18 22:48:16 +0800 |
|---|---|---|
| committer | 魏曹先生 <1992414357@qq.com> | 2026-06-18 22:48:16 +0800 |
| commit | 0f7b2a50b05f38d886234ff6b031766c7af1dabb (patch) | |
| tree | 9c9b5d4aa11c91c117b08e829ec33361c4aa6275 /examples/example-pack-err/src/main.rs | |
| parent | dd28430b67dcfda6dd2e91750a4c1a62c085150a (diff) | |
Add `pack_err!` macro for error structs with automatic name field
Diffstat (limited to 'examples/example-pack-err/src/main.rs')
| -rw-r--r-- | examples/example-pack-err/src/main.rs | 101 |
1 files changed, 101 insertions, 0 deletions
diff --git a/examples/example-pack-err/src/main.rs b/examples/example-pack-err/src/main.rs new file mode 100644 index 0000000..72fecd6 --- /dev/null +++ b/examples/example-pack-err/src/main.rs @@ -0,0 +1,101 @@ +//! Example `pack_err!` +//! +//! > This example demonstrates how to use the `pack_err!` macro to define error types +//! > with automatic `name` field (set to snake_case at compile time) and optional `info` field. +//! > Also demonstrates `--json` serialization when `general_renderer` is enabled. +//! +//! Run: +//! ```bash +//! cargo run --manifest-path examples/example-pack-err/Cargo.toml --quiet -- find +//! cargo run --manifest-path examples/example-pack-err/Cargo.toml --quiet -- find --json +//! cargo run --manifest-path examples/example-pack-err/Cargo.toml --quiet -- find Cargo.toml +//! cargo run --manifest-path examples/example-pack-err/Cargo.toml --quiet -- find Cargo.toml --json +//! cargo run --manifest-path examples/example-pack-err/Cargo.toml --quiet -- find src +//! cargo run --manifest-path examples/example-pack-err/Cargo.toml --quiet -- find src --json +//! ``` +//! +//! Output: +//! ```plaintext +//! Search path not provided +//! {"name":"error_not_found"} +//! Not a directory: Cargo.toml +//! {"name":"error_not_dir","info":"Cargo.toml"} +//! Found directory: src +//! {"inner":"src"} +//! ``` + +use mingling::prelude::*; +use mingling::setup::GeneralRendererSetup; +use std::path::PathBuf; + +dispatcher!("find", CMDFind => EntryFind); + +// --------- IMPORTANT --------- +// `pack_err!` is a convenient macro for defining error types. +// +// Simple form: pack_err!(ErrorNotFound); +// Typed form: pack_err!(ErrorNotDir = PathBuf); +// +// The simple form generates a struct with `name: String` and `impl Default`. +// name = "error_not_found" (automatically snake_cased at compile time) +// +// The typed form additionally generates `pub fn new(info)`. +// name = "error_not_dir" +// +// When `general_renderer` is enabled, the struct also gets +// `#[derive(serde::Serialize)]` for --json / --yaml output. +// --------- IMPORTANT --------- + +// Simple form — name = "error_not_found" +pack_err!(ErrorNotFound); + +// Typed form — name = "error_not_dir" +pack_err!(ErrorNotDir = PathBuf); + +// Success type using traditional pack! +pack!(ResultPath = PathBuf); + +#[chain] +fn handle_find(args: EntryFind) -> Next { + let Some(path_str) = args.inner.first().cloned() else { + // No path provided → use the simple error form (Default) + return ErrorNotFound::default().to_render(); + }; + + let path = PathBuf::from(&path_str); + if path.is_dir() { + // Is a directory → success + ResultPath::new(path).to_render() + } else { + // Not a directory (or doesn't exist) → use the typed error form + ErrorNotDir::new(path).to_render() + } +} + +/// Renders the successful result with the found directory path. +#[renderer] +fn render_result_path(path: ResultPath) { + r_println!("Found directory: {}", path.display()); +} + +/// Renders the error when no search path is provided. +#[renderer] +fn render_error_not_found(_: ErrorNotFound) { + r_println!("Search path not provided"); +} + +/// Renders the error when the given path is not a directory. +#[renderer] +fn render_error_not_dir(err: ErrorNotDir) { + r_println!("Not a directory: {}", err.info.display()); +} + +gen_program!(); + +fn main() { + let mut program = ThisProgram::new(); + // Add GeneralRendererSetup to support --json / --yaml flags + program.with_setup(GeneralRendererSetup); + program.with_dispatcher(CMDFind); + let _ = program.exec(); +} |
