Skip to content
This repository was archived by the owner on Aug 16, 2021. It is now read-only.

Commit bbadb12

Browse files
authored
Merge pull request #228 from sgrif/sg-allow-skipping-msg-variant
Allow skipping the `Msg` variant
2 parents d69c655 + b162068 commit bbadb12

File tree

3 files changed

+109
-45
lines changed

3 files changed

+109
-45
lines changed

src/error_chain.rs

Lines changed: 84 additions & 45 deletions
Original file line numberDiff line numberDiff line change
@@ -102,13 +102,68 @@ macro_rules! impl_error_chain_processed {
102102
#[allow(unused)]
103103
pub type $result_name<T> = ::std::result::Result<T, $error_name>;
104104
};
105-
// Without `Result` wrapper.
105+
106+
// With `Msg` variant.
107+
(
108+
types {
109+
$error_name:ident, $error_kind_name:ident, $($types:tt)*
110+
}
111+
links $links:tt
112+
foreign_links $foreign_links:tt
113+
errors { $($errors:tt)* }
114+
) => {
115+
impl_error_chain_processed! {
116+
types {
117+
$error_name, $error_kind_name, $($types)*
118+
}
119+
skip_msg_variant
120+
links $links
121+
foreign_links $foreign_links
122+
errors {
123+
/// A convenient variant for String.
124+
Msg(s: String) {
125+
description(&s)
126+
display("{}", s)
127+
}
128+
129+
$($errors)*
130+
}
131+
}
132+
133+
impl<'a> From<&'a str> for $error_kind_name {
134+
fn from(s: &'a str) -> Self {
135+
$error_kind_name::Msg(s.into())
136+
}
137+
}
138+
139+
impl From<String> for $error_kind_name {
140+
fn from(s: String) -> Self {
141+
$error_kind_name::Msg(s)
142+
}
143+
}
144+
145+
impl<'a> From<&'a str> for $error_name {
146+
fn from(s: &'a str) -> Self {
147+
Self::from_kind(s.into())
148+
}
149+
}
150+
151+
impl From<String> for $error_name {
152+
fn from(s: String) -> Self {
153+
Self::from_kind(s.into())
154+
}
155+
}
156+
};
157+
158+
// Without `Result` wrapper or `Msg` variant.
106159
(
107160
types {
108161
$error_name:ident, $error_kind_name:ident,
109162
$result_ext_name:ident;
110163
}
111164

165+
skip_msg_variant
166+
112167
links {
113168
$( $link_variant:ident ( $link_error_path:path, $link_kind_path:path )
114169
$( #[$meta_links:meta] )*; ) *
@@ -294,33 +349,13 @@ macro_rules! impl_error_chain_processed {
294349
}
295350
}
296351

297-
impl<'a> From<&'a str> for $error_name {
298-
fn from(s: &'a str) -> Self {
299-
$error_name::from_kind(s.into())
300-
}
301-
}
302-
303-
impl From<String> for $error_name {
304-
fn from(s: String) -> Self {
305-
$error_name::from_kind(s.into())
306-
}
307-
}
308-
309-
310352
// The ErrorKind type
311353
// --------------
312354

313355
impl_error_chain_kind! {
314356
/// The kind of an error.
315357
#[derive(Debug)]
316358
pub enum $error_kind_name {
317-
318-
/// A convenient variant for String.
319-
Msg(s: String) {
320-
description(&s)
321-
display("{}", s)
322-
}
323-
324359
$(
325360
$(#[$meta_links])*
326361
$link_variant(e: $link_kind_path) {
@@ -350,18 +385,6 @@ macro_rules! impl_error_chain_processed {
350385
}
351386
) *
352387

353-
impl<'a> From<&'a str> for $error_kind_name {
354-
fn from(s: &'a str) -> Self {
355-
$error_kind_name::Msg(s.to_string())
356-
}
357-
}
358-
359-
impl From<String> for $error_kind_name {
360-
fn from(s: String) -> Self {
361-
$error_kind_name::Msg(s)
362-
}
363-
}
364-
365388
impl From<$error_name> for $error_kind_name {
366389
fn from(e: $error_name) -> Self {
367390
e.0
@@ -411,48 +434,64 @@ macro_rules! impl_error_chain_processed {
411434
#[macro_export(local_inner_macros)]
412435
macro_rules! error_chain_processing {
413436
(
414-
({}, $b:tt, $c:tt, $d:tt)
437+
({}, $($rest:tt)*)
415438
types $content:tt
416439
$( $tail:tt )*
417440
) => {
418441
error_chain_processing! {
419-
($content, $b, $c, $d)
442+
($content, $($rest)*)
420443
$($tail)*
421444
}
422445
};
446+
423447
(
424-
($a:tt, {}, $c:tt, $d:tt)
448+
($a:tt, {}, $($rest:tt)*)
425449
links $content:tt
426450
$( $tail:tt )*
427451
) => {
428452
error_chain_processing! {
429-
($a, $content, $c, $d)
453+
($a, $content, $($rest)*)
430454
$($tail)*
431455
}
432456
};
457+
433458
(
434-
($a:tt, $b:tt, {}, $d:tt)
459+
($a:tt, $b:tt, {}, $($rest:tt)*)
435460
foreign_links $content:tt
436461
$( $tail:tt )*
437462
) => {
438463
error_chain_processing! {
439-
($a, $b, $content, $d)
464+
($a, $b, $content, $($rest)*)
440465
$($tail)*
441466
}
442467
};
468+
443469
(
444-
($a:tt, $b:tt, $c:tt, {})
470+
($a:tt, $b:tt, $c:tt, {}, $($rest:tt)*)
445471
errors $content:tt
446472
$( $tail:tt )*
447473
) => {
448474
error_chain_processing! {
449-
($a, $b, $c, $content)
475+
($a, $b, $c, $content, $($rest)*)
476+
$($tail)*
477+
}
478+
};
479+
480+
(
481+
($a:tt, $b:tt, $c:tt, $d:tt, {}, $($rest:tt)*)
482+
skip_msg_variant
483+
$( $tail:tt )*
484+
) => {
485+
error_chain_processing! {
486+
($a, $b, $c, $d, {skip_msg_variant}, $($rest)*)
450487
$($tail)*
451488
}
452489
};
453-
( ($a:tt, $b:tt, $c:tt, $d:tt) ) => {
490+
491+
( ($a:tt, $b:tt, $c:tt, $d:tt, {$($e:tt)*},) ) => {
454492
impl_error_chain_processed! {
455493
types $a
494+
$($e)*
456495
links $b
457496
foreign_links $c
458497
errors $d
@@ -463,10 +502,10 @@ macro_rules! error_chain_processing {
463502
/// Macro for generating error types and traits. See crate level documentation for details.
464503
#[macro_export(local_inner_macros)]
465504
macro_rules! error_chain {
466-
( $( $block_name:ident { $( $block_content:tt )* } )* ) => {
505+
( $($args:tt)* ) => {
467506
error_chain_processing! {
468-
({}, {}, {}, {})
469-
$($block_name { $( $block_content )* })*
507+
({}, {}, {}, {}, {},)
508+
$($args)*
470509
}
471510
};
472511
}

src/lib.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -163,6 +163,10 @@
163163
//! display("unknown toolchain version: '{}'", v), // trailing comma is allowed
164164
//! }
165165
//! }
166+
//!
167+
//! // If this annotation is left off, a variant `Msg(s: String)` will be added, and `From`
168+
//! // impls will be provided for `String` and `&str`
169+
//! skip_msg_variant
166170
//! }
167171
//!
168172
//! # fn main() {}

tests/tests.rs

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -662,3 +662,24 @@ fn trailing_comma_in_errors_impl() {
662662
}
663663
};
664664
}
665+
666+
#[test]
667+
fn skipping_msg_variant() {
668+
error_chain! {
669+
skip_msg_variant
670+
671+
errors {
672+
MyMsg(s: String) {
673+
description(&s)
674+
display("{}", s)
675+
}
676+
}
677+
}
678+
679+
let x = Error::from_kind(ErrorKind::MyMsg("some string".into()));
680+
// This would fail to compile if we generate a `Msg` variant
681+
match *x.kind() {
682+
ErrorKind::MyMsg(_) => {}
683+
ErrorKind::__Nonexhaustive {} => {}
684+
}
685+
}

0 commit comments

Comments
 (0)