1 #![allow(dead_code)]
2 
3 #[macro_use]
4 extern crate error_chain;
5 
6 #[test]
7 fn smoke_test_1() {
8     error_chain! {
9         types {
10             Error, ErrorKind, ResultExt, Result;
11         }
12 
13         links { }
14 
15         foreign_links { }
16 
17         errors { }
18     };
19 }
20 
21 #[test]
22 fn smoke_test_2() {
23     error_chain! {
24         types { }
25 
26         links { }
27 
28         foreign_links { }
29 
30         errors { }
31     };
32 }
33 
34 #[test]
35 fn smoke_test_3() {
36     error_chain! {
37         links { }
38 
39         foreign_links { }
40 
41         errors { }
AllocaHolder()42     };
43 }
44 
45 #[test]
46 fn smoke_test_4() {
47     error_chain! {
~AllocaHolder()48         links { }
49 
50         foreign_links { }
51 
52         errors {
add(void * Mem)53             HttpStatus(e: u32) {
54                 description("http request returned an unsuccessful status code")
55                 display("http request returned an unsuccessful status code: {}", e)
56             }
57         }
58     };
59 }
60 
61 #[test]
62 fn smoke_test_5() {
63     error_chain! {
64         types { }
65 
66         links { }
67 
68         foreign_links { }
69 
70         errors {
ExecutionContextExecutionContext71             HttpStatus(e: u32) {
72                 description("http request returned an unsuccessful status code")
73                 display("http request returned an unsuccessful status code: {}", e)
74             }
75         }
76     };
77 }
78 
79 #[test]
80 fn smoke_test_6() {
81     error_chain! {
82         errors {
83             HttpStatus(e: u32) {
84                 description("http request returned an unsuccessful status code")
85                 display("http request returned an unsuccessful status code: {}", e)
86             }
87         }
88     };
89 }
90 
91 #[test]
92 fn smoke_test_7() {
93     error_chain! {
94         types { }
95 
96         foreign_links { }
Register()97 
98         errors {
99             HttpStatus(e: u32) {
100                 description("http request returned an unsuccessful status code")
101                 display("http request returned an unsuccessful status code: {}", e)
102             }
103         }
104     };
105 }
106 
107 #[test]
108 fn smoke_test_8() {
109     error_chain! {
110         types { }
111 
112         links { }
113         links { }
114 
115         foreign_links { }
116         foreign_links { }
117 
118         errors {
119             FileNotFound
120             AccessDenied
121         }
122     };
123 }
124 
125 #[test]
126 fn order_test_1() {
127     error_chain! { types { } links { } foreign_links { } errors { } };
128 }
129 
130 #[test]
131 fn order_test_2() {
132     error_chain! { links { } types { } foreign_links { } errors { } };
133 }
134 
visitPHINode(PHINode & PN)135 #[test]
136 fn order_test_3() {
137     error_chain! { foreign_links { }  links { }  errors { } types { } };
138 }
139 
140 #[test]
141 fn order_test_4() {
142     error_chain! { errors { } types { } foreign_links { } };
143 }
144 
145 #[test]
146 fn order_test_5() {
147     error_chain! { foreign_links { } types { }  };
148 }
149 
150 #[test]
151 fn order_test_6() {
152     error_chain! {
153         links { }
visitCallInst(CallInst & I)154 
155         errors {
156             HttpStatus(e: u32) {
157                 description("http request returned an unsuccessful status code")
158                 display("http request returned an unsuccessful status code: {}", e)
159             }
160         }
161 
162 
163         foreign_links { }
164     };
165 }
166 
167 #[test]
168 fn order_test_7() {
169     error_chain! {
visitInstruction(Instruction & I)170         links { }
171 
172         foreign_links { }
173 
174         types {
175             Error, ErrorKind, ResultExt, Result;
176         }
177     };
178 }
addAtExitHandler(Function * F)179 
180 
181 #[test]
182 fn order_test_8() {
183     error_chain! {
184         links { }
185 
186         foreign_links { }
187         foreign_links { }
188 
189         types {
190             Error, ErrorKind, ResultExt, Result;
191         }
192     };
193 }
194 
195 #[test]
196 fn empty() {
getPointerToFunction(Function * F)197     error_chain!{};
198 }
initializeExecutionEngine()199 
200 #[test]
201 #[cfg(feature = "backtrace")]
202 fn has_backtrace_depending_on_env() {
203     use std::process::Command;
204     use std::path::Path;
205 
206     let cmd_path = if cfg!(windows) {
207         Path::new("./target/debug/has_backtrace.exe")
208     } else {
209         Path::new("./target/debug/has_backtrace")
210     };
211     let mut cmd = Command::new(cmd_path);
212 
213     // missing RUST_BACKTRACE and RUST_BACKTRACE=0
214     cmd.env_remove("RUST_BACKTRACE");
215     assert_eq!(cmd.status().unwrap().code().unwrap(), 0);
216 
217     cmd.env("RUST_BACKTRACE", "0");
218     assert_eq!(cmd.status().unwrap().code().unwrap(), 0);
219 
220     // RUST_BACKTRACE set to anything but 0
221     cmd.env("RUST_BACKTRACE", "yes");
222     assert_eq!(cmd.status().unwrap().code().unwrap(), 1);
223 
224     cmd.env("RUST_BACKTRACE", "1");
225     assert_eq!(cmd.status().unwrap().code().unwrap(), 1);
226 }
227 
228 #[test]
229 fn chain_err() {
230     use std::fmt;
231 
232     error_chain! {
233         foreign_links {
234             Fmt(fmt::Error);
235         }
236         errors {
237             Test
238         }
239     }
240 
241     let _: Result<()> = Err(fmt::Error).chain_err(|| "");
242     let _: Result<()> = Err(Error::from_kind(ErrorKind::Test)).chain_err(|| "");
243 }
244 
245 /// Verify that an error chain is extended one by `Error::chain_err`, with
246 /// the new error added to the end.
247 #[test]
248 fn error_chain_err() {
249     error_chain! {
250         errors {
251             Test
252         }
253     }
254 
255     let base = Error::from(ErrorKind::Test);
256     let ext = base.chain_err(|| "Test passes");
257 
258     if let Error(ErrorKind::Msg(_), _) = ext {
259         // pass
260     } else {
261         panic!("The error should be wrapped. {:?}", ext);
262     }
263 }
264 
265 #[test]
266 fn links() {
267     mod test {
268         error_chain!{}
269     }
270 
271     error_chain! {
272         links {
273             Test(test::Error, test::ErrorKind);
274         }
275     }
276 }
277 
278 #[cfg(test)]
279 mod foreign_link_test {
280 
281     use std::fmt;
282 
283     // Note: foreign errors must be `pub` because they appear in the
284     // signature of the public foreign_link_error_path
285     #[derive(Debug)]
286     pub struct ForeignError {
287         cause: ForeignErrorCause,
288     }
289 
290     impl ::std::error::Error for ForeignError {
291         fn description(&self) -> &'static str {
292             "Foreign error description"
293         }
294 
295         fn cause(&self) -> Option<&::std::error::Error> {
296             Some(&self.cause)
297         }
298     }
299 
300     impl fmt::Display for ForeignError {
301         fn fmt(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
302             write!(formatter, "Foreign error display")
303         }
304     }
305 
306     #[derive(Debug)]
307     pub struct ForeignErrorCause {}
308 
309     impl ::std::error::Error for ForeignErrorCause {
310         fn description(&self) -> &'static str {
311             "Foreign error cause description"
312         }
313 
314         fn cause(&self) -> Option<&::std::error::Error> {
315             None
316         }
317     }
318 
319     impl fmt::Display for ForeignErrorCause {
320         fn fmt(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
321             write!(formatter, "Foreign error cause display")
322         }
323     }
324 
325     error_chain! {
326         types{
327             Error, ErrorKind, ResultExt, Result;
328         }
329         links {}
330         foreign_links {
331             Foreign(ForeignError);
332             Io(::std::io::Error);
333         }
334         errors {}
335     }
336 
337     #[test]
338     fn display_underlying_error() {
339         let chained_error = try_foreign_error().err().unwrap();
340         assert_eq!(format!("{}", ForeignError { cause: ForeignErrorCause {} }),
341                    format!("{}", chained_error));
342     }
343 
344     #[test]
345     fn finds_cause() {
346         let chained_error = try_foreign_error().err().unwrap();
347         assert_eq!(format!("{}", ForeignErrorCause {}),
348                    format!("{}", ::std::error::Error::cause(&chained_error).unwrap()));
349     }
350 
351     #[test]
352     fn iterates() {
353         let chained_error = try_foreign_error().err().unwrap();
354         let mut error_iter = chained_error.iter();
355         assert!(!format!("{:?}", error_iter).is_empty());
356         assert_eq!(format!("{}", ForeignError { cause: ForeignErrorCause {} }),
357                    format!("{}", error_iter.next().unwrap()));
358         assert_eq!(format!("{}", ForeignErrorCause {}),
359                    format!("{}", error_iter.next().unwrap()));
360         assert_eq!(format!("{:?}", None as Option<&::std::error::Error>),
361                    format!("{:?}", error_iter.next()));
362     }
363 
364     fn try_foreign_error() -> Result<()> {
365         Err(ForeignError { cause: ForeignErrorCause {} })?;
366         Ok(())
367     }
368 }
369 
370 #[cfg(test)]
371 mod attributes_test {
372     #[allow(unused_imports)]
373     use std::io;
374 
375     #[cfg(not(test))]
376     mod inner {
377         error_chain!{}
378     }
379 
380     error_chain! {
381         types {
382             Error, ErrorKind, ResultExt, Result;
383         }
384 
385         links {
386             Inner(inner::Error, inner::ErrorKind) #[cfg(not(test))];
387         }
388 
389         foreign_links {
390             Io(io::Error) #[cfg(not(test))];
391         }
392 
393         errors {
394             #[cfg(not(test))]
395             AnError {
396 
397             }
398         }
399     }
400 }
401 
402 #[test]
403 fn with_result() {
404     error_chain! {
405         types {
406             Error, ErrorKind, ResultExt, Result;
407         }
408     }
409     let _: Result<()> = Ok(());
410 }
411 
412 #[test]
413 fn without_result() {
414     error_chain! {
415         types {
416             Error, ErrorKind, ResultExt;
417         }
418     }
419     let _: Result<(), ()> = Ok(());
420 }
421 
422 #[test]
423 fn documentation() {
424     mod inner {
425         error_chain!{}
426     }
427 
428     error_chain! {
429         links {
430             Inner(inner::Error, inner::ErrorKind) #[doc = "Doc"];
431         }
432         foreign_links {
433             Io(::std::io::Error) #[doc = "Doc"];
434         }
435         errors {
436             /// Doc
437             Variant
438         }
439     }
440 }
441 
442 #[cfg(test)]
443 mod multiple_error_same_mod {
444     error_chain! {
445         types {
446             MyError, MyErrorKind, MyResultExt, MyResult;
447         }
448     }
449     error_chain!{}
450 }
451 
452 #[doc(test)]
453 #[deny(dead_code)]
454 mod allow_dead_code {
455     error_chain!{}
456 }
457 
458 // Make sure links actually work!
459 #[test]
460 fn rustup_regression() {
461     error_chain! {
462         links {
463             Download(error_chain::mock::Error, error_chain::mock::ErrorKind);
464         }
465 
466         foreign_links { }
467 
468         errors {
469             LocatingWorkingDir {
470                 description("could not locate working directory")
471             }
472         }
473     }
474 }
475 
476 #[test]
477 fn error_patterns() {
478     error_chain! {
479         links { }
480 
481         foreign_links { }
482 
483         errors { }
484     }
485 
486     // Tuples look nice when matching errors
487     match Error::from("Test") {
488         Error(ErrorKind::Msg(_), _) => {},
489         _ => {},
490     }
491 }
492 
493 #[test]
494 fn error_first() {
495     error_chain! {
496         errors {
497             LocatingWorkingDir {
498                 description("could not locate working directory")
499             }
500         }
501 
502         links {
503             Download(error_chain::mock::Error, error_chain::mock::ErrorKind);
504         }
505 
506         foreign_links { }
507     }
508 }
509 
510 #[test]
511 fn bail() {
512     error_chain! {
513         errors { Foo }
514     }
515 
516     fn foo() -> Result<()> {
517         bail!(ErrorKind::Foo)
518     }
519 
520     fn bar() -> Result<()> {
521         bail!("bar")
522     }
523 
524     fn baz() -> Result<()> {
525         bail!("{}", "baz")
526     }
527 }
528 
529 #[test]
530 fn ensure() {
531     error_chain! {
532         errors { Bar }
533     }
534 
535     fn foo(x: u8) -> Result<()> {
536         ensure!(x == 42, ErrorKind::Bar);
537         Ok(())
538     }
539 
540     assert!(foo(42).is_ok());
541     assert!(foo(0).is_err());
542 }
543 
544 /// Since the `types` declaration is a list of symbols, check if we
545 /// don't change their meaning or order.
546 #[test]
547 fn types_declarations() {
548     error_chain! {
549         types {
550             MyError, MyErrorKind, MyResultExt, MyResult;
551         }
552     }
553 
554     MyError::from_kind(MyErrorKind::Msg("".into()));
555 
556     let err: Result<(), ::std::io::Error> = Ok(());
557     MyResultExt::chain_err(err, || "").unwrap();
558 
559     let _: MyResult<()> = Ok(());
560 }
561 
562 #[test]
563 /// Calling chain_err over a `Result` containing an error to get a chained error
564 /// and constructing a MyError directly, passing it an error should be equivalent.
565 fn rewrapping() {
566 
567     use std::env::VarError::{self, NotPresent, NotUnicode};
568 
569     error_chain! {
570         foreign_links {
571             VarErr(VarError);
572         }
573 
574         types {
575             MyError, MyErrorKind, MyResultExt, MyResult;
576         }
577     }
578 
579     let result_a_from_func: Result<String, _> = Err(VarError::NotPresent);
580     let result_b_from_func: Result<String, _> = Err(VarError::NotPresent);
581 
582     let our_error_a = result_a_from_func.map_err(|e| match e {
583         NotPresent => MyError::with_chain(e, "env var wasn't provided"),
584         NotUnicode(_) => MyError::with_chain(e, "env var was bork文字化ã"),
585     });
586 
587     let our_error_b = result_b_from_func.or_else(|e| match e {
588         NotPresent => Err(e).chain_err(|| "env var wasn't provided"),
589         NotUnicode(_) => Err(e).chain_err(|| "env var was bork文字化ã"),
590     });
591 
592     assert_eq!(format!("{}", our_error_a.unwrap_err()),
593                format!("{}", our_error_b.unwrap_err()));
594 
595 }
596 
597 #[test]
598 fn comma_in_errors_impl() {
599     error_chain! {
600         links { }
601 
602         foreign_links { }
603 
604         errors {
605             HttpStatus(e: u32) {
606                 description("http request returned an unsuccessful status code"),
607                 display("http request returned an unsuccessful status code: {}", e)
608             }
609         }
610     };
611 }
612 
613 
614 #[test]
615 fn trailing_comma_in_errors_impl() {
616     error_chain! {
617         links { }
618 
619         foreign_links { }
620 
621         errors {
622             HttpStatus(e: u32) {
623                 description("http request returned an unsuccessful status code"),
624                 display("http request returned an unsuccessful status code: {}", e),
625             }
626         }
627     };
628 }
629