1#[macro_export]
42macro_rules! assert_some {
43 ($cond:expr $(,)?) => {
44 match $cond {
45 ::core::option::Option::Some(t) => t,
46 ::core::option::Option::None => {
47 ::core::panic!("assertion failed, expected Some(_), got None");
48 }
49 }
50 };
51 ($cond:expr, $($arg:tt)+) => {
52 match $cond {
53 ::core::option::Option::Some(t) => t,
54 ::core::option::Option::None => {
55 ::core::panic!("assertion failed, expected Some(_), got None: {}", ::core::format_args!($($arg)+));
56 }
57 }
58 };
59}
60
61#[macro_export]
68macro_rules! debug_assert_some {
69 ($($arg:tt)*) => {
70 #[cfg(debug_assertions)]
71 $crate::assert_some!($($arg)*);
72 }
73}
74
75#[cfg(test)]
76mod tests {
77 #[test]
78 fn some() {
79 assert_some!(Some(()));
80 }
81
82 #[test]
83 #[should_panic(expected = "assertion failed, expected Some(_), got None")]
84 fn not_some() {
85 assert_some!(None::<()>);
86 }
87
88 #[test]
89 #[should_panic(expected = "assertion failed, expected Some(_), got None: foo")]
90 fn not_some_custom_message() {
91 assert_some!(None::<()>, "foo");
92 }
93
94 #[test]
95 fn some_value_returned() {
96 let value = assert_some!(Some(42));
97 assert_eq!(value, 42);
98 }
99
100 #[test]
101 #[cfg_attr(not(debug_assertions), ignore = "only run in debug mode")]
102 fn debug_some() {
103 debug_assert_some!(Some(()));
104 }
105
106 #[test]
107 #[cfg_attr(not(debug_assertions), ignore = "only run in debug mode")]
108 #[should_panic(expected = "assertion failed, expected Some(_), got None")]
109 fn debug_not_some() {
110 debug_assert_some!(None::<()>);
111 }
112
113 #[test]
114 #[cfg_attr(not(debug_assertions), ignore = "only run in debug mode")]
115 #[should_panic(expected = "assertion failed, expected Some(_), got None: foo")]
116 fn debug_not_some_custom_message() {
117 debug_assert_some!(None::<()>, "foo");
118 }
119
120 #[test]
121 #[cfg_attr(debug_assertions, ignore = "only run in release mode")]
122 fn debug_release_not_some() {
123 debug_assert_some!(None::<()>);
124 }
125
126 #[test]
127 fn does_not_require_some_to_impl_debug() {
128 enum Foo {
129 Bar,
130 }
131
132 assert_some!(Some(Foo::Bar));
133 }
134
135 #[test]
136 fn debug_does_not_require_some_to_impl_debug() {
137 #[allow(dead_code)]
138 enum Foo {
139 Bar,
140 }
141
142 debug_assert_some!(Some(Foo::Bar));
143 }
144
145 #[test]
146 fn does_not_require_some_to_impl_debug_custom_message() {
147 enum Foo {
148 Bar,
149 }
150
151 assert_some!(Some(Foo::Bar), "foo");
152 }
153
154 #[test]
155 fn debug_does_not_require_some_to_impl_debug_custom_message() {
156 #[allow(dead_code)]
157 enum Foo {
158 Bar,
159 }
160
161 debug_assert_some!(Some(Foo::Bar), "foo");
162 }
163}