use mercurius::{Event, FrontMatter, MarkdownExt, Parser, Raw, Result, Tag, ReadableDate};
use std::cell::RefCell;
use std::rc::Rc;
use std::iter::once;

macro_rules! assert_events {
    ($iter:expr, $( $event:expr), *) => {
        $(
            assert_eq!($iter.next(), Some($event));
        )*
        assert_eq!($iter.next(), None);
    };
}

#[test]
fn frontmatter_overwrite() -> Result<()> {
    let mut iter = Parser::new(include_str!("data/test.md"))?
        .after(
            |e| match &e {
                Event::End(Tag::Heading(1)) => true,
                _ => false,
            },
            |fm| {
                vec![Event::Text(
                    fm.as_ref()
                        .and_then(|fm| Some(fm.title.clone()))
                        .unwrap_or("Nothing".into())
                        .into(),
                )]
            },
        )
        .link(Parser::new(include_str!("data/frontmatter.md"))?.after(
            |e| match &e {
                Event::End(Tag::Heading(1)) => true,
                _ => false,
            },
            |fm| {
                vec![Event::Text(
                    fm.as_ref()
                        .and_then(|fm| Some(fm.title.clone()))
                        .unwrap_or("Nothing".into())
                        .into(),
                )]
            },
        ));
    assert_events!(
        iter,
        Event::Start(Tag::Heading(1)),
        Event::Text("Heading".into()),
        Event::End(Tag::Heading(1)),
        Event::Text("FrontMatter".into()),
        Event::Start(Tag::Heading(1)),
        Event::Text("Heading".into()),
        Event::End(Tag::Heading(1)),
        Event::Text("FrontMatter".into())
    );
    Ok(())
}

#[test]
fn frontmatter_inspect() {
    let mut fst: Option<FrontMatter> = None;
    let _ = Raw::new(
        Rc::new(RefCell::new(Some(FrontMatter {
            title: "First".into(),
            create_date: ReadableDate::new(2000, 1, 2),
            ..Default::default()
        }))).into(),
        once("foo".to_owned()),
    ).after(|e| e == "foo", |fm| once(fm.as_ref().unwrap().title.clone()))
    .inspect_frontmatter(&mut fst).collect::<Vec<_>>();
    assert_eq!(fst.unwrap().title, "First");
}
