Crate enum_extract_macro
source ·Expand description
Derive functions on an Enum for easily accessing individual items in the Enum. This crate is intended to be used with the enum-extract-error crate.
Summary
This crate adds a EnumExtract
derive macro that adds the following functions for each variant in your enum:
is_[variant]
: Returns a bool indicated whether the actual variant matches the expected variant.as_[variant]
: Returns a Result with a reference to the data contained by the variant, or an error if the actual variant is not the expected variant type.as_[variant]_mut
: Likeas_[variant]
but returns a mutable reference.into_[variant]
: Likeas_[variant]
but consumes the value and returns an owned value instead of a reference.extract_as_[variant]
: Callsas_[variant]
and returns the data or panics if there was an error.extract_as_[variant]_mut
: Callsas_[variant]_mut
and returns the data or panics if there was an error.extract_into_[variant]
: Callsinto_[variant]
and returns the data or panics if there was an error.
Notes on the extract
functions
These functions are slightly different from calling as_[variant]().unwrap()
because they panic with the Display
output of EnumExtractError
rather than the Debug
output.
Since these functions can panic they are not recommended for production code. Their main use is in tests, in which they can simplify and flatten tests significantly.
Examples
Unit Variants
Check if the variant is the expected variant:
use enum_extract_macro::EnumExtract;
#[derive(Debug, EnumExtract)]
enum UnitVariants {
One,
Two,
}
let unit = UnitVariants::One;
assert!(unit.is_one());
assert!(!unit.is_two());
Unnamed Variants
Check if the variant is the expected variant:
use enum_extract_macro::EnumExtract;
#[derive(Debug, EnumExtract)]
enum UnnamedVariants {
One(u32),
Two(u32, i32),
}
let unnamed = UnnamedVariants::One(1);
assert!(unnamed.is_one());
assert!(!unnamed.is_two());
Get the variant’s value:
use enum_extract_macro::EnumExtract;
#[derive(Debug, EnumExtract)]
enum UnnamedVariants {
One(u32),
Two(u32, i32),
}
fn main() -> Result<(), enum_extract_error::EnumExtractError> {
let mut unnamed = UnnamedVariants::One(1);
// returns a reference to the value
let one = unnamed.as_one()?;
assert_eq!(*one, 1);
// returns a mutable reference to the value
let one = unnamed.as_one_mut()?;
assert_eq!(*one, 1);
// returns the value by consuming the enum
let one = unnamed.into_one()?;
assert_eq!(one, 1);
Ok(())
}
If the variant has multiple values, a tuple will be returned:
use enum_extract_macro::EnumExtract;
#[derive(Debug, EnumExtract)]
enum UnnamedVariants {
One(u32),
Two(u32, i32),
}
fn main() -> Result<(), enum_extract_error::EnumExtractError> {
let mut unnamed = UnnamedVariants::Two(1, 2);
// returns a reference to the value
let two = unnamed.as_two()?;
assert_eq!(two, (&1, &2));
// returns a mutable reference to the value
let two = unnamed.as_two_mut()?;
assert_eq!(two, (&mut 1, &mut 2));
// returns the value by consuming the enum
let two = unnamed.into_two()?;
assert_eq!(two, (1, 2));
Ok(())
}
Extract variants of all of the above methods will panic with a decent message if the variant is not the expected variant. Very useful for testing, but not recommended for production code.
See the enum-extract-error crate for more information on the error type.
use enum_extract_macro::EnumExtract;
#[derive(Debug, EnumExtract)]
enum UnnamedVariants {
One(u32),
Two(u32, i32),
}
let mut unnamed = UnnamedVariants::One(1);
// returns a reference to the value
let one = unnamed.extract_as_one();
assert_eq!(*one, 1);
// returns a mutable reference to the value
let one = unnamed.extract_as_one_mut();
assert_eq!(*one, 1);
// returns the value by consuming the enum
let one = unnamed.extract_into_one();
assert_eq!(one, 1);
use enum_extract_macro::EnumExtract;
#[derive(Debug, EnumExtract)]
enum UnnamedVariants {
One(u32),
Two(u32, i32),
}
let unnamed = UnnamedVariants::One(1);
// panics with a decent message
let one = unnamed.extract_as_two();
Named Variants
Check if the variant is the expected variant:
use enum_extract_macro::EnumExtract;
#[derive(Debug, EnumExtract)]
enum NamedVariants {
One {
first: u32
},
Two {
first: u32,
second: i32
},
}
let named = NamedVariants::One { first: 1 };
assert!(named.is_one());
assert!(!named.is_two());
Get the variant’s value:
use enum_extract_macro::EnumExtract;
#[derive(Debug, EnumExtract)]
enum NamedVariants {
One {
first: u32
},
Two {
first: u32,
second: i32
},
}
fn main() -> Result<(), enum_extract_error::EnumExtractError> {
let mut named = NamedVariants::One { first: 1 };
// returns a reference to the value
let one = named.as_one()?;
assert_eq!(*one, 1);
// returns a mutable reference to the value
let one = named.as_one_mut()?;
assert_eq!(*one, 1);
// returns the value by consuming the enum
let one = named.into_one()?;
assert_eq!(one, 1);
Ok(())
}
If the variant has multiple values, a tuple will be returned:
use enum_extract_macro::EnumExtract;
#[derive(Debug, EnumExtract)]
enum NamedVariants {
One {
first: u32
},
Two {
first: u32,
second: i32
},
}
fn main() -> Result<(), enum_extract_error::EnumExtractError> {
let mut unnamed = NamedVariants::Two { first: 1, second: 2 };
// returns a reference to the value
let two = unnamed.as_two()?;
assert_eq!(two, (&1, &2));
// returns a mutable reference to the value
let two = unnamed.as_two_mut()?;
assert_eq!(two, (&mut 1, &mut 2));
// returns the value by consuming the enum
let two = unnamed.into_two()?;
assert_eq!(two, (1, 2));
Ok(())
}
Extract variants of all of the above methods will panic with a decent message if the variant is not the expected variant. Very useful for testing, but not recommended for production code.
See the enum-extract-error crate for more information on the error type.
use enum_extract_macro::EnumExtract;
#[derive(Debug, EnumExtract)]
enum NamedVariants {
One {
first: u32
},
Two {
first: u32,
second: i32
},
}
let mut named = NamedVariants::One { first: 1 };
// returns a reference to the value
let one = named.extract_as_one();
assert_eq!(*one, 1);
// returns a mutable reference to the value
let one = named.extract_as_one_mut();
assert_eq!(*one, 1);
// returns the value by consuming the enum
let one = named.extract_into_one();
assert_eq!(one, 1);
use enum_extract_macro::EnumExtract;
#[derive(Debug, EnumExtract)]
enum NamedVariants {
One {
first: u32
},
Two {
first: u32,
second: i32
},
}
let named = NamedVariants::One { first: 1 };
// panics with a decent message
let one = named.extract_as_two();
Derive Macros
- Derive functions on an Enum for easily accessing individual items in the Enum