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