self.visit_testable(macro_def.name.to_string(), ¯o_def.attrs, |_| ());
}
}
+
+#[cfg(test)]
+mod tests {
+ use super::{TestOptions, make_test};
+
+ #[test]
+ fn make_test_basic() {
+ //basic use: wraps with `fn main`, adds `#![allow(unused)]`
+ let opts = TestOptions::default();
+ let input =
+"assert_eq!(2+2, 4);";
+ let expected =
+"#![allow(unused)]
+fn main() {
+assert_eq!(2+2, 4);
+}".to_string();
+ let output = make_test(input, None, false, &opts);
+ assert_eq!(output, (expected.clone(), 2));
+ }
+
+ #[test]
+ fn make_test_crate_name_no_use() {
+ //if you give a crate name but *don't* use it within the test, it won't bother inserting
+ //the `extern crate` statement
+ let opts = TestOptions::default();
+ let input =
+"assert_eq!(2+2, 4);";
+ let expected =
+"#![allow(unused)]
+fn main() {
+assert_eq!(2+2, 4);
+}".to_string();
+ let output = make_test(input, Some("asdf"), false, &opts);
+ assert_eq!(output, (expected, 2));
+ }
+
+ #[test]
+ fn make_test_crate_name() {
+ //if you give a crate name and use it within the test, it will insert an `extern crate`
+ //statement before `fn main`
+ let opts = TestOptions::default();
+ let input =
+"use asdf::qwop;
+assert_eq!(2+2, 4);";
+ let expected =
+"#![allow(unused)]
+extern crate asdf;
+fn main() {
+use asdf::qwop;
+assert_eq!(2+2, 4);
+}".to_string();
+ let output = make_test(input, Some("asdf"), false, &opts);
+ assert_eq!(output, (expected, 3));
+ }
+
+ #[test]
+ fn make_test_no_crate_inject() {
+ //even if you do use the crate within the test, setting `opts.no_crate_inject` will skip
+ //adding it anyway
+ let opts = TestOptions {
+ no_crate_inject: true,
+ attrs: vec![],
+ };
+ let input =
+"use asdf::qwop;
+assert_eq!(2+2, 4);";
+ let expected =
+"#![allow(unused)]
+fn main() {
+use asdf::qwop;
+assert_eq!(2+2, 4);
+}".to_string();
+ let output = make_test(input, Some("asdf"), false, &opts);
+ assert_eq!(output, (expected, 2));
+ }
+
+ #[test]
+ fn make_test_ignore_std() {
+ //even if you include a crate name, and use it in the doctest, we still won't include an
+ //`extern crate` statement if the crate is "std" - that's included already by the compiler!
+ let opts = TestOptions::default();
+ let input =
+"use std::*;
+assert_eq!(2+2, 4);";
+ let expected =
+"#![allow(unused)]
+fn main() {
+use std::*;
+assert_eq!(2+2, 4);
+}".to_string();
+ let output = make_test(input, Some("std"), false, &opts);
+ assert_eq!(output, (expected, 2));
+ }
+
+ #[test]
+ fn make_test_manual_extern_crate() {
+ //when you manually include an `extern crate` statement in your doctest, make_test assumes
+ //you've included one for your own crate too
+ let opts = TestOptions::default();
+ let input =
+"extern crate asdf;
+use asdf::qwop;
+assert_eq!(2+2, 4);";
+ let expected =
+"#![allow(unused)]
+fn main() {
+extern crate asdf;
+use asdf::qwop;
+assert_eq!(2+2, 4);
+}".to_string();
+ let output = make_test(input, Some("asdf"), false, &opts);
+ assert_eq!(output, (expected, 2));
+ }
+
+ #[test]
+ fn make_test_opts_attrs() {
+ //if you supplied some doctest attributes with #![doc(test(attr(...)))], it will use those
+ //instead of the stock #![allow(unused)]
+ let mut opts = TestOptions::default();
+ opts.attrs.push("feature(sick_rad)".to_string());
+ let input =
+"use asdf::qwop;
+assert_eq!(2+2, 4);";
+ let expected =
+"#![feature(sick_rad)]
+extern crate asdf;
+fn main() {
+use asdf::qwop;
+assert_eq!(2+2, 4);
+}".to_string();
+ let output = make_test(input, Some("asdf"), false, &opts);
+ assert_eq!(output, (expected, 3));
+
+ //adding more will also bump the returned line offset
+ opts.attrs.push("feature(hella_dope)".to_string());
+ let expected =
+"#![feature(sick_rad)]
+#![feature(hella_dope)]
+extern crate asdf;
+fn main() {
+use asdf::qwop;
+assert_eq!(2+2, 4);
+}".to_string();
+ let output = make_test(input, Some("asdf"), false, &opts);
+ assert_eq!(output, (expected, 4));
+ }
+
+ #[test]
+ fn make_test_crate_attrs() {
+ //including inner attributes in your doctest will apply them to the whole "crate", pasting
+ //them outside the generated main function
+ let opts = TestOptions::default();
+ let input =
+"#![feature(sick_rad)]
+assert_eq!(2+2, 4);";
+ let expected =
+"#![allow(unused)]
+#![feature(sick_rad)]
+fn main() {
+assert_eq!(2+2, 4);
+}".to_string();
+ let output = make_test(input, None, false, &opts);
+ assert_eq!(output, (expected, 2));
+ }
+
+ #[test]
+ fn make_test_with_main() {
+ //including your own `fn main` wrapper lets the test use it verbatim
+ let opts = TestOptions::default();
+ let input =
+"fn main() {
+ assert_eq!(2+2, 4);
+}";
+ let expected =
+"#![allow(unused)]
+fn main() {
+ assert_eq!(2+2, 4);
+}".to_string();
+ let output = make_test(input, None, false, &opts);
+ assert_eq!(output, (expected, 1));
+ }
+
+ #[test]
+ fn make_test_fake_main() {
+ //...but putting it in a comment will still provide a wrapper
+ let opts = TestOptions::default();
+ let input =
+"//Ceci n'est pas une `fn main`
+assert_eq!(2+2, 4);";
+ let expected =
+"#![allow(unused)]
+fn main() {
+//Ceci n'est pas une `fn main`
+assert_eq!(2+2, 4);
+}".to_string();
+ let output = make_test(input, None, false, &opts);
+ assert_eq!(output, (expected.clone(), 2));
+ }
+
+ #[test]
+ fn make_test_dont_insert_main() {
+ //even with that, if you set `dont_insert_main`, it won't create the `fn main` wrapper
+ let opts = TestOptions::default();
+ let input =
+"//Ceci n'est pas une `fn main`
+assert_eq!(2+2, 4);";
+ let expected =
+"#![allow(unused)]
+//Ceci n'est pas une `fn main`
+assert_eq!(2+2, 4);".to_string();
+ let output = make_test(input, None, true, &opts);
+ assert_eq!(output, (expected.clone(), 1));
+ }
+}